Content Schemas¶
Every interrupt you raise is a content class — a typed description of what
you're asking the operator to do. Pick a class below by matching your use
case, wrap your payload in it, and pass it to raise_interrupt. See the
Integration Guide for one
worked example per family.
How to pick a class¶
Every concrete class belongs to one of 4 families (HitlType), and every
family has 2-3 concrete variants (HitlSubType) that differ in what the
operator does and what comes back:
| Family | Class | Operator does this | Responds with (TypedDict) |
|---|---|---|---|
| Approval — accept/reject something | BinaryApprovalContent |
Picks approve or reject, no edits | BinaryApprovalResponse — {"decision": str} |
ModifyApprovalContent |
Approves/rejects, may edit fields first | ModifyApprovalResponse — {"decision": str, "values"?: dict} |
|
| Decision — choose from options | SingleDecisionContent |
Picks exactly one option | SingleDecisionResponse — {"selected": str} |
MultiDecisionContent |
Picks one-to-many options | MultiDecisionResponse — {"selected": list[str]} |
|
RankDecisionContent |
Orders all options by preference | RankDecisionResponse — {"ranking": list[str]} |
|
| Context — collect info the agent needs | FreetextContextContent |
Types an open-ended answer | FreetextContextResponse — {"value": str} |
FormContextContent |
Fills in a multi-field form | FormContextResponse — {"values": dict} |
|
ConfirmContextContent |
Reads a statement and acknowledges it | ConfirmContextResponse — {"confirmed": bool} |
|
| Edit — review/revise agent-generated content | ContentEditContent |
Reviews and optionally rewrites a text draft | ContentEditResponse — {"content": str} |
ToolArgsEditContent |
Reviews and edits pending tool-call args | ToolArgsEditResponse — {"args": dict} |
All 9 concrete classes inherit from one abstract base, HitlContent, through
an intermediate per-family base (ApprovalContent, DecisionContent,
ContextContent, EditContent) that fixes the type constant. You never
instantiate the abstract or family bases directly — always use one of the 9
leaf classes in the table above.
hgateway_sdk.HitlContent
dataclass
¶
HitlContent(prompt: str)
Bases: Generic[TResp], ABC
Abstract base for all HITL interrupt content objects.
Parameterised by TResp — the TypedDict that describes the operator's
reply for the concrete subclass. Developers never instantiate this class
directly; use one of the 10 concrete subclasses.
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question or instruction displayed to the operator
above the interaction widget (e.g. |
type |
HitlType
|
Class-level constant ( |
sub_type |
Enum
|
Class-level constant ( |
Approval¶
Ask the operator to accept or reject something the agent has produced or is about to do.
hgateway_sdk.ApprovalContent
dataclass
¶
ApprovalContent(prompt: str)
Bases: HitlContent[TResp]
Base for Approval-family interrupts (type = HitlType.APPROVAL).
Approval interrupts ask an operator to accept or reject something the agent has produced or is about to do. The two concrete variants differ in whether the operator can also make edits:
BinaryApprovalContent— approve/reject only (no editing).ModifyApprovalContent— approve/reject and optionally modify fields.
Attributes:
| Name | Type | Description |
|---|---|---|
type |
HitlType
|
Always |
hgateway_sdk.BinaryApprovalContent
dataclass
¶
BinaryApprovalContent(prompt: str, choices: list[Choice] = (lambda: [Choice(constants.APPROVE_KEY, constants.APPROVE_LABEL), Choice(constants.REJECT_KEY, constants.REJECT_LABEL)])())
Bases: ApprovalContent[BinaryApprovalResponse]
Approval interrupt that asks the operator to approve or reject an action.
The operator is shown a prompt and two buttons (by default Approve
and Reject). The gateway returns a BinaryApprovalResponse whose
decision key contains the key string of the chosen Choice.
Usage example::
import hgateway_sdk as hg
content = hg.BinaryApprovalContent(
prompt="Approve sending this email to the customer?",
choices=[
hg.Choice("approve", "Send it"),
hg.Choice("reject", "Cancel", irreversible=False),
],
)
hg.raise_interrupt("send_email_approval", content)
# Operator response shape: BinaryApprovalResponse
# {"decision": "approve"} or {"decision": "reject"}
If choices is omitted the SDK defaults to a standard Approve / Reject
pair (keys "approve" / "reject").
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question shown to the operator. |
choices |
list[Choice]
|
Ordered list of |
sub_type |
Approval
|
Always |
hgateway_sdk.ModifyApprovalContent
dataclass
¶
ModifyApprovalContent(prompt: str, choices: list[Choice] = list(), modifiable: list[ModifiableField] = list())
Bases: ApprovalContent[ModifyApprovalResponse]
Approval interrupt that lets the operator edit fields before approving.
Similar to BinaryApprovalContent but also surfaces a set of
ModifiableField values the operator can change before they submit their
decision. The gateway returns a ModifyApprovalResponse with the chosen
decision key and a values dict of any edited fields.
Usage example::
import hgateway_sdk as hg
content = hg.ModifyApprovalContent(
prompt="Review and approve the refund amount.",
choices=[
hg.Choice("approve", "Approve"),
hg.Choice("reject", "Reject"),
],
modifiable=[
hg.ModifiableField("amount", "Refund Amount", 50.00, hg.FieldType.NUMBER),
],
)
hg.raise_interrupt("refund_approval", content)
# Operator response shape: ModifyApprovalResponse
# {"decision": "approve", "values": {"amount": 45.00}}
# values key is NotRequired — absent when the operator made no edits.
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question shown to the operator. |
choices |
list[Choice]
|
List of |
modifiable |
list[ModifiableField]
|
List of |
sub_type |
Approval
|
Always |
Decision¶
Present the operator with a list of Choice elements
and ask them to choose.
hgateway_sdk.DecisionContent
dataclass
¶
DecisionContent(prompt: str)
Bases: HitlContent[TResp]
Base for Decision-family interrupts (type = HitlType.DECISION).
Decision interrupts present the operator with a list of Choice objects
and ask them to choose. The three concrete variants differ in how many
items can be selected and in what form the result is returned:
SingleDecisionContent— pick exactly one option.MultiDecisionContent— pick one-to-many options with optional bounds.RankDecisionContent— order all options by preference.
Attributes:
| Name | Type | Description |
|---|---|---|
type |
HitlType
|
Always |
hgateway_sdk.SingleDecisionContent
dataclass
¶
SingleDecisionContent(prompt: str, options: list[Choice] = list())
Bases: DecisionContent[SingleDecisionResponse]
Decision interrupt that asks the operator to choose exactly one option.
The operator is shown a prompt and a list of Choice objects. They
must select exactly one. The gateway returns a SingleDecisionResponse
whose selected key is the key of the chosen option.
Usage example::
import hgateway_sdk as hg
content = hg.SingleDecisionContent(
prompt="Which deployment environment should we target?",
options=[
hg.Choice("staging", "Staging", description="Safe sandbox"),
hg.Choice("prod", "Production", impact_hint="Irreversible"),
],
)
hg.raise_interrupt("deploy_env_decision", content)
# Operator response shape: SingleDecisionResponse
# {"selected": "staging"}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question shown to the operator. |
options |
list[Choice]
|
Ordered list of |
sub_type |
Decision
|
Always |
hgateway_sdk.MultiDecisionContent
dataclass
¶
MultiDecisionContent(prompt: str, options: list[Choice] = list(), min_select: int = 1, max_select: int | None = None)
Bases: DecisionContent[MultiDecisionResponse]
Decision interrupt that asks the operator to choose one or more options.
Like SingleDecisionContent but the operator may select multiple items.
The selection is bounded by min_select (inclusive lower bound) and
max_select (inclusive upper bound; None means no upper limit). The
gateway returns a MultiDecisionResponse whose selected key is a list
of the chosen option keys.
Usage example::
import hgateway_sdk as hg
content = hg.MultiDecisionContent(
prompt="Select the teams to notify about this incident.",
options=[
hg.Choice("infra", "Infrastructure"),
hg.Choice("backend", "Backend"),
hg.Choice("frontend", "Frontend"),
],
min_select=1,
max_select=2,
)
hg.raise_interrupt("notify_teams", content)
# Operator response shape: MultiDecisionResponse
# {"selected": ["infra", "backend"]}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question shown to the operator. |
options |
list[Choice]
|
Ordered list of |
min_select |
int
|
Minimum number of options the operator must select.
Defaults to |
max_select |
int | None
|
Maximum number of options the operator may select.
|
sub_type |
Decision
|
Always |
hgateway_sdk.RankDecisionContent
dataclass
¶
RankDecisionContent(prompt: str, options: list[Choice] = list())
Bases: DecisionContent[RankDecisionResponse]
Decision interrupt that asks the operator to rank all options.
All options are presented and the operator must order them from most to
least preferred. The gateway returns a RankDecisionResponse whose
ranking key is an ordered list of all option keys, highest preference
first.
Usage example::
import hgateway_sdk as hg
content = hg.RankDecisionContent(
prompt="Rank these outreach channels by priority.",
options=[
hg.Choice("email", "Email"),
hg.Choice("sms", "SMS"),
hg.Choice("push", "Push Notification"),
],
)
hg.raise_interrupt("channel_rank", content)
# Operator response shape: RankDecisionResponse
# {"ranking": ["push", "email", "sms"]}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question shown to the operator. |
options |
list[Choice]
|
Ordered list of |
sub_type |
Decision
|
Always |
Context¶
Ask the operator to provide information the agent needs before it can continue.
hgateway_sdk.ContextContent
dataclass
¶
ContextContent(prompt: str)
Bases: HitlContent[TResp]
Base for Context-family interrupts (type = HitlType.CONTEXT).
Context interrupts ask the operator to provide information that the agent needs before it can continue. The three concrete variants differ in the structure of the expected input:
FreetextContextContent— open-ended text answer.FormContextContent— structured multi-field form.ConfirmContextContent— simple acknowledgement (read and confirm).
Attributes:
| Name | Type | Description |
|---|---|---|
type |
HitlType
|
Always |
hgateway_sdk.FreetextContextContent
dataclass
¶
FreetextContextContent(prompt: str, input: FreetextInput = None)
Bases: ContextContent[FreetextContextResponse]
Context interrupt that collects a free-form text response from the operator.
The operator sees a prompt and a single text-area input described by
the FreetextInput element. The gateway returns a
FreetextContextResponse whose value key holds the typed text.
Usage example::
import hgateway_sdk as hg
content = hg.FreetextContextContent(
prompt="What is the customer's preferred resolution?",
input=hg.FreetextInput(
label="Customer preference",
placeholder="Describe in a few sentences…",
),
)
hg.raise_interrupt("customer_pref", content)
# Operator response shape: FreetextContextResponse
# {"value": "The customer prefers a full refund."}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable question shown to the operator. |
input |
FreetextInput
|
A |
sub_type |
Context
|
Always |
hgateway_sdk.FormContextContent
dataclass
¶
FormContextContent(prompt: str, fields: list[FormField] = list())
Bases: ContextContent[FormContextResponse]
Context interrupt that collects structured data via a multi-field form.
Each FormField in fields becomes one input row in the gateway UI
with its own label, type, and optional placeholder. The gateway returns a
FormContextResponse whose values key is a dict mapping each field
key to the value the operator entered.
Usage example::
import hgateway_sdk as hg
from hgateway_sdk.constants import FieldType
content = hg.FormContextContent(
prompt="Provide the ticket details before we escalate.",
fields=[
hg.FormField("ticket_id", "Ticket ID", FieldType.STRING, required=True),
hg.FormField("priority", "Priority (1-5)", FieldType.NUMBER),
hg.FormField("is_urgent", "Mark as urgent?", FieldType.BOOLEAN),
],
)
hg.raise_interrupt("ticket_details", content)
# Operator response shape: FormContextResponse
# {"values": {"ticket_id": "TKT-123", "priority": 2, "is_urgent": True}}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable instruction shown above the form. |
fields |
list[FormField]
|
Ordered list of |
sub_type |
Context
|
Always |
hgateway_sdk.ConfirmContextContent
dataclass
¶
ConfirmContextContent(prompt: str, statement: str = '')
Bases: ContextContent[ConfirmContextResponse]
Context interrupt that asks the operator to acknowledge a statement.
Useful when the agent needs to ensure a human has read a notice, warning, or
policy disclosure before the workflow continues. No data is collected beyond
the acknowledgement itself. The gateway returns a ConfirmContextResponse
whose confirmed key is True when the operator clicks "Confirm".
Usage example::
import hgateway_sdk as hg
content = hg.ConfirmContextContent(
prompt="Please confirm you have read the data-retention policy.",
statement=(
"By confirming, you acknowledge that all customer PII will be "
"deleted after 90 days as required by our data policy."
),
)
hg.raise_interrupt("policy_ack", content)
# Operator response shape: ConfirmContextResponse
# {"confirmed": True}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Human-readable instruction shown to the operator (e.g. "Please read and confirm the following."). |
statement |
str
|
The body text the operator must read before confirming. Defaults to an empty string. |
sub_type |
Context
|
Always |
Edit¶
Surface agent-generated content or planned tool arguments for the operator to inspect and optionally revise before execution proceeds.
hgateway_sdk.EditContent
dataclass
¶
EditContent(prompt: str)
Bases: HitlContent[TResp]
Base for Edit-family interrupts (type = HitlType.EDIT).
Edit interrupts surface agent-generated content or planned tool arguments for the operator to inspect and optionally revise before execution proceeds. The two concrete variants differ in what is being edited:
ContentEditContent— a free-form text draft (e.g. an email body).ToolArgsEditContent— structured arguments for a pending tool call.
Attributes:
| Name | Type | Description |
|---|---|---|
type |
HitlType
|
Always |
hgateway_sdk.ContentEditContent
dataclass
¶
ContentEditContent(prompt: str, draft: str = '')
Bases: EditContent[ContentEditResponse]
Edit interrupt that surfaces a free-form text draft for the operator to revise.
The operator sees the draft text in an editable text area together with
the prompt. They may change it freely or leave it as-is and submit.
The gateway returns a ContentEditResponse whose content key holds
the (possibly edited) text.
Usage example::
import hgateway_sdk as hg
content = hg.ContentEditContent(
prompt="Review the generated email and edit if needed before sending.",
draft=(
"Hi Jane,\n\n"
"We're following up on your recent support request…\n\n"
"Best, Support Team"
),
)
hg.raise_interrupt("email_draft_review", content)
# Operator response shape: ContentEditResponse
# {"content": "Hi Jane,\n\nThank you for reaching out…\n\nBest, Support Team"}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Instruction shown to the operator above the editable text area. |
draft |
str
|
Initial text the operator sees and may edit. Defaults to an empty string. |
sub_type |
Edit
|
Always |
hgateway_sdk.ToolArgsEditContent
dataclass
¶
ToolArgsEditContent(prompt: str, tool_name: str = '', args: list[ToolArg] = list())
Bases: EditContent[ToolArgsEditResponse]
Edit interrupt that exposes a tool call's arguments for operator review.
Before the agent invokes a tool, the operator can inspect each ToolArg
and change the value of any editable arguments. Non-editable args are
shown read-only. The gateway returns a ToolArgsEditResponse whose
args key is a dict mapping each arg key to its (possibly updated)
value.
Usage example::
import hgateway_sdk as hg
from hgateway_sdk.constants import FieldType
content = hg.ToolArgsEditContent(
prompt="Review the SQL query arguments before execution.",
tool_name="run_sql",
args=[
hg.ToolArg("table", "Target Table", "orders", FieldType.STRING, editable=False),
hg.ToolArg("limit", "Row Limit", 1000, FieldType.NUMBER, editable=True),
],
)
hg.raise_interrupt("sql_args_review", content)
# Operator response shape: ToolArgsEditResponse
# {"args": {"table": "orders", "limit": 500}}
Attributes:
| Name | Type | Description |
|---|---|---|
prompt |
str
|
Instruction shown to the operator above the argument list. |
tool_name |
str
|
Name of the tool that will be called. Displayed as context. Defaults to an empty string. |
args |
list[ToolArg]
|
List of |
sub_type |
Edit
|
Always |
Utility elements¶
The primitive objects nested inside the content classes above — never raised on their own.
- Choice — selectable item used by Approval (as a button) and Decision
(as a list item) content:
BinaryApprovalContent.choices,ModifyApprovalContent.choices,SingleDecisionContent.options,MultiDecisionContent.options,RankDecisionContent.options. - FreetextInput — text-area descriptor for
FreetextContextContent.input. - FormField — one typed input row for
FormContextContent.fields. - ModifiableField — one editable value for
ModifyApprovalContent.modifiable. - ToolArg — one named tool-call argument for
ToolArgsEditContent.args.
hgateway_sdk.Choice
dataclass
¶
Choice(key: str, label: str, description: Optional[str] = None, irreversible: bool = False, impact_hint: Optional[str] = None)
A labelled selectable item presented to the operator.
Used both as a button option in Approval interrupts
(BinaryApprovalContent.choices, ModifyApprovalContent.choices) and
as a list item in Decision interrupts (SingleDecisionContent.options,
MultiDecisionContent.options, RankDecisionContent.options).
Usage example (nested inside content)::
import hgateway_sdk as hg
hg.BinaryApprovalContent(
prompt="Approve the refund?",
choices=[
hg.Choice("approve", "Approve Refund"),
hg.Choice("reject", "Reject", irreversible=False, impact_hint="No refund issued"),
],
)
hg.SingleDecisionContent(
prompt="Which deployment environment?",
options=[
hg.Choice("staging", "Staging", description="Low-risk test environment"),
hg.Choice("prod", "Production", irreversible=True, impact_hint="Affects live users"),
],
)
Attributes:
| Name | Type | Description |
|---|---|---|
key |
str
|
Machine-readable identifier returned in the response
( |
label |
str
|
Human-readable label displayed to the operator. |
description |
Optional[str]
|
Optional longer text providing context about this choice.
Displayed below the label in the gateway UI. Defaults to |
irreversible |
bool
|
When |
impact_hint |
Optional[str]
|
Optional short text displayed alongside the item to give
the operator a risk or consequence hint (e.g. |
hgateway_sdk.FreetextInput
dataclass
¶
FreetextInput(label: str, placeholder: Optional[str] = None)
Descriptor for the single open-text input in a FreetextContextContent.
Defines the label and optional placeholder shown to the operator inside the
text-area widget. There is exactly one FreetextInput per
FreetextContextContent.
Usage example (nested inside content)::
import hgateway_sdk as hg
hg.FreetextContextContent(
prompt="Describe the customer's preferred outcome.",
input=hg.FreetextInput(
label="Customer preference",
placeholder="Summarise in 1-3 sentences…",
),
)
Attributes:
| Name | Type | Description |
|---|---|---|
label |
str
|
Human-readable label rendered above the text area. |
placeholder |
Optional[str]
|
Optional greyed-out hint text shown inside an empty text
area. Defaults to |
hgateway_sdk.FormField
dataclass
¶
FormField(key: str, label: str, type: FieldType, required: bool = False, placeholder: Optional[str] = None)
A single typed input row inside a FormContextContent interrupt.
Each FormField maps to one labelled input widget in the gateway UI.
The type attribute controls what kind of widget is rendered and what
value type is returned in FormContextResponse.values.
Usage example (nested inside content)::
import hgateway_sdk as hg
from hgateway_sdk.constants import FieldType
hg.FormContextContent(
prompt="Provide escalation details.",
fields=[
hg.FormField("ticket_id", "Ticket ID", FieldType.STRING, required=True,
placeholder="e.g. TKT-001"),
hg.FormField("priority", "Priority (1-5)", FieldType.NUMBER),
hg.FormField("urgent", "Mark urgent?", FieldType.BOOLEAN),
],
)
Attributes:
| Name | Type | Description |
|---|---|---|
key |
str
|
Machine-readable field identifier. Used as the key in
|
label |
str
|
Human-readable field label shown next to the input. |
type |
FieldType
|
|
required |
bool
|
When |
placeholder |
Optional[str]
|
Optional hint text shown inside an empty input (e.g.
|
hgateway_sdk.ModifiableField
dataclass
¶
ModifiableField(key: str, label: str, value: Any, type: FieldType)
A named, typed value the operator can change as part of a modify-approval.
Used inside ModifyApprovalContent.modifiable to expose fields that the
operator may adjust before they submit their approval decision. All fields
in this list are always editable; use ToolArg with editable=False
if you need read-only display.
Usage example (nested inside content)::
import hgateway_sdk as hg
from hgateway_sdk.constants import FieldType
hg.ModifyApprovalContent(
prompt="Review and approve the refund.",
choices=[hg.Choice("approve", "Approve"), hg.Choice("reject", "Reject")],
modifiable=[
hg.ModifiableField("amount", "Refund Amount (USD)", 75.00, FieldType.NUMBER),
hg.ModifiableField("note", "Internal Note", "", FieldType.STRING),
hg.ModifiableField(
"reason", "Reason", ["duplicate", "fraud", "other"], FieldType.DROPDOWN
),
],
)
Attributes:
| Name | Type | Description |
|---|---|---|
key |
str
|
Machine-readable field identifier. Used as the key in
|
label |
str
|
Human-readable label shown next to the input widget. |
value |
Any
|
Current (pre-populated) value shown to the operator. Can be any
JSON-serialisable type consistent with |
type |
FieldType
|
|
hgateway_sdk.ToolArg
dataclass
¶
ToolArg(key: str, label: str, value: Any, type: FieldType, editable: bool = True)
A single named argument in a pending tool call, surfaced for operator review.
Used inside ToolArgsEditContent.args to expose each argument of a
planned tool call. Arguments with editable=True can be changed by the
operator; arguments with editable=False are shown read-only as context.
Usage example (nested inside content)::
import hgateway_sdk as hg
from hgateway_sdk.constants import FieldType
hg.ToolArgsEditContent(
prompt="Review SQL arguments before execution.",
tool_name="run_sql",
args=[
hg.ToolArg("table", "Target Table", "orders", FieldType.STRING, editable=False),
hg.ToolArg("limit", "Row Limit", 1000, FieldType.NUMBER, editable=True),
hg.ToolArg("dry_run", "Dry Run?", False, FieldType.BOOLEAN, editable=True),
],
)
Attributes:
| Name | Type | Description |
|---|---|---|
key |
str
|
Machine-readable argument name. Used as the key in
|
label |
str
|
Human-readable argument label shown in the gateway UI. |
value |
Any
|
Pre-populated current value of the argument. Can be any
JSON-serialisable type consistent with |
type |
FieldType
|
|
editable |
bool
|
When |