add_test_end_users #
Generated automatically from the published contract sources.
A script calls this action over HTTPS at POST https://turnzero.ai/api/v1/actions/add_test_end_users, with a bearer credential and the action's payload as the JSON body. An MCP connection lists this action as the tool tzcloud_add_test_end_users.
Build metadata: Registered in this build. Registration describes the default dispatcher in this build. It does not guarantee that a caller has the required credential or grant, that a tool is listed for that connection, or that the required service is configured.
Contract description #
Create test end users on an application's sign-in realm with labels, or remove them with remove: true and end_users or all: true. Pass application and environment. This tests sign-in without a person or mailbox. Each user has <label>@synthetic.turnzero.ai, receives no mail, and is removed after 48 hours. Open the returned test sign-in page, enter its address, get its code with read_test_signin_code, and enter the code; the session is real and your code runs unchanged.
On production, and under workforce on development too, a minted token needs the test_end_users grant; a session needs none. Removal needs no browser approval, removes held codes, and ends sessions on every router within sixty seconds. Removing a real end user is refused; use delete_end_user for that.
More about this action #
Your session creates test end users on every realm. A minted token needs the test_end_users grant on production, and under the workforce audience on either realm. A creation is refused test_end_users_not_admitted where the realm or your credential is not admitted, and test_end_users_ceiling_reached past twenty on the realm or fifty created within the hour.
The environment argument is required: pass development or production, the environment whose realm you address. The development realm exists only after create_environment has turned development on.
The development realm accepts every credential from its creation, except under the workforce audience. create_environment removes no test end user. Mint a token with the test_end_users grant with mint_token; the person claims it with token claim.
The call returns test_signin_page, the realm's test sign-in page. For each label it returns the user's id, label, email, expires_at, and created. Where an unexpired test end user already has a label, the call returns that user with created false and creates nothing, so a repeat is safe. Where the test end user with a label has expired, the call removes it and creates it afresh.
Test end users count toward no user count or limit. Where the call is refused test_end_users_not_admitted, the refusal's detail gives the remedy. The call is also refused not_test_end_user for a label whose address belongs to a real end user, and test_end_users_disabled while the platform's TEST_END_USERS setting is off.
The labels argument takes one to twenty labels. Each label is the local part of a test end user's address at the fixture domain synthetic.turnzero.ai. A label is three to forty characters: a lowercase letter, then lowercase letters, digits, and hyphens. A label whose address another end user of the realm has is refused 409 not_test_end_user.
remove: true removes test end users at once, passing end_users, their ids, up to twenty, or all: true. The environment argument is required: development or production, the realm you address. The call creates no pending action and needs no approval, because a test end user has no person's data. Each removal also deletes the user's held codes and ends the sign-ins they could still confirm. The call is refused whole with not_test_end_user, removing nothing, where any listed user is not a test end user of that realm; remove a real end user with delete_end_user.
remove: true works while the platform's TEST_END_USERS setting is off, so you can always clean up. A member the other form takes is refused invalid_request by name: labels is a creation's alone, and end_users and all a removal's.
To create, pass application, environment, and one to twenty labels. To remove, pass application, environment, remove: true, and end_users or all: true.
Access and action metadata #
{
"name": "add_test_end_users",
"resource": "realm",
"tier": "reversible",
"surface": "tzcloud",
"product": "cloud",
"summary": "Create or remove the test end users of one realm of your account's own application. A call with `labels` makes up to twenty, `application` and `environment` both required. Each is a user row holding one verified `email` identity `<label>@synthetic.turnzero.ai`, expiring 48 hours after its creation, and counted as no user. It signs in through the realm's own emailed-code route, its code held for `read_test_signin_code` and never sent. For a label an unexpired test end user of the realm holds, the call returns that user unchanged with `created` false, so a retry creates nothing. A label whose row has expired is removed and created afresh. It admits the account's session and a token carrying `test_end_users` on every realm. On a production realm, and on a workforce application's realm, it refuses any other minted token `test_end_users_not_admitted`. Each creation there writes one info line with the application, the environment, the count, and the credential, and no address. Refused `test_end_users_ceiling_reached` past twenty unexpired test end users on the realm or fifty created by the application's realms within the hour. Refused `not_test_end_user` for a label whose address another end user of the realm holds, and `test_end_users_disabled` while the control plane's `TEST_END_USERS` setting reads `off`. `remove: true` removes test end users at once, with no pending action, `application` and `environment` both required and either `end_users` or `all` true: each removal ends the user's rows, identities, and sessions, writes the user revocation row the routers sync, deletes the user's held codes, and takes the live tickets they were started under. Refused whole `not_test_end_user` where any named user is not a test end user of the realm. A removal is admitted while `TEST_END_USERS` reads `off`, so an operator's stop strands no test end user.",
"annotations": {
"readOnlyHint": false,
"destructiveHint": true,
"openWorldHint": false
}
}
MCP catalog entry #
{
"name": "add_test_end_users",
"title": "Create or remove test app users",
"tier": "reversible",
"summary": "Create test end users on an application's sign-in realm with `labels`, or remove them with `remove: true` and `end_users` or `all: true`. Pass `application` and `environment`. This tests sign-in without a person or mailbox. Each user has `<label>@synthetic.turnzero.ai`, receives no mail, and is removed after 48 hours. Open the returned test sign-in page, enter its address, get its code with `read_test_signin_code`, and enter the code; the session is real and your code runs unchanged.\n\nOn production, and under `workforce` on development too, a minted token needs the `test_end_users` grant; a session needs none. Removal needs no browser approval, removes held codes, and ends sessions on every router within sixty seconds. Removing a real end user is refused; use `delete_end_user` for that.",
"owners": [
"ACS-L0-21",
"ACS-L0-20",
"PLD-L0-40",
"ACS-L0-06"
],
"scenario": "ACS-L0-21"
}
request #
| JSON pointer | Description and constraints |
|---|---|
| "" (root) | Type: object Required fields: ["application"] Additional properties: false Retired members: expires_in_days: Each test end user lasts 48 hours from its creation, one fixed lifetime: call again without expires_in_days. act: Leave act out: pass labels to add, or remove: true with end_users or all. |
| / |
The application id, from list_applications; one of your account's own.Type: string |
| / |
Required by both acts, and refused invalid_request without it: the environment whose realm you address.Type: string Pattern: ^(development|production)$ |
| / |
Required to create: each the local part of a test end user's address at the fixture domain synthetic.turnzero.ai; one whose address another end user holds is refused 409 not_test_end_user.Type: array Minimum items: 1 Maximum items: 20 |
| / |
Type: string Pattern: ^[a-z][a-z0-9-]{2,39}$ |
| / |
To delete: the test end users' ids, one of end_users and all required and never both; an id that is not a test end user of the realm refuses the whole request 409 not_test_end_user, and nothing is removed.Type: array Minimum items: 1 Maximum items: 20 |
| / |
Type: string |
| / |
To delete every test end user of the realm; one of end_users and all is required, and never both.Required value: true |
| / |
true removes test end users at once, naming end_users or all.Type: boolean |
response #
| JSON pointer | Description and constraints |
|---|---|
| "" (root) | Type: object Required fields: ["contract_version","realm","application"] Additional properties: false |
| / |
Required value: 1 |
| / |
The realm identifier: the application id for production, <id>:development for development.Type: string |
| / |
Type: string |
| / |
The environment whose realm the call addressed. Type: string Pattern: ^(development|production)$ |
| / |
On a creation: The realm's test sign-in page, /__account/signin/test on the environment's hostname, which offers the emailed-code form to a test end user on every admitting realm with a non-empty route set.Type: string |
| / |
On a creation: one entry per label, in the request's order. Type: array Minimum items: 1 Maximum items: 20 |
| / |
Type: object Required fields: ["id","label","email","expires_at","created"] Additional properties: false |
| / |
The test end user's opaque identifier, the one list_end_users returns.Type: string |
| / |
Type: string |
| / |
<label>@synthetic.turnzero.ai, the verified address the user signs in with.Type: string |
| / |
The instant from which the platform's expiry pass removes the user, within ten minutes. Type: string |
| / |
True where this call created the row, false where an unexpired test end user already held the label and was returned unchanged. Type: boolean |
| / |
On a removal: the identifiers of the test end users removed, each with its identities, sessions, held codes, and live tickets; empty where none was found. Type: array |
| / |
Type: string |
| / |
Type: string |
Complete payload contract #
{
"request": {
"type": "object",
"required": [
"application"
],
"properties": {
"application": {
"type": "string",
"description": "The application id, from `list_applications`; one of your account's own."
},
"environment": {
"type": "string",
"pattern": "^(development|production)$",
"description": "Required by both acts, and refused `invalid_request` without it: the environment whose realm you address."
},
"labels": {
"type": "array",
"minItems": 1,
"maxItems": 20,
"items": {
"type": "string",
"pattern": "^[a-z][a-z0-9-]{2,39}$"
},
"description": "Required to create: each the local part of a test end user's address at the fixture domain `synthetic.turnzero.ai`; one whose address another end user holds is refused 409 `not_test_end_user`."
},
"end_users": {
"type": "array",
"minItems": 1,
"maxItems": 20,
"items": {
"type": "string"
},
"description": "To delete: the test end users' ids, one of `end_users` and `all` required and never both; an id that is not a test end user of the realm refuses the whole request 409 `not_test_end_user`, and nothing is removed."
},
"all": {
"const": true,
"description": "To delete every test end user of the realm; one of `end_users` and `all` is required, and never both."
},
"remove": {
"type": "boolean",
"description": "`true` removes test end users at once, naming `end_users` or `all`."
}
},
"additionalProperties": false,
"x-retired": {
"expires_in_days": "Each test end user lasts 48 hours from its creation, one fixed lifetime: call again without expires_in_days.",
"act": "Leave act out: pass labels to add, or remove: true with end_users or all."
}
},
"response": {
"type": "object",
"required": [
"contract_version",
"realm",
"application"
],
"properties": {
"contract_version": {
"const": 1
},
"realm": {
"type": "string",
"description": "The realm identifier: the application id for production, `<id>:development` for development."
},
"application": {
"type": "string"
},
"environment": {
"type": "string",
"pattern": "^(development|production)$",
"description": "The environment whose realm the call addressed."
},
"test_signin_page": {
"type": "string",
"description": "On a creation: The realm's test sign-in page, `/__account/signin/test` on the environment's hostname, which offers the emailed-code form to a test end user on every admitting realm with a non-empty route set."
},
"test_end_users": {
"type": "array",
"minItems": 1,
"maxItems": 20,
"description": "On a creation: one entry per label, in the request's order.",
"items": {
"type": "object",
"required": [
"id",
"label",
"email",
"expires_at",
"created"
],
"properties": {
"id": {
"type": "string",
"description": "The test end user's opaque identifier, the one `list_end_users` returns."
},
"label": {
"type": "string"
},
"email": {
"type": "string",
"description": "`<label>@synthetic.turnzero.ai`, the verified address the user signs in with."
},
"expires_at": {
"type": "string",
"description": "The instant from which the platform's expiry pass removes the user, within ten minutes."
},
"created": {
"type": "boolean",
"description": "True where this call created the row, false where an unexpired test end user already held the label and was returned unchanged."
}
},
"additionalProperties": false
}
},
"removed": {
"type": "array",
"items": {
"type": "string"
},
"description": "On a removal: the identifiers of the test end users removed, each with its identities, sessions, held codes, and live tickets; empty where none was found."
},
"detail": {
"type": "string"
}
},
"additionalProperties": false
}
}
Shared contracts #
- Refusals: every refusal, by surface, with its cause and its remedy
- schemas/wire_error.schema.json
- schemas/wire_errors.json
- schemas/action_payloads.json (includes shared shapes)
- management_api_contract.md