Spatial Share Links

Create public read-only links for documents, document folders, model bundles, or mixed collections.

Spatial share links let clients expose documents, document folders, processed model bundles, or selected mixed collections through a public, read-only URL. The URL itself belongs to the Atlas frontend. The API stores the link settings and resolves the UID when an anonymous viewer opens the link.

Only processed model bundles can be shared as bundle resources. Source upload bundles are not supported by this flow.

Authenticated clients can manage links from a model bundle:

GET /v1/spatial/bundles/{bundleId}/share-links
Authorization: Bearer <personal-access-token>
POST /v1/spatial/bundles/{bundleId}/share-links
Authorization: Bearer <personal-access-token>
Content-Type: application/json

{
  "password": "optional-password",
  "expiresAt": "2026-06-30T12:00:00Z",
  "bundleIds": [
    "22222222-2222-2222-2222-222222222222",
    "33333333-3333-3333-3333-333333333333"
  ]
}

Set password to null, empty, or whitespace for a no-password link. Set expiresAt to null for no expiration. Omit bundleIds to share only the route model bundle. Include bundleIds to add more processed model bundles to the same link; the route {bundleId} is always included and remains the primary model.

Each response includes:

  • uid: the public share identifier
  • publicUrl: the frontend URL to give to a viewer
  • passwordRequired: whether the link needs a password unlock request
  • expiresAt: the optional expiration timestamp
  • bundleId: the primary model bundle id clients should open by default
  • scope: the resources included in the link, including every model bundle id

The list endpoint uses the standard PagedListResponse<T> shape with offset and limit. It returns every share link that includes the route model bundle, including links with multiple model bundles.

Documents have matching document-scoped endpoints:

GET /v1/spatial/documents/{documentId}/share-links
Authorization: Bearer <personal-access-token>
POST /v1/spatial/documents/{documentId}/share-links
Authorization: Bearer <personal-access-token>
Content-Type: application/json

{
  "password": null,
  "expiresAt": null
}

Document folders have matching folder-scoped endpoints:

GET /v1/spatial/documents/folders/{folderId}/share-links
Authorization: Bearer <personal-access-token>
POST /v1/spatial/documents/folders/{folderId}/share-links
Authorization: Bearer <personal-access-token>
Content-Type: application/json

{
  "password": null,
  "expiresAt": null
}

A folder-scoped link exposes every document in that folder and descendant folders. It is live: documents added later under the same folder path become visible through the existing link.

When a model bundle is accessible through a public link, the response also includes spatial annotations from that model location and the location documents linked from those annotations. Annotation-linked documents are resolved at view time and appear in the public documents list with download links only after the model link is accessible. Each annotation in annotations also includes its own linked documents entries so viewers can render picture pins and open the matching files without an authenticated annotation API call.

Create a mixed-scope link with the generic endpoint:

POST /v1/spatial/share-links
Authorization: Bearer <personal-access-token>
Content-Type: application/json

{
  "password": "optional-password",
  "expiresAt": "2026-06-30T12:00:00Z",
  "scope": {
    "documentIds": ["11111111-1111-1111-1111-111111111111"],
    "folderIds": ["33333333-3333-3333-3333-333333333333"],
    "bundleIds": ["22222222-2222-2222-2222-222222222222"]
  }
}

Replace link settings, and optionally the full document/folder/model scope, with:

PATCH /v1/spatial/share-links/{shareLinkId}
Authorization: Bearer <personal-access-token>
Content-Type: application/json

{
  "password": null,
  "expiresAt": null,
  "scope": {
    "documentIds": [
      "11111111-1111-1111-1111-111111111111",
      "33333333-3333-3333-3333-333333333333"
    ],
    "folderIds": ["44444444-4444-4444-4444-444444444444"],
    "bundleIds": ["22222222-2222-2222-2222-222222222222"]
  }
}

Omit scope to keep the existing resources unchanged. Include scope to replace the entire resource set. Use this to manage the model list after link creation by replacing bundleIds with the desired processed model bundle ids. The generic endpoint preserves the current primary model when that model is still in the replacement scope; the bundle-scoped PATCH /v1/spatial/bundles/{bundleId}/share-links/{shareLinkId} endpoint keeps the route model included and primary. Managing or replacing a scope requires write access to every current and proposed resource.

Revoke a link with:

DELETE /v1/spatial/share-links/{shareLinkId}
Authorization: Bearer <personal-access-token>

Managing links requires the same write access used to upload or manage every scoped document, document folder, or model bundle. Read-only viewers cannot create, edit, or revoke links.

Atlas extracts the UID from its frontend route and calls:

GET /v1/spatial/shared/{uid}

For a no-password link, the response includes bundles, folders, documents, and annotations. bundleId, displayName, version, detailLevel, capturedAt, and top-level files describe the primary model bundle to open first; additional model bundles are available from bundles. Bundle files use the same BundleFilePresignedDownloadResponse shape as authenticated bundle file download lists. Documents include metadata, folderPath, and a presigned document link. The document link includes thumbnailUrl when a generated small thumbnail already exists for an image or PDF document; use url as the fallback and keep downloads pointed at url. Folder-scoped documents and annotation-linked documents for accessible model bundle locations are returned in the same documents list as explicitly scoped documents.

Each entry in annotations contains the public annotation geometry and display metadata, including annotationId, locationId, title, body, category, status, priority, color, position, altitudeMode, geometryType, coordinates, savedView, normal, createdAt, and updatedAt. The annotation's nested documents list uses the same public document shape as the top-level documents list and includes presigned link values after the share link is accessible.

For a password-protected link, the first response returns passwordRequired=true and no file links. Submit the password in a second request:

POST /v1/spatial/shared/{uid}/unlock
Content-Type: application/json

{
  "password": "viewer-password"
}

The unlock response includes the same scoped metadata and download entries.

Public share-link access is read-only. It exposes annotation records only as shared view data and does not expose upload, edit, delete, job, or share-management operations.

Error behavior

  • Unknown UID: 404 Not Found
  • Incorrect password: 401 Unauthorized
  • Expired link: 410 Gone
  • Revoked link: 410 Gone

On this page