Workspaces
Domains
client.domains manages the domains a workspace classifies its files against. See Domains for the concept, and the API reference for every field.
- A domain is a two-level taxonomy: a list of classes, each a
groupand asubgroupwith a description written for the classifier. - Whose it is: Nace provides some (
owner: "platform"), and your account can author its own (owner: "tenant"). - Cost: managing domains costs nothing and works at any balance.
A domain version is a draft or published:
| State | What you can do |
|---|---|
| Draft | Edit it in place, as often as you like, then publish it once. Publishing is one-way. |
| Published | Give it to a new workspace. It never changes again: duplicate it and edit the copy. |
Nace's own domains never change either: copy them the same way. A workspace is pinned to the version it was made with, so editing a copy never reaches it.
Every method that works on one domain takes its domainId first; one you can't see rejects with NotFoundError, code domain_not_found.
-
A taxonomy is a list of classes,
{ classes: [...], allow_other: true }. A document that fits no class is labelled as such, not forced into one. Each class has:groupandsubgroup: lowercase letters, digits and single underscores, up to 64 characters each.description: what the classifier reads.aliases(optional): earlier names.
If a class doesn't follow these rules, the whole
createorupdateis refused with422 invalid_request, and nothing is saved. -
A write returns its validation:
create,update,publishandduplicatereturn aDomainWrite, with the saveddomainand avalidationof what is wrong with the taxonomy so far. A draft that follows the rules can still be onepublishrefuses, withdomain_validation_failed: one with no classes, or with a class in the reserved groupother. -
Errors: a published domain passed to
updateorpublishrejects withConflictError(domain_not_editable), and a platform one withPermissionDeniedError. A taxonomy that fails validation onpublishrejects withUnprocessableEntityError(domain_validation_failed), with the rules to fix indetail. Alimitoutside 1 to 200, or adomainIdthat is empty or holds/,?or#, throws aNaceErrorbefore any request. -
No automatic retries on creates:
create,publishandduplicatearen't idempotent, since a retry after the first call landed answers409or makes a second copy. They aren't retried unless you passretryinoptions.list,iter,getandupdateare retried.
List domains
client.domains.list(params?, options?) returns APIPromise<DomainPage>, one page of the domains your account sees, the platform's and its own. params is a DomainListParams.
| Parameter | Type | Required | Description |
|---|---|---|---|
owner | "platform" | "tenant" | No | Only the platform's domains, or only your account's. |
status | "draft" | "published" | No | Only drafts, or only published versions. Only a published one can create a workspace. |
slug | string | No | Only the versions of this slug. |
limit | number | No | 1 to 200. Default: 50. |
cursor | string | null | No | The previous page's next_cursor. Keep going until it's null. |
const page = await client.domains.list({ owner: "platform", status: "published" });
for (const domain of page.items) {
console.log(domain.slug, domain.version, domain.class_count);
}Iterate over domains
client.domains.iter(params?, options?) returns AsyncGenerator<DomainSummary>, following every page, 200 a page.
| Parameter | Type | Required | Description |
|---|---|---|---|
owner | "platform" | "tenant" | No | Only the platform's domains, or only your account's. |
status | "draft" | "published" | No | Only drafts, or only published versions. |
slug | string | No | Only the versions of this slug. |
for await (const domain of client.domains.iter({ owner: "tenant" })) {
console.log(domain.domain_id, domain.slug, domain.status);
}Create a domain
client.domains.create(params, options?) returns APIPromise<DomainWrite>: a draft owned by your account. params is a CreateDomainParams.
| Parameter | Type | Required | Description |
|---|---|---|---|
slug | string | Yes | Lowercase letters, digits and single underscores, up to 64. It can't change later. A slug in use throws ConflictError. |
display_name | string | Yes | 1 to 200 characters. |
taxonomy | Record<string, unknown> | No | The classes, as described above. Default: empty. |
const draft = await client.domains.create({ slug: "leases", display_name: "Leases" });
console.log(draft.domain.domain_id, draft.validation.valid);Read a domain
client.domains.get(domainId, options?) returns APIPromise<Domain>: one domain version with its taxonomy.
| Parameter | Type | Required | Description |
|---|---|---|---|
domainId | string | Yes | The domain version. |
const domain = await client.domains.get(domainId);
console.log(domain.taxonomy, domain.published_at);Update a draft
client.domains.update(domainId, params, options?) returns APIPromise<DomainWrite>, as saved. params is an UpdateDomainParams; a field you leave out stays as it is.
| Parameter | Type | Required | Description |
|---|---|---|---|
domainId | string | Yes | The draft. |
params.display_name | string | No | The new name, 1 to 200 characters. |
params.taxonomy | Record<string, unknown> | No | Replaces the whole taxonomy. |
await client.domains.update(draft.domain.domain_id, {
taxonomy: {
classes: [
{ group: "leases", subgroup: "amendments", description: "Amendments to a signed lease.", aliases: [] },
],
},
});Publish a domain
client.domains.publish(domainId, options?) returns APIPromise<DomainWrite>: the draft, frozen, so workspaces can use it by its slug. It is one-way.
| Parameter | Type | Required | Description |
|---|---|---|---|
domainId | string | Yes | The draft. |
const published = await client.domains.publish(draft.domain.domain_id);
console.log(published.domain.selectable, published.validation.valid);Duplicate a domain
client.domains.duplicate(domainId, options?) returns APIPromise<DomainWrite>: a draft copy of any domain you see, the platform's included, under a new slug. Workspaces pinned to the original never see the copy.
| Parameter | Type | Required | Description |
|---|---|---|---|
domainId | string | Yes | The domain to copy. |
const copy = await client.domains.duplicate(published.domain.domain_id);
console.log(copy.domain.slug, copy.domain.status); // a draft under a new slugCreate a workspace against a domain
Pass the published domain's slug as domain_slug. See Create a workspace.
const workspace = await client.workspaces.create({ name: "fy25-leases", domain_slug: "leases" });
console.log(workspace.domain_slug, workspace.domain_id);