Taxonomies
9 endpoints, generated from the API's own OpenAPI document. The codes the data routes take: NAICS, SOC, areas, MSAs, ownership, periods. Not metered; cacheable.
GET /v2/taxonomies/naics/levels
The NAICS hierarchy's level names
Credentials: API key or App session. Operation id dataListNaicsLevels.
The names behind level on NAICS items and the naics hierarchy (0 Total, 1 Domain, 2 Super-sector, 3 Sector, 4 to 7 the 3- to 6-digit codes), from the vintage's level lookup. Never paged. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
The levels, in level order.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataLevelItemalways present- Every level, in level order.
data[].levelintegeralways present- The level number used by
levelon taxonomy items andnaics_level/soc_levelon the data routes. (at least 0) data[].namestringalways present- The level's name, e.g.
Sector(NAICS 3),Detailed occupation(SOC 4),County(areas 2). metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other).
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/soc/levels
The SOC hierarchy's level names
Credentials: API key or App session. Operation id dataListSocLevels.
The names behind level on SOC items and the soc hierarchy (0 Total, 1 Major group, 2 Minor group, 3 Broad occupation, 4 Detailed occupation), from the vintage's level lookup. Never paged. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
The levels, in level order.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataLevelItemalways present- Every level, in level order.
data[].levelintegeralways present- The level number used by
levelon taxonomy items andnaics_level/soc_levelon the data routes. (at least 0) data[].namestringalways present- The level's name, e.g.
Sector(NAICS 3),Detailed occupation(SOC 4),County(areas 2). metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other).
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/areas/levels
The area hierarchy's level names
Credentials: API key or App session. Operation id dataListAreaLevels.
The names behind level on area items and the fips hierarchy (0 Nation, 1 State, 2 County), from the vintage's level lookup. Never paged. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
The levels, in level order.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataLevelItemalways present- Every level, in level order.
data[].levelintegeralways present- The level number used by
levelon taxonomy items andnaics_level/soc_levelon the data routes. (at least 0) data[].namestringalways present- The level's name, e.g.
Sector(NAICS 3),Detailed occupation(SOC 4),County(areas 2). metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other).
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/naics
NAICS industry codes
Credentials: API key or App session. Operation id dataListNaics.
The vintage's NAICS platform codes in nested order (a parent before its children), filtered and paged. Filters combine (AND). Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
levelquery · integer- Only codes at this hierarchy level (0 to 7; see
/v2/taxonomies/naics/levels). (0 to 7) parentquery · string- Only the direct children of this NAICS platform code (digits only, e.g.
31). (pattern ^\d+$) qquery · string- Search: codes whose title contains this text (case-insensitive) or whose code starts with it.
leafquery · "true" | "false"true: only codes that are the parent of no code (the lowest set);false: only parents.cursorquery · string- Opaque cursor from
meta.pagination.next_cursorof the previous page. limitquery · integer- Items per page, 1 to 5,000 (default 1,000). (default 1000; 1 to 5000)
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
A page of NAICS codes.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataTaxonomyItemalways present- The codes on this page, in nested order.
data[].codestringalways present- The code to use in requests. NAICS: the platform code (
10is the total, all industries;101/102the domains;1011..1029the super-sectors; then the standard 2- to 6-digit codes, with each range sector stored under its first code,31for 31-33). SOC:11-1011form;00-0000is the total. data[].display_codestring- NAICS only: the code as BLS prints it,
31-33,44-45or48-49for the range sectors, otherwise equal tocode. For display;codestays the identity. data[].titlestring or nullalways present- The code's title in this vintage.
data[].levelintegeralways present- The position in the BLS hierarchy, named by
GET /v2/taxonomies/{naics|soc}/levels(not a digit count). NAICS: 0 Total, 1 Domain, 2 Super-sector, 3 Sector (2-digit), 4 to 7 the 3- to 6-digit codes. SOC: 0 Total, 1 Major group, 2 Minor group, 3 Broad occupation, 4 Detailed occupation. (at least 0) data[].parentstring or nullalways present- The parent code; null at the root (the total).
data[].nested_orderintegeralways present- The code's position in the depth-first order of the hierarchy; series answers sort codes by it.
data[].is_leafbooleanalways present- True when the code is the parent of no code (the lowest set: NAICS 6-digit codes; SOC detailed occupations and the broad occupations with no children).
naics_level=leaf/soc_level=leafon the data routes selects exactly these. metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other), bad_request for a level that is not an integer from 0 to 7, a leaf other than true or false, or a non-numeric parent, bad_request for a bad cursor or a limit outside 1 to 5,000.
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/soc
SOC occupation codes
Credentials: API key or App session. Operation id dataListSoc.
The vintage's SOC codes in nested order, filtered and paged. Filters combine (AND). Items carry no display_code. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
levelquery · integer- Only codes at this hierarchy level (0 to 4; see
/v2/taxonomies/soc/levels). (0 to 4) parentquery · string- Only the direct children of this SOC code (e.g.
11-0000). qquery · string- Search: codes whose title contains this text (case-insensitive) or whose code starts with it.
leafquery · "true" | "false"true: only codes that are the parent of no code (the lowest set);false: only parents.cursorquery · string- Opaque cursor from
meta.pagination.next_cursorof the previous page. limitquery · integer- Items per page, 1 to 5,000 (default 1,000). (default 1000; 1 to 5000)
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
A page of SOC codes.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataTaxonomyItemalways present- The codes on this page, in nested order.
data[].codestringalways present- The code to use in requests. NAICS: the platform code (
10is the total, all industries;101/102the domains;1011..1029the super-sectors; then the standard 2- to 6-digit codes, with each range sector stored under its first code,31for 31-33). SOC:11-1011form;00-0000is the total. data[].display_codestring- NAICS only: the code as BLS prints it,
31-33,44-45or48-49for the range sectors, otherwise equal tocode. For display;codestays the identity. data[].titlestring or nullalways present- The code's title in this vintage.
data[].levelintegeralways present- The position in the BLS hierarchy, named by
GET /v2/taxonomies/{naics|soc}/levels(not a digit count). NAICS: 0 Total, 1 Domain, 2 Super-sector, 3 Sector (2-digit), 4 to 7 the 3- to 6-digit codes. SOC: 0 Total, 1 Major group, 2 Minor group, 3 Broad occupation, 4 Detailed occupation. (at least 0) data[].parentstring or nullalways present- The parent code; null at the root (the total).
data[].nested_orderintegeralways present- The code's position in the depth-first order of the hierarchy; series answers sort codes by it.
data[].is_leafbooleanalways present- True when the code is the parent of no code (the lowest set: NAICS 6-digit codes; SOC detailed occupations and the broad occupations with no children).
naics_level=leaf/soc_level=leafon the data routes selects exactly these. metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other), bad_request for a level that is not an integer from 0 to 4 or a leaf other than true or false, bad_request for a bad cursor or a limit outside 1 to 5,000.
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/areas
Geographic areas (nation, states, counties)
Credentials: API key or App session. Operation id dataListAreas.
The vintage's areas in FIPS order, filtered and paged: the nation, the states and DC, and every county-level area including the 50 per-state catch-alls. Filters combine (AND). Areas have no nested order. The list does not depend on the plan: entitlement applies when data is requested. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
levelquery · integer- Only areas at this level: 0 nation, 1 state, 2 county. (0 to 2)
parentquery · string- Only the areas directly inside this area code:
00lists the states,22the counties of Louisiana. (pattern ^(\d{2}|\d{5})$) qquery · string- Search: areas whose name contains this text (case-insensitive) or whose source FIPS code starts with it.
cursorquery · string- Opaque cursor from
meta.pagination.next_cursorof the previous page. limitquery · integer- Items per page, 1 to 5,000 (default 1,000). (default 1000; 1 to 5000)
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
A page of areas.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataAreaItemalways present- The areas on this page, in FIPS order.
data[].codestringalways present- The FIPS code, zero-padded:
00nation,22state,22073county. data[].titlestring or nullalways present- The area's name (
Ouachita Parish, Louisianastyle;Undefinedfor a catch-all). data[].level0 | 1 | 2always present- 0 nation, 1 state, 2 county (names on
GET /v2/taxonomies/areas/levels). data[].parentstring or nullalways present- The containing area's code:
00for a state, the state code for a county; null for the nation. data[].typestring or nullalways present- The source's area type label (for example
County; catch-alls are typedCountytoo, so do not use it to find them). metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other), bad_request for a level that is not an integer from 0 to 2 or a parent that is not 00, a 2-digit state or a 5-digit county, bad_request for a bad cursor or a limit outside 1 to 5,000.
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/msas
Metropolitan statistical areas, live and retired
Credentials: API key or App session. Operation id dataListMsas.
Every MSA the vintage's taxonomy names, in code order, with its member counties at the latest MSA map year. Retired MSAs (no counties in the latest map) are listed too, marked, with where their counties went, so a retired name stays findable. Filters combine (AND). Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
qquery · string- Search: MSAs whose title contains this text (case-insensitive) or whose code starts with it.
contains_fipsquery · string- Only the MSA this county belongs to NOW (matched against
member_fips, so a retired MSA is never returned). (pattern ^\d{5}$) cursorquery · string- Opaque cursor from
meta.pagination.next_cursorof the previous page. limitquery · integer- Items per page, 1 to 5,000 (default 1,000). (default 1000; 1 to 5000)
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
A page of MSAs.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataMsaalways present- The MSAs on this page, in code order.
data[].codestringalways present- The MSA code, without leading zeros (
35380); use it asareas=msa:<code>. data[].titlestring or nullalways present- The MSA's name.
data[].member_fipsarray of stringalways present- The member county codes in the LATEST MSA map year; empty for a retired MSA. The only field
contains_fipsmatches.msa:<code>expands to these, catch-alls never included. data[].retiredbooleanalways present- True when the MSA has no counties in the latest map. A retired MSA named in
msa:<code>is 400retired_msa; it is never silently replaced by its successor. data[].retired_afterinteger- Retired only: the last MSA map year in which it had member counties.
data[].last_member_fipsarray of string- Retired only: its member counties in that year.
data[].successorsarray of object- Retired only: the MSAs those counties belong to in the latest map, each with how many of them; ordered by that count descending, then code. Empty when none of them is in any MSA now.
data[].successors[].codestringalways present- The successor MSA's code.
data[].successors[].titlestring or nullalways present- The successor MSA's name.
data[].successors[].countiesintegeralways present- How many of the retired MSA's last member counties are in this MSA now. (at least 1)
metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other), bad_request for a contains_fips that is not a 5-digit county code, bad_request for a bad cursor or a limit outside 1 to 5,000.
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/ownership
Ownership codes
Credentials: API key or App session. Operation id dataListOwnership.
The four ownerships the data is split by (federal, state and local government, private), with the tokens ownership= takes. Never paged. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
The ownerships.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataOwnershipItemalways present- The ownerships, in QCEW code order.
data[].code"fed" | "state" | "local" | "private"always present- The token to use in
ownership=. data[].legacy_code1 | 2 | 3 | 5always present- The QCEW ownership code (1 federal, 2 state, 3 local government, 5 private), also accepted in
ownership=. data[].titlestringalways present- The ownership's name, e.g.
Federal Government. metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other).
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
GET /v2/taxonomies/periods
The period axis
Credentials: API key or App session. Operation id dataListPeriods.
Every (year, quarter) the vintage holds, in order, including the carried-forward and projected quarters (meta.provenance_boundaries says which). from and to on the data routes must fall inside it. Never paged. Any authenticated caller: an API key (live or sandbox) or a session, any role. Taxonomies are free: not behind the entitlement gate, not admission-gated, not metered, and not limited by plan (a non-current vintage= needs no prior-vintage entitlement here; a withdrawn or superseded one is still refused). A sandbox key reads the sandbox vintage's taxonomy, which is real apart from its five invented counties and MSAs. Caching: with an explicit vintage= the answer can never change and is Cache-Control: public, max-age=31536000, immutable; without it, no-cache with the same strong ETag, so revalidating with If-None-Match answers an empty 304 until a release moves the current vintage. Problems are never cached.
Parameters
vintagequery · string- The vintage to read (default: the current one). Pinning it makes the answer immutable and cacheable for a year. (pattern ^(\d{8}|sandbox-\d{4}\.\d+)$)
X-DTG-Orgheader · string (uuid)- Session only: the organization the request acts in, when the person belongs to more than one (default: their own organization). An API key is bound to its organization; on a key this header must name that organization or be omitted. A malformed id, or an organization the caller is not an active member of, is 404
not_found.
Responses
200 success
The quarters.
As application/json.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After). X-DTG-Sandboxheader- Present, with the value
true, on every response to a sandbox API key, success and problem alike; it is set as soon as the credential is known. Every value in a sandbox response is synthetic and must never be published as data. Absent for live keys and sessions. ETagheader- A strong tag over the body less
meta.generated_at: the same for a pinned and an unpinned read of the same content and for every credential. Cache-Controlheaderpublic, max-age=31536000, immutablewhenvintage=was given;no-cacheotherwise.
dataarray of DataPeriodItemalways present- Every quarter, in time order.
data[].yearintegeralways present- Calendar year.
data[].quarter1 | 2 | 3 | 4always present- Calendar quarter.
metaDataMetaalways present- The
metaof every v2 envelope (spec section 3). It is written afterdataon the wire. Clients must tolerate unknown fields. meta.vintagestringalways present- The vintage the answer was read from: the internal build id (
20260913; a sandbox key's aresandbox-2026.1). Cite it and pass it back asvintage=to reproduce the answer exactly: a released vintage never changes. Its public name, such asDTG 2026.3, is thelabelonGET /v2/vintages. meta.sandboxtrue- Present, and true, only when the answer was read from a sandbox vintage: every value is synthetic and must never be published. Absent otherwise.
meta.generated_atstring (date-time)always present- When this response was produced, UTC, to the second (
2026-09-27T18:42:15Z). meta.granularity"annual" | "quarterly"- Data routes only: the period granularity of the points (on /map,
quarterlywhenqtrwas given). Absent on taxonomy responses. meta.provenance_boundariesDataProvenanceBoundariesalways present- Where the vintage's published record ends and estimation begins, recorded per vintage at build time and returned on every envelope. Compare a point's period against these ranges to know what kind of value it is. For OCCUPATION data this is the only provenance there is: occupation values carry no per-value label, so a period inside
actualsis published-basis, insidecescarried forward, insideprojectionsprojected. Industry values also carry their owndisclosurecode, which is authoritative for the value. The ranges move with each release; read them, never hard-code them. meta.provenance_boundaries.actualsobjectalways present- Quarters published by BLS in QCEW (the Quarterly Census of Employment and Wages). Industry values here have disclosure 0 (published) or 1 (estimated by DTG where QCEW withheld the value).
meta.provenance_boundaries.actuals.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.actuals.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.cesobjectalways present- Quarters after the latest QCEW release, carried forward from the CES and SAE monthly employment surveys (their rate of change applied to DTG's base, not their levels). Industry values here have disclosure 2.
meta.provenance_boundaries.ces.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.ces.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projectionsobjectalways present- Projected quarters, out to the end of the period axis. Industry values here have disclosure 3.
meta.provenance_boundaries.projections.fromstringalways present- First quarter of the range, lower case, e.g.
2004q1. (pattern ^\d{4}q[1-4]$) meta.provenance_boundaries.projections.tostringalways present- Last quarter of the range, lower case, e.g.
2025q4. (pattern ^\d{4}q[1-4]$) meta.geographyobject- Data routes only. Absent on taxonomy responses.
meta.geography.requestedintegeralways present- /series and /lq: the number of distinct areas the request resolved to before entitlement (a
state:XX,msa:orcluster:token counts its counties; a plain state code counts 1; noareascounts the nation as 1). /map: the counties of theareasrestriction, or without one the counties with a row for this code and period (catch-alls never counted). (at least 0) meta.geography.returnedintegeralways present- Areas (on /map, counties) that passed entitlement and are in the answer. On a summed request these are the areas inside the one summed series. (at least 0)
meta.geography.excludedintegeralways present- Requested counties the organization's entitlement removed (outside the active county set, or every county while the subscription is past due). On /map a requested-versus-returned gap beyond
excludedmeans counties with no data for the code and period, not an exclusion. (at least 0) meta.geography.regionDataRegion- Present only on a request whose areas were summed into one series (a lone
cluster:<id>ormsa:<code>, orsum=areas/combine=sum): what the summed area is made of. The CSV preamble prints it as# region:lines and the workbook's Source sheet asRegionrows. meta.geography.region.labelstringalways present- The summed series'
arealabel: the cluster's name or the MSA's title when one was asked for alone, otherwisecustom region. meta.geography.region.areasarray of DataRegionAreaalways present- Each area as requested, in request order.
meta.geography.region.areas[].tokenstringalways present- The token exactly as requested:
22073,22,00,state:22,msa:35380,cluster:<id>. meta.geography.region.areas[].kind"nation" | "state" | "county" | "stateAll" | "msa" | "cluster"always present- What the token is: the nation (
00), a state's own row (22), a county,stateAll(astate:XXtoken: every county of the state, its catch-all included), an MSA, or one of the organization's area clusters. meta.geography.region.areas[].codestringalways present- The area's code: a FIPS code for a county or state (the 2-digit state code for
stateAll), or the token itself, lower-cased, formsa:<code>andcluster:<id>. meta.geography.region.areas[].namestring or nullalways present- The area's name: the vintage taxonomy's title for a county or state, the MSA's title, or the cluster's name. Null where the taxonomy has none.
meta.geography.region.areas[].resolvedarray of stringalways present- The area codes this token contributed to the sum after entitlement. A county the plan does not cover appears in no list;
geography.excludedcounts it. meta.geography.region.resolvedarray of stringalways present- Every area code summed, deduplicated, in request order, after entitlement.
meta.paginationDataPaginationalways presentmeta.pagination.cursorstring or nullalways present- The
cursorthis page was requested with; null for the first page or an unpaged request. meta.pagination.next_cursorstring or nullalways present- Pass as
cursorto get the next page. Null on the last page and on every unpaged response, so null always means there is nothing more. meta.pagination.countintegeralways present- Rows in
dataon this response: series on /series and /lq, rows on /map, items on a taxonomy. (at least 0)
304 redirect
Not modified: the If-None-Match tag still matches. No body.
ETagheader- The current tag.
400 error
Bad request. Codes: unknown_parameter (a query parameter this route does not take; parameters[] names them), repeated_parameter (a parameter given more than once; parameter), bad_request (more than 50 query parameters), bad_request for a malformed vintage (a live key or a session takes YYYYMMDD, a sandbox key sandbox-YYYY.N; an id shaped for the other scope is refused the same way, so neither scope can probe the other).
As application/problem+json.
401 error
Unauthenticated. Codes: unauthenticated (no credential, or an API key or session that is unknown or expired); key_revoked (an API key that was revoked: revoked_at, and reason -- holder, admin, member_removed, seat_removed, api_disabled, addon_ended, account_closed, org_closed, retired, or null for a key revoked before T110 -- and a sentence saying when and why).
As application/problem+json.
403 error
Forbidden. Codes: no_membership (the account has no active organization membership), account_suspended (O56: the caller's own account is suspended by DTG; reason where recorded), org_suspended (the organization is suspended; organization {id, name} and, where recorded, reason), org_closed (the organization is closed; organization), wrong_instance (a key of the mode this process does not serve, for example a sandbox key on a live-only process; expected, and base_url naming the address that serves it).
As application/problem+json.
404 error
Not found. Codes: not_found (no such vintage in the caller's scope, or an X-DTG-Org header naming an organization the caller does not belong to), vintage_superseded (the pinned vintage was withdrawn and replaced by a correction; superseded_by names it; re-run against it), vintage_withdrawn (the pinned vintage was withdrawn and no correction exists yet; current names the vintage to use).
As application/problem+json.
414 error
URI too long. Codes: uri_too_long (the request URL is longer than the configured maximum, 8,192 bytes by default).
As application/problem+json.
429 error
Rate limited, and only that: rate_limited (over the 120 requests a minute per credential or 300 a minute per organization; the sandbox ceilings are lower). Retry-After and X-RateLimit-* say when to retry. This route is not admission-gated or metered.
As application/problem+json.
Retry-Afterheader- Seconds to wait before retrying.
X-RateLimit-Limitheader- The per-minute request ceiling that applies.
X-RateLimit-Remainingheader- Requests left in the current window.
X-RateLimit-Resetheader- Seconds until the window refills: on every answer, the time until the bucket is full again; on a refusal, until a request is allowed (as
Retry-After).
500 error
Server error. Codes: internal_error (for example a vintage file the server cannot read).
As application/problem+json.
Problem codes: unknown_parameter (400), repeated_parameter (400), bad_request (400), unauthenticated (401), key_revoked (401), account_closed (401), org_closed (401), no_membership (403), account_suspended (403), org_suspended (403), org_closed (403), wrong_instance (403), not_found (404), vintage_superseded (404), vintage_withdrawn (404), uri_too_long (414), rate_limited (429), internal_error (500). Every problem is a problem document.
Generated from taigan/openapi.yaml at catahoula 77925fab712f(API document version 2.0).