Skip to main content

Document IDs

Document IDs are unique identifiers of a document that can be automatically generated by the server or manually specified by the user.

Why Use Document IDs

Every document in a database needs a unique identifier. Squid supports multiple ID formats depending on your database type and schema, from simple strings to composite keys spanning multiple fields. Understanding how IDs work lets you correctly reference, create, and look up documents.

Overview

Squid's built-in database supports two different types of document IDs, while database connectors require an object for their document ID.

Built-in database

In Squid's built-in database, document IDs can be one of two types:

  1. A string that is unique within the collection. A string is an effective way to identify one document from many others. Often, developers will set string IDs to be randomly generated UUIDs. You can also provide your own unique string:
Client code
const collectionRef = squid.collection('users');
const docRef = collectionRef.doc('my_custom_id');
await docRef.insert({ name: 'John Doe', age: 30 });
  1. Composite primary keys, which take the form of an object. If the user modifies the schema of a collection in the console and makes the primary key composite, the ID must be in the form of an object, such as {employeeName: string, deptId: string}. This allows you to specify multiple fields as the document ID. For example, if Jane Doe in department 12345 just celebrated her birthday, we may update her age as follows:
Client code
const collectionRef = squid.collection('employees');
const docRef = collectionRef.doc({ employeeName: 'Jane Doe', deptId: '12345' });
await docRef.update({ age: 31 });

Auto ID generation

An ID is auto generated by Squid when the user does not specify an ID and the schema does not require the ID to be a composite primary key. In the example below, the ID is automatically generated:

Client code
const collectionRef = squid.collection('users');
await collectionRef.doc().insert({ name: 'John Doe', age: 30 });

External database connectors

For any non-built-in connector, the document ID must be in the form of an object, even if the primary key is not composite.

Here's an example of how to create a document with a custom ID in a database connector:

Client code
const collectionRef = squid.collection('users', 'CONNECTOR_ID');
const docRef = collectionRef.doc({ id: 'my_custom_id' });
await docRef.insert({ name: 'John Doe', age: 30 });

Querying by Document ID

Document IDs are queryable through the __docId__ pseudo-field, available on every connector without knowing the underlying primary key column names. The docId() and docIds() query shortcuts cover the common cases:

Client code
await squid.collection<User>('users').query().docId('user_abc123').snapshot();

For composite primary keys, pass an object with all key fields:

Client code
await squid
.collection('inventory', 'CONNECTOR_ID')
.query()
.docId({ orgId: 'o1', itemId: 'i1' })
.snapshot();

Composite-key __docId__ filters support only the equality operators (==, !=, in, not in) and are not available on Elasticsearch and DynamoDB connectors. Single-key filters support the full operator set on all connectors. See filtering by document ID for details, and delete by query for deleting documents by ID filter.

Error Handling

ErrorCauseSolution
Invalid ID formatPassing a string ID for an external connector, which requires an objectUse an object ID for external connectors: doc({ id: 'value' })
Missing composite key fieldsNot providing all fields required by a composite primary keyInclude all fields defined in the composite key schema
ID conflict on insertInserting a document with an ID that already existsUse a unique ID, or call update() instead if modifying an existing document

Best Practices

  1. Use string IDs for simple lookups in the built-in database when a single field uniquely identifies the document:

    Client code
    const userRef = squid.collection<User>('users').doc('user_abc123');
  2. Use composite keys when multiple fields define uniqueness, such as a combination of department and employee name:

    Client code
    const empRef = squid.collection('employees').doc({
    deptId: 'engineering',
    employeeId: 'emp_456',
    });
  3. Always use object IDs for external connectors, even when the primary key is a single column. This is a Squid requirement for consistency across connector types.

  4. Use auto-generated IDs when you do not need control over the ID value, such as when creating log entries or events:

    Client code
    await squid.collection('events').doc().insert({ type: 'click', timestamp: Date.now() });