Reorder a location service or set its display names
The same write the console's location services page makes. A partial write: a member absent from the body is left alone, and at least one of position and names must be present. position moves the service to that place in the location's list; a value outside the list — below 1 or above its size — moves it to the nearest end, and the other services are renumbered contiguously. names is keyed by language code, matched exactly (upper case, as names is read): a string sets that language's display name for this location, and null, an empty string or a blank string clears it. A language names leaves out keeps its override. A name is at most 80 characters after trimming. A key that is not in the location's language list is refused not_writable, a key for a language deactivated in the workspace language catalogue inactive, and a longer name too_long; those names refusals of one body are reported together. A refusal of the body's shape — an unknown member, an invalid_format value, neither position nor names present — is reported first and alone. A refused body changes nothing — the order included. The service's code never changes: a body carrying a code member is refused. The answer is the updated entry.
Behavior and permissions
Requires a credential whose reach includes the location. Both a tenant administrator's and a location manager's credential reach this operation; a location outside the credential's reach is the 404, never a 403. A service the location does not offer, one of another tenant, or a segment that is not an identifier is 404 service_not_found.
Authorization · Example request · Parameters · Request body · Responses
PATCH/api/integration/v1/locations/{locationId}/services/{serviceId}
Authorization
- apiKeyAuth — apiKey sent in the Authorization header
Use Authorization: Api-Key <secret>. Get a credential and check the scopes and issuer authority required for this operation.
Example request
Set QMS_BASE_URL to your workspace URL and QMS_API_KEY to your secret. Replace example identifiers with your own.
curl --request PATCH "$QMS_BASE_URL/api/integration/v1/locations/22222222-2222-4222-8222-222222222222/services/33333333-3333-4333-8333-333333333333" \
--header "Authorization: Api-Key $QMS_API_KEY" \
--header "Content-Type: application/json" \
--data '{
"position": 1,
"names": {
"LT": "Kasa",
"EN": null
}
}'Parameters
| Name | In | Required | Schema |
|---|---|---|---|
locationId | path | yes | {"type":"string"} |
serviceId | path | yes | {"type":"string"} |
locationId: The location's opaque identifier.
serviceId: The catalogue service's opaque identifier.
Request body
{
"position": 1,
"names": {
"LT": "Kasa",
"EN": null
}
}Request schema
At least one member must be present.
position · integer · optional
The place to move the service to. A value below 1 moves it to the first place and a value above the list's size to the last.
names · object · optional
The display names to set, keyed by language code exactly as `names` is read. A string sets the name, and `null`, an empty or a blank string clears it; a language left out keeps its override. A name is at most 80 characters after trimming.
Raw JSON Schema
application/json
{
"type": "object",
"description": "At least one member must be present.",
"properties": {
"position": {
"type": "integer",
"description": "The place to move the service to. A value below 1 moves it to the first place and a value above the list's size to the last.",
"example": 1
},
"names": {
"type": "object",
"description": "The display names to set, keyed by language code exactly as `names` is read. A string sets the name, and `null`, an empty or a blank string clears it; a language left out keeps its override. A name is at most 80 characters after trimming.",
"additionalProperties": {
"type": [
"string",
"null"
],
"maxLength": 80
},
"example": {
"LT": "Kasa",
"EN": null
}
}
},
"minProperties": 1,
"additionalProperties": false
}Responses
200 — The updated entry.
{
"id": "33333333-3333-4333-8333-333333333333",
"code": "P663",
"catalogueName": "Cash services",
"position": 1,
"names": {
"LT": "Kasa",
"EN": null
}
}200 response schema
One service of a location's list.
id · string · required
The catalogue service's opaque identifier.
code · string · required
The catalogue service's code, which never changes.
catalogueName · string · required
The service's tenant-wide name in the catalogue.
position · integer · required
The service's place in the location's list.
names · object · required
The location's display name for the service, keyed by language code: one member per language in the location's language list, the override or `null` where the location has none. A name is at most 80 characters after trimming.
Raw JSON Schema
application/json
{
"type": "object",
"description": "One service of a location's list.",
"properties": {
"id": {
"type": "string",
"description": "The catalogue service's opaque identifier.",
"example": "33333333-3333-4333-8333-333333333333"
},
"code": {
"type": "string",
"description": "The catalogue service's code, which never changes.",
"example": "P663"
},
"catalogueName": {
"type": "string",
"description": "The service's tenant-wide name in the catalogue.",
"example": "Cash services"
},
"position": {
"type": "integer",
"minimum": 1,
"description": "The service's place in the location's list.",
"example": 1
},
"names": {
"type": "object",
"description": "The location's display name for the service, keyed by language code: one member per language in the location's language list, the override or `null` where the location has none. A name is at most 80 characters after trimming.",
"additionalProperties": {
"type": [
"string",
"null"
],
"maxLength": 80
},
"example": {
"LT": "Kasa",
"EN": null
}
}
},
"required": [
"id",
"code",
"catalogueName",
"position",
"names"
],
"additionalProperties": false
}400 — The location service edit was refused before anything was written, the order included. Two codes share this status: `validation_failed` when a member the body sent is not acceptable — one `errors` entry per offending field, every `names.<code>` refusal of the body together; a refusal of the body's shape is reported first and alone — and `service_code_immutable` when the body carries a `code` member at all. Branch on `code`.
{
"type": "urn:qms:problem:validation_failed",
"title": "Validation Failed",
"status": 400,
"code": "validation_failed",
"detail": "The request body failed field validation.",
"errors": [
{
"field": "names.PL",
"code": "not_writable"
}
]
}{
"type": "urn:qms:problem:service_code_immutable",
"title": "Service Code Immutable",
"status": 400,
"code": "service_code_immutable",
"detail": "The service code cannot be changed after creation."
}400 response schema
An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.
type · string · required
A URN identifying the problem kind, one per `code`.
title · string · required
A fixed English summary of the problem kind.
status · integer · required
The HTTP status code, repeated in the body.
code · string · required
The published slug this surface's error vocabulary uses.
detail · string · required
An English explanation of this occurrence.
errors · array · optional
One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.
Show nested fields
One offending field of a 400 field-validation refusal.
field · string · required
The member as THIS document spells it, which is not always what the same field is called inside the system.
code · string · required
The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`. Three of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.
blockers · array · optional
One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.
Show nested fields
One non-zero blocking category of a 409 refusal, and how many things it counted.
kind · string · required
What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.
Allowed values: "LOCATION", "TICKET", "APPOINTMENT", "TEMPLATE", "OPERATOR"
count · integer · required
How many of them there are. Always greater than zero.
checkCode · string · optional
The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.
planLimit · object · optional
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
Show nested fields
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
currentPlan · object · required
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
activeLocations · integer · required
The number of ACTIVE locations the tenant holds.
nextPlan · object · optional
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
enterpriseOffer · object · optional
The published Enterprise offer, named when no active plan covers the tenant's active location count.
Show nested fields
The published Enterprise offer, named when no active plan covers the tenant's active location count.
minLocations · integer · required
The smallest number of locations the offer covers.
fromMonthlyPriceCents · integer · int64 · required
The monthly price from which the offer starts, in euro cents.
extraLocationPriceCents · integer · int64 · required
The monthly price of each location beyond `minLocations`, in euro cents.
contactEmail · string · optional
The address to write to about a larger plan or an individual contract.
Raw JSON Schema
application/problem+json
{
"type": "object",
"description": "An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.",
"properties": {
"type": {
"type": "string",
"description": "A URN identifying the problem kind, one per `code`.",
"example": "urn:qms:problem:location_not_found"
},
"title": {
"type": "string",
"description": "A fixed English summary of the problem kind.",
"example": "Location Not Found"
},
"status": {
"type": "integer",
"description": "The HTTP status code, repeated in the body.",
"example": 404
},
"code": {
"type": "string",
"description": "The published slug this surface's error vocabulary uses.",
"example": "location_not_found"
},
"detail": {
"type": "string",
"description": "An English explanation of this occurrence.",
"example": "No location was found for this identifier."
},
"errors": {
"type": "array",
"description": "One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.",
"items": {
"type": "object",
"description": "One offending field of a 400 field-validation refusal.",
"properties": {
"field": {
"type": "string",
"description": "The member as THIS document spells it, which is not always what the same field is called inside the system.",
"example": "defaultLocale"
},
"code": {
"type": "string",
"description": "The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`.\n\nThree of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.",
"example": "invalid_locale"
}
},
"required": [
"field",
"code"
]
}
},
"blockers": {
"type": "array",
"description": "One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.",
"items": {
"type": "object",
"description": "One non-zero blocking category of a 409 refusal, and how many things it counted.",
"properties": {
"kind": {
"type": "string",
"description": "What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.",
"enum": [
"LOCATION",
"TICKET",
"APPOINTMENT",
"TEMPLATE",
"OPERATOR"
],
"example": "TICKET"
},
"count": {
"type": "integer",
"description": "How many of them there are. Always greater than zero.",
"example": 3
}
},
"required": [
"kind",
"count"
]
}
},
"checkCode": {
"type": "string",
"description": "The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.",
"example": "unreachable"
},
"planLimit": {
"type": "object",
"description": "What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.",
"properties": {
"currentPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"activeLocations": {
"type": "integer",
"description": "The number of ACTIVE locations the tenant holds.",
"example": 3
},
"nextPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"enterpriseOffer": {
"type": "object",
"description": "The published Enterprise offer, named when no active plan covers the tenant's active location count.",
"properties": {
"minLocations": {
"type": "integer",
"description": "The smallest number of locations the offer covers.",
"example": 8
},
"fromMonthlyPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price from which the offer starts, in euro cents.",
"example": 27900
},
"extraLocationPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price of each location beyond `minLocations`, in euro cents.",
"example": 2900
}
},
"required": [
"minLocations",
"fromMonthlyPriceCents",
"extraLocationPriceCents"
]
},
"contactEmail": {
"type": "string",
"description": "The address to write to about a larger plan or an individual contract.",
"example": "sales@example.com"
}
},
"required": [
"currentPlan",
"activeLocations"
]
}
},
"required": [
"type",
"title",
"status",
"code",
"detail"
],
"additionalProperties": false
}401 — No valid API credential was presented. Every refusal cause — absent, malformed, unknown, expired, revoked, or belonging to another tenant — answers with this one document, and no `WWW-Authenticate` header is returned.
{
"type": "urn:qms:problem:unauthenticated",
"title": "Unauthenticated",
"status": 401,
"code": "unauthenticated",
"detail": "The request presented no valid API credential."
}401 response schema
An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.
type · string · required
A URN identifying the problem kind, one per `code`.
title · string · required
A fixed English summary of the problem kind.
status · integer · required
The HTTP status code, repeated in the body.
code · string · required
The published slug this surface's error vocabulary uses.
detail · string · required
An English explanation of this occurrence.
errors · array · optional
One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.
Show nested fields
One offending field of a 400 field-validation refusal.
field · string · required
The member as THIS document spells it, which is not always what the same field is called inside the system.
code · string · required
The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`. Three of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.
blockers · array · optional
One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.
Show nested fields
One non-zero blocking category of a 409 refusal, and how many things it counted.
kind · string · required
What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.
Allowed values: "LOCATION", "TICKET", "APPOINTMENT", "TEMPLATE", "OPERATOR"
count · integer · required
How many of them there are. Always greater than zero.
checkCode · string · optional
The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.
planLimit · object · optional
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
Show nested fields
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
currentPlan · object · required
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
activeLocations · integer · required
The number of ACTIVE locations the tenant holds.
nextPlan · object · optional
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
enterpriseOffer · object · optional
The published Enterprise offer, named when no active plan covers the tenant's active location count.
Show nested fields
The published Enterprise offer, named when no active plan covers the tenant's active location count.
minLocations · integer · required
The smallest number of locations the offer covers.
fromMonthlyPriceCents · integer · int64 · required
The monthly price from which the offer starts, in euro cents.
extraLocationPriceCents · integer · int64 · required
The monthly price of each location beyond `minLocations`, in euro cents.
contactEmail · string · optional
The address to write to about a larger plan or an individual contract.
Raw JSON Schema
application/problem+json
{
"type": "object",
"description": "An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.",
"properties": {
"type": {
"type": "string",
"description": "A URN identifying the problem kind, one per `code`.",
"example": "urn:qms:problem:location_not_found"
},
"title": {
"type": "string",
"description": "A fixed English summary of the problem kind.",
"example": "Location Not Found"
},
"status": {
"type": "integer",
"description": "The HTTP status code, repeated in the body.",
"example": 404
},
"code": {
"type": "string",
"description": "The published slug this surface's error vocabulary uses.",
"example": "location_not_found"
},
"detail": {
"type": "string",
"description": "An English explanation of this occurrence.",
"example": "No location was found for this identifier."
},
"errors": {
"type": "array",
"description": "One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.",
"items": {
"type": "object",
"description": "One offending field of a 400 field-validation refusal.",
"properties": {
"field": {
"type": "string",
"description": "The member as THIS document spells it, which is not always what the same field is called inside the system.",
"example": "defaultLocale"
},
"code": {
"type": "string",
"description": "The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`.\n\nThree of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.",
"example": "invalid_locale"
}
},
"required": [
"field",
"code"
]
}
},
"blockers": {
"type": "array",
"description": "One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.",
"items": {
"type": "object",
"description": "One non-zero blocking category of a 409 refusal, and how many things it counted.",
"properties": {
"kind": {
"type": "string",
"description": "What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.",
"enum": [
"LOCATION",
"TICKET",
"APPOINTMENT",
"TEMPLATE",
"OPERATOR"
],
"example": "TICKET"
},
"count": {
"type": "integer",
"description": "How many of them there are. Always greater than zero.",
"example": 3
}
},
"required": [
"kind",
"count"
]
}
},
"checkCode": {
"type": "string",
"description": "The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.",
"example": "unreachable"
},
"planLimit": {
"type": "object",
"description": "What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.",
"properties": {
"currentPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"activeLocations": {
"type": "integer",
"description": "The number of ACTIVE locations the tenant holds.",
"example": 3
},
"nextPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"enterpriseOffer": {
"type": "object",
"description": "The published Enterprise offer, named when no active plan covers the tenant's active location count.",
"properties": {
"minLocations": {
"type": "integer",
"description": "The smallest number of locations the offer covers.",
"example": 8
},
"fromMonthlyPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price from which the offer starts, in euro cents.",
"example": 27900
},
"extraLocationPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price of each location beyond `minLocations`, in euro cents.",
"example": 2900
}
},
"required": [
"minLocations",
"fromMonthlyPriceCents",
"extraLocationPriceCents"
]
},
"contactEmail": {
"type": "string",
"description": "The address to write to about a larger plan or an individual contract.",
"example": "sales@example.com"
}
},
"required": [
"currentPlan",
"activeLocations"
]
}
},
"required": [
"type",
"title",
"status",
"code",
"detail"
],
"additionalProperties": false
}403 — The authenticated credential does not carry a scope that admits this operation. The scope check runs before every other admission check, so this refusal displaces `insufficient_authority` on an operation that requires both.
{
"type": "urn:qms:problem:insufficient_scope",
"title": "Insufficient Scope",
"status": 403,
"code": "insufficient_scope",
"detail": "The API credential does not reach this operation."
}403 response schema
An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.
type · string · required
A URN identifying the problem kind, one per `code`.
title · string · required
A fixed English summary of the problem kind.
status · integer · required
The HTTP status code, repeated in the body.
code · string · required
The published slug this surface's error vocabulary uses.
detail · string · required
An English explanation of this occurrence.
errors · array · optional
One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.
Show nested fields
One offending field of a 400 field-validation refusal.
field · string · required
The member as THIS document spells it, which is not always what the same field is called inside the system.
code · string · required
The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`. Three of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.
blockers · array · optional
One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.
Show nested fields
One non-zero blocking category of a 409 refusal, and how many things it counted.
kind · string · required
What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.
Allowed values: "LOCATION", "TICKET", "APPOINTMENT", "TEMPLATE", "OPERATOR"
count · integer · required
How many of them there are. Always greater than zero.
checkCode · string · optional
The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.
planLimit · object · optional
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
Show nested fields
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
currentPlan · object · required
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
activeLocations · integer · required
The number of ACTIVE locations the tenant holds.
nextPlan · object · optional
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
enterpriseOffer · object · optional
The published Enterprise offer, named when no active plan covers the tenant's active location count.
Show nested fields
The published Enterprise offer, named when no active plan covers the tenant's active location count.
minLocations · integer · required
The smallest number of locations the offer covers.
fromMonthlyPriceCents · integer · int64 · required
The monthly price from which the offer starts, in euro cents.
extraLocationPriceCents · integer · int64 · required
The monthly price of each location beyond `minLocations`, in euro cents.
contactEmail · string · optional
The address to write to about a larger plan or an individual contract.
Raw JSON Schema
application/problem+json
{
"type": "object",
"description": "An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.",
"properties": {
"type": {
"type": "string",
"description": "A URN identifying the problem kind, one per `code`.",
"example": "urn:qms:problem:location_not_found"
},
"title": {
"type": "string",
"description": "A fixed English summary of the problem kind.",
"example": "Location Not Found"
},
"status": {
"type": "integer",
"description": "The HTTP status code, repeated in the body.",
"example": 404
},
"code": {
"type": "string",
"description": "The published slug this surface's error vocabulary uses.",
"example": "location_not_found"
},
"detail": {
"type": "string",
"description": "An English explanation of this occurrence.",
"example": "No location was found for this identifier."
},
"errors": {
"type": "array",
"description": "One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.",
"items": {
"type": "object",
"description": "One offending field of a 400 field-validation refusal.",
"properties": {
"field": {
"type": "string",
"description": "The member as THIS document spells it, which is not always what the same field is called inside the system.",
"example": "defaultLocale"
},
"code": {
"type": "string",
"description": "The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`.\n\nThree of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.",
"example": "invalid_locale"
}
},
"required": [
"field",
"code"
]
}
},
"blockers": {
"type": "array",
"description": "One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.",
"items": {
"type": "object",
"description": "One non-zero blocking category of a 409 refusal, and how many things it counted.",
"properties": {
"kind": {
"type": "string",
"description": "What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.",
"enum": [
"LOCATION",
"TICKET",
"APPOINTMENT",
"TEMPLATE",
"OPERATOR"
],
"example": "TICKET"
},
"count": {
"type": "integer",
"description": "How many of them there are. Always greater than zero.",
"example": 3
}
},
"required": [
"kind",
"count"
]
}
},
"checkCode": {
"type": "string",
"description": "The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.",
"example": "unreachable"
},
"planLimit": {
"type": "object",
"description": "What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.",
"properties": {
"currentPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"activeLocations": {
"type": "integer",
"description": "The number of ACTIVE locations the tenant holds.",
"example": 3
},
"nextPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"enterpriseOffer": {
"type": "object",
"description": "The published Enterprise offer, named when no active plan covers the tenant's active location count.",
"properties": {
"minLocations": {
"type": "integer",
"description": "The smallest number of locations the offer covers.",
"example": 8
},
"fromMonthlyPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price from which the offer starts, in euro cents.",
"example": 27900
},
"extraLocationPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price of each location beyond `minLocations`, in euro cents.",
"example": 2900
}
},
"required": [
"minLocations",
"fromMonthlyPriceCents",
"extraLocationPriceCents"
]
},
"contactEmail": {
"type": "string",
"description": "The address to write to about a larger plan or an individual contract.",
"example": "sales@example.com"
}
},
"required": [
"currentPlan",
"activeLocations"
]
}
},
"required": [
"type",
"title",
"status",
"code",
"detail"
],
"additionalProperties": false
}404 — Nothing was found to act on. Two codes share this status: `location_not_found` when the location is outside the credential's reach, belongs to another tenant, was permanently deleted or was named by a segment that is not an identifier; and `service_not_found` when the location is reachable but does not offer the service, the service belongs to another tenant, or the segment is not an identifier. Branch on `code`.
{
"type": "urn:qms:problem:location_not_found",
"title": "Location Not Found",
"status": 404,
"code": "location_not_found",
"detail": "No location was found for this identifier."
}{
"type": "urn:qms:problem:service_not_found",
"title": "Service Not Found",
"status": 404,
"code": "service_not_found",
"detail": "No service was found for this identifier."
}404 response schema
An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.
type · string · required
A URN identifying the problem kind, one per `code`.
title · string · required
A fixed English summary of the problem kind.
status · integer · required
The HTTP status code, repeated in the body.
code · string · required
The published slug this surface's error vocabulary uses.
detail · string · required
An English explanation of this occurrence.
errors · array · optional
One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.
Show nested fields
One offending field of a 400 field-validation refusal.
field · string · required
The member as THIS document spells it, which is not always what the same field is called inside the system.
code · string · required
The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`. Three of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.
blockers · array · optional
One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.
Show nested fields
One non-zero blocking category of a 409 refusal, and how many things it counted.
kind · string · required
What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.
Allowed values: "LOCATION", "TICKET", "APPOINTMENT", "TEMPLATE", "OPERATOR"
count · integer · required
How many of them there are. Always greater than zero.
checkCode · string · optional
The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.
planLimit · object · optional
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
Show nested fields
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
currentPlan · object · required
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
activeLocations · integer · required
The number of ACTIVE locations the tenant holds.
nextPlan · object · optional
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
enterpriseOffer · object · optional
The published Enterprise offer, named when no active plan covers the tenant's active location count.
Show nested fields
The published Enterprise offer, named when no active plan covers the tenant's active location count.
minLocations · integer · required
The smallest number of locations the offer covers.
fromMonthlyPriceCents · integer · int64 · required
The monthly price from which the offer starts, in euro cents.
extraLocationPriceCents · integer · int64 · required
The monthly price of each location beyond `minLocations`, in euro cents.
contactEmail · string · optional
The address to write to about a larger plan or an individual contract.
Raw JSON Schema
application/problem+json
{
"type": "object",
"description": "An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.",
"properties": {
"type": {
"type": "string",
"description": "A URN identifying the problem kind, one per `code`.",
"example": "urn:qms:problem:location_not_found"
},
"title": {
"type": "string",
"description": "A fixed English summary of the problem kind.",
"example": "Location Not Found"
},
"status": {
"type": "integer",
"description": "The HTTP status code, repeated in the body.",
"example": 404
},
"code": {
"type": "string",
"description": "The published slug this surface's error vocabulary uses.",
"example": "location_not_found"
},
"detail": {
"type": "string",
"description": "An English explanation of this occurrence.",
"example": "No location was found for this identifier."
},
"errors": {
"type": "array",
"description": "One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.",
"items": {
"type": "object",
"description": "One offending field of a 400 field-validation refusal.",
"properties": {
"field": {
"type": "string",
"description": "The member as THIS document spells it, which is not always what the same field is called inside the system.",
"example": "defaultLocale"
},
"code": {
"type": "string",
"description": "The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`.\n\nThree of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.",
"example": "invalid_locale"
}
},
"required": [
"field",
"code"
]
}
},
"blockers": {
"type": "array",
"description": "One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.",
"items": {
"type": "object",
"description": "One non-zero blocking category of a 409 refusal, and how many things it counted.",
"properties": {
"kind": {
"type": "string",
"description": "What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.",
"enum": [
"LOCATION",
"TICKET",
"APPOINTMENT",
"TEMPLATE",
"OPERATOR"
],
"example": "TICKET"
},
"count": {
"type": "integer",
"description": "How many of them there are. Always greater than zero.",
"example": 3
}
},
"required": [
"kind",
"count"
]
}
},
"checkCode": {
"type": "string",
"description": "The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.",
"example": "unreachable"
},
"planLimit": {
"type": "object",
"description": "What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.",
"properties": {
"currentPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"activeLocations": {
"type": "integer",
"description": "The number of ACTIVE locations the tenant holds.",
"example": 3
},
"nextPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"enterpriseOffer": {
"type": "object",
"description": "The published Enterprise offer, named when no active plan covers the tenant's active location count.",
"properties": {
"minLocations": {
"type": "integer",
"description": "The smallest number of locations the offer covers.",
"example": 8
},
"fromMonthlyPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price from which the offer starts, in euro cents.",
"example": 27900
},
"extraLocationPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price of each location beyond `minLocations`, in euro cents.",
"example": 2900
}
},
"required": [
"minLocations",
"fromMonthlyPriceCents",
"extraLocationPriceCents"
]
},
"contactEmail": {
"type": "string",
"description": "The address to write to about a larger plan or an individual contract.",
"example": "sales@example.com"
}
},
"required": [
"currentPlan",
"activeLocations"
]
}
},
"required": [
"type",
"title",
"status",
"code",
"detail"
],
"additionalProperties": false
}500 — The request could not be processed. The body names no internal detail. A retry is safe on every read described here; on a create, an edit or a lifecycle transition a retry may or may not repeat a change that already committed, so read the resource back before retrying one of those.
{
"type": "urn:qms:problem:internal_error",
"title": "Internal Server Error",
"status": 500,
"code": "internal_error",
"detail": "The request could not be processed."
}500 response schema
An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.
type · string · required
A URN identifying the problem kind, one per `code`.
title · string · required
A fixed English summary of the problem kind.
status · integer · required
The HTTP status code, repeated in the body.
code · string · required
The published slug this surface's error vocabulary uses.
detail · string · required
An English explanation of this occurrence.
errors · array · optional
One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.
Show nested fields
One offending field of a 400 field-validation refusal.
field · string · required
The member as THIS document spells it, which is not always what the same field is called inside the system.
code · string · required
The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`. Three of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.
blockers · array · optional
One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.
Show nested fields
One non-zero blocking category of a 409 refusal, and how many things it counted.
kind · string · required
What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.
Allowed values: "LOCATION", "TICKET", "APPOINTMENT", "TEMPLATE", "OPERATOR"
count · integer · required
How many of them there are. Always greater than zero.
checkCode · string · optional
The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.
planLimit · object · optional
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
Show nested fields
What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.
currentPlan · object · required
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
activeLocations · integer · required
The number of ACTIVE locations the tenant holds.
nextPlan · object · optional
A plan named by a `plan_location_limit_reached` refusal.
Show nested fields
A plan named by a `plan_location_limit_reached` refusal.
planId · string · required
The plan's stable identifier.
displayName · string · required
The plan's name, not translated.
maxLocations · integer · required
The most ACTIVE locations the plan covers.
enterpriseOffer · object · optional
The published Enterprise offer, named when no active plan covers the tenant's active location count.
Show nested fields
The published Enterprise offer, named when no active plan covers the tenant's active location count.
minLocations · integer · required
The smallest number of locations the offer covers.
fromMonthlyPriceCents · integer · int64 · required
The monthly price from which the offer starts, in euro cents.
extraLocationPriceCents · integer · int64 · required
The monthly price of each location beyond `minLocations`, in euro cents.
contactEmail · string · optional
The address to write to about a larger plan or an individual contract.
Raw JSON Schema
application/problem+json
{
"type": "object",
"description": "An RFC 9457 problem document: `type`, `title`, `status`, `code` and `detail`, every one of those five always present. `errors`, `blockers`, `checkCode` and `planLimit` are the exceptions — each is scoped to one family of refusal and is ABSENT on every other document, which is why none is required below. `code` is the stable, machine-readable member; branch on it rather than on `title` or `detail`, which are English prose meant for a developer reading a log.",
"properties": {
"type": {
"type": "string",
"description": "A URN identifying the problem kind, one per `code`.",
"example": "urn:qms:problem:location_not_found"
},
"title": {
"type": "string",
"description": "A fixed English summary of the problem kind.",
"example": "Location Not Found"
},
"status": {
"type": "integer",
"description": "The HTTP status code, repeated in the body.",
"example": 404
},
"code": {
"type": "string",
"description": "The published slug this surface's error vocabulary uses.",
"example": "location_not_found"
},
"detail": {
"type": "string",
"description": "An English explanation of this occurrence.",
"example": "No location was found for this identifier."
},
"errors": {
"type": "array",
"description": "One entry per offending field of a 400 field-validation refusal. Present on those alone, and ABSENT — not null, not an empty array — on every other problem document, including a field-validation refusal that can name no single field. Sorted by `field`, so two refusals over the same body produce the same document.",
"items": {
"type": "object",
"description": "One offending field of a 400 field-validation refusal.",
"properties": {
"field": {
"type": "string",
"description": "The member as THIS document spells it, which is not always what the same field is called inside the system.",
"example": "defaultLocale"
},
"code": {
"type": "string",
"description": "The published reason slug. Typed as a plain string rather than an enumeration, because the set is not closed — an integrity backstop can report a slug outside the published list. The values in use today are `required`, `too_long`, `invalid_format`, `invalid_timezone`, `invalid_locale`, `invalid_country`, `name_taken`, `code_taken`, `display_prefix_taken`, `out_of_range`, `not_in_catalogue`, `archived`, `duplicate`, `not_found`, `not_linked_to_location`, `inactive`, `language_not_in_catalogue`, `not_writable`, `password_too_short` and `password_breached`.\n\nThree of them are worth a sentence. `invalid_format` covers a value whose SHAPE is wrong — a window code that is not alphanumeric, a time that is not `HH:MM` — and, on the operating hours, the one fault that is a relation rather than a shape: a `closesAt` that is not after its `opensAt`, where both values are well formed and it is their ORDER that is refused. It also covers a member whose JSON type cannot be read — a string where a boolean belongs — reported under its path, e.g. `operatingHours[0].closed`. `not_found` means the member names something this tenant does not hold; it is the same word as the document-level `code` that answers an unserved path, at a different level and never with that status. `not_writable` is the operator invite, the operator profile edit and the visit-reason replace's own: a body member the request type declares no slot for, refused by NAME whether or not its value would have changed anything. `password_too_short` and `password_breached` are the operator create's own, under `initialPassword`.",
"example": "invalid_locale"
}
},
"required": [
"field",
"code"
]
}
},
"blockers": {
"type": "array",
"description": "One entry per non-zero blocking category of a 409 refusal that names what blocks it. Present on those alone, and ABSENT on every other problem document. A category with nothing to report is absent rather than present with a count of 0.",
"items": {
"type": "object",
"description": "One non-zero blocking category of a 409 refusal, and how many things it counted.",
"properties": {
"kind": {
"type": "string",
"description": "What kind of thing still depends on the entry — or, on a configuration refusal, on what the write would take away.",
"enum": [
"LOCATION",
"TICKET",
"APPOINTMENT",
"TEMPLATE",
"OPERATOR"
],
"example": "TICKET"
},
"count": {
"type": "integer",
"description": "How many of them there are. Always greater than zero.",
"example": 3
}
},
"required": [
"kind",
"count"
]
}
},
"checkCode": {
"type": "string",
"description": "The discovery-failure code of a `connection_check_failed` refusal: `unreachable`, `timeout`, `not_https`, `private_address`, `issuer_mismatch`, `missing_endpoint` or `invalid_document`. Present on that refusal alone, and ABSENT on every other problem document.",
"example": "unreachable"
},
"planLimit": {
"type": "object",
"description": "What a `plan_location_limit_reached` refusal reports. Present on that refusal alone, and ABSENT on every other problem document. Exactly one of `nextPlan` and `enterpriseOffer` is present: `nextPlan` when an active plan above the active location count exists, `enterpriseOffer` when none does. `contactEmail` is absent when no contact address is configured.",
"properties": {
"currentPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"activeLocations": {
"type": "integer",
"description": "The number of ACTIVE locations the tenant holds.",
"example": 3
},
"nextPlan": {
"type": "object",
"description": "A plan named by a `plan_location_limit_reached` refusal.",
"properties": {
"planId": {
"type": "string",
"description": "The plan's stable identifier.",
"example": "business"
},
"displayName": {
"type": "string",
"description": "The plan's name, not translated.",
"example": "Business"
},
"maxLocations": {
"type": "integer",
"description": "The most ACTIVE locations the plan covers.",
"example": 5
}
},
"required": [
"planId",
"displayName",
"maxLocations"
]
},
"enterpriseOffer": {
"type": "object",
"description": "The published Enterprise offer, named when no active plan covers the tenant's active location count.",
"properties": {
"minLocations": {
"type": "integer",
"description": "The smallest number of locations the offer covers.",
"example": 8
},
"fromMonthlyPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price from which the offer starts, in euro cents.",
"example": 27900
},
"extraLocationPriceCents": {
"type": "integer",
"format": "int64",
"description": "The monthly price of each location beyond `minLocations`, in euro cents.",
"example": 2900
}
},
"required": [
"minLocations",
"fromMonthlyPriceCents",
"extraLocationPriceCents"
]
},
"contactEmail": {
"type": "string",
"description": "The address to write to about a larger plan or an individual contract.",
"example": "sales@example.com"
}
},
"required": [
"currentPlan",
"activeLocations"
]
}
},
"required": [
"type",
"title",
"status",
"code",
"detail"
],
"additionalProperties": false
}