Directus SDK
Learn how to setup a Directus client with the TypeScript SDK
If you are working on a TypeScript project, you can use the Directus SDK library. The SDK provides utilities and helpers to interact with a Directus instance with (mostly) full type safety.
Setting up your client
To get started with the Directus SDK, install the required dependency:
pnpm add @directus/sdk
# or
npm install @directus/sdk
Then configure your client:
import { createDirectus, rest, staticToken } from '@directus/sdk'
import type { Schema } from '@my-generated-schema'
const DIRECTUS_BASE_URL = 'https://content.onderwijsloket.com'
const DIRECTUS_TOKEN = '<my-api-token>'
const directus = createDirectus<Schema>(DIRECTUS_BASE_URL)
.with(staticToken(DIRECTUS_TOKEN))
.with(rest())
To create a type-aware client, you must pass a Schema type argument. There is currently no official type package available for the Onderwijsloket API, but you can generate type definitions based on the OpenAPI specification. Refer to the related guide for instructions.
Using commands
The SDK exposes various commands that can be used with the client. In most cases, you will primarily use readItem and readItems. A full list of available commands can be found in the SDK source code.
/**
* Check the Directus SDK source code for all available commands
* @link https://github.com/directus/directus/tree/main/sdk/src/rest/commands
*/
import { readItems } from '@directus/sdk'
/**
* articles will be typed as:
* Pick<Schema['articles'], 'id' | 'title' | 'slug'>[]
*/
const articles = await directus.request(
readItems('articles', {
filter: {
status: {
_eq: 'published'
}
}
fields: ['id', 'title', 'slug'],
limit: 5
})
)
Caveats
While the SDK provides type safety, it can also introduce some limitations.
Filter Rules and Type Inference
Filter rules are not reflected in inferred types. For example, if you apply a { _nnull: true } filter to a field, that field may still be typed as null.
Relational Type Resolution
A larger issue occurs with relational fields not being properly resolved in the inferred types. This may require you to cast the type manually or use type guards.
/**
* Article type is inferred as:
* {
* id: string
* authors: string[] | { authors_id: string | null | { name: string } }[]
* }
*
* Even though we requested embedded fields, the SDK still resolves
* the type as a potential string.
*/
const article = await directus.request(
readItem('articles', '<article-id>', {
fields: [
'id',
{
authors: [
{
authors_id: ['name']
}
]
}
]
})
)