Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 4 additions & 0 deletions docs/.vitepress/config.js
Original file line number Diff line number Diff line change
Expand Up @@ -631,6 +631,10 @@ function sidebar() {
link: '/self-hosted/docker-guide',
text: 'Docker Guide',
},
{
link: '/self-hosted/projen-d9',
text: 'Projen Template',
},
{
link: '/self-hosted/cli',
text: 'CLI',
Expand Down
9 changes: 8 additions & 1 deletion docs/dictionary.txt
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@
(F|f)rontend
(F|f)rontmatter
(H|h)ardcode
(H|h)ealthcheck
(H|h)ealthchecks?
(H|h)ostname
(I|i)nit
(I|i)ntegrations
Expand All @@ -47,6 +47,7 @@
(R|r)epo
(R|r)ollup
(S|s)erverless
(S|s)caffolded?
(S|s)chemas?
(S|s)endmail
(S|s)lugify
Expand Down Expand Up @@ -136,7 +137,9 @@ customizable
customizations
DateTime
DDoS
deps
destructured
dev
devs
DigitalOcean
DigitalOcean's
Expand Down Expand Up @@ -218,6 +221,7 @@ Knex
Koyeb
KPIs
Kubernetes
LaWebcapsule
LDAP
localhost
lowercased
Expand Down Expand Up @@ -289,6 +293,8 @@ pre-defined
pre-existing
pre-formatted
pre-installed
(P|p)rojen
(P|p)rojen-(.*)
programmatically
Programmatically
ProgressEvent
Expand Down Expand Up @@ -335,6 +341,7 @@ SSR
StackOverflow
stylization
subdirectory
subprojects?
substring
SuperAdmins?
superset
Expand Down
8 changes: 8 additions & 0 deletions docs/self-hosted/docker-guide.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,14 @@ problems. If you can't or don't want to use Docker, we also publish an

:::

::: tip Building a backend with extensions?
This page covers the simplest way to **run** d9 with Docker. If you're using d9 as
the backbone of a complete backend (custom extensions, a team that needs a
consistent dev experience, multiple environments to keep in sync), the
[projen template for d9](/self-hosted/projen-d9) generates the whole project
(Dockerfile, Compose file, extensions folder, tasks) from a single source of truth.
:::

d9 is published to [Docker Hub]({{DOCKER_HUB_URL}}) under `lawebcapsule/d9`. To use the
latest d9 image from Docker Hub, run:

Expand Down
193 changes: 193 additions & 0 deletions docs/self-hosted/projen-d9.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,193 @@
---
description: Scaffold a d9 project with Docker Compose, extension management, and GitHub PR/issue templates using the @wbce/projen-d9 template.
readTime: 4 min read
---

# Projen Template

[`@wbce/projen-d9`](https://www.npmjs.com/package/@wbce/projen-d9) is a
[projen](https://projen.io) template for d9 projects. It scaffolds a local
development setup with Docker Compose (Postgres + Redis), extension management, and
GitHub PR and issue templates, and allows you to produce a Docker image you can
deploy to any environment.

Companion package:
[`@wbce/projen-d9-extension`](https://www.npmjs.com/package/@wbce/projen-d9-extension)
for authoring extensions.

::: info Just want to run d9?
If you only need to run d9 (no extensions, no customization), the
[Docker Guide](/self-hosted/docker-guide) is the easier and faster path: one
`docker run` command, no project scaffolding.
:::

## Bootstrap a new project

```sh
npx projen new --from @wbce/projen-d9
```

This creates a `.projenrc.js` and synthesizes the project.

## Integrate into an existing project
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Maybe add an explicit trigger warning message :
Projen may automatically replace certain folders and files. ..

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

it's the message just under, isn't it ?


When you're adopting the template inside an existing d9 repo, projen needs to take
ownership of `package.json` and a handful of other files. The cleanest path is to
delete `package.json` and let `projen new` regenerate everything, then reconcile the
diff against your old config:

1. **Start a feature branch.** Run `git checkout -b add-projen`. You want a clean
working tree so the post-synth diff is meaningful.
2. **Delete `package.json`** They'll be reconstructed from `.projenrc.js`.

```sh
rm package.json Dockerfile docker-compose.yml .gitignore tsconfig.json
```

3. **Bootstrap with `--no-git`.** The flag stops projen from running `git init` or
making an initial commit on top of your existing history, so you keep full
control of when to commit.

```sh
npx projen new --from @wbce/projen-d9 --no-git
```

4. **Reconcile the diff.** Compare the regenerated files against the previous
commit (`git diff HEAD`). Anything missing from your old setup (extra deps,
custom env vars in `docker-compose.yml`, extra Dockerfile steps, custom scripts)
needs to be expressed in `.projenrc.js`, not patched into the generated files.
Iterate: edit `.projenrc.js`, re-run `npx projen`, diff again.

5. **Commit once the diff is clean.**

::: tip Don't commit until the diff is right
Every `npx projen` run overwrites the managed files, so partial commits are easy
to clobber. Keep iterating on `.projenrc.js` until the generated output matches
what you need, then commit the whole set together.
:::

## Usage

`.projenrc.js`:

```js
import { D9Project } from '@wbce/projen-d9';
import { D9ExtensionType } from '@wbce/projen-d9-extension';

const project = new D9Project({
name: 'my-d9',
defaultReleaseBranch: 'main',
eslintOptions: {
dirs: ['src', 'test'],
prettier: true,
},
});

// A shared package other extensions can depend on
project.addExtension('shared', []);

// A hook extension that depends on the shared package
const myHook = project.addExtension('my-hook', [D9ExtensionType.HOOK]);
myHook.addDeps('shared@workspace:');

project.synth();
```

Then synth and start it:

```sh
npx projen
npx projen first-run # boot stack + create admin user
npx projen run # start d9 (port 8055)
```

The default admin user is `admin@example.com` / `totototo`.

::: warning Default credentials
The default admin password (`totototo`) is intentionally weak so you remember to
change it. Rotate it before exposing the instance to anything beyond `localhost`.
:::

The Docker container sets `EXTENSIONS_AUTO_RELOAD=true`, so editing an extension and
re-running `npx projen build-extensions` is enough. No restart, no redeploy.

### Extension types

`D9ExtensionType` values: `INTERFACE`, `DISPLAY`, `LAYOUT`, `MODULE`, `PANEL`,
`ENDPOINT`, `HOOK`, `OPERATION`. Pass an empty array for a shared (non-extension)
package.

Extensions live under `./plugins/` (configurable via `extensionsFolderName`) and are
built by the `build-extensions` task.

```js
// Single-type extension: a standalone `directus:extension` package
project.addExtension('audit-log', [D9ExtensionType.HOOK]);

// Multiple types: bundled under one `directus:extension` of type 'bundle'
project.addExtension('reporting-suite', [
D9ExtensionType.ENDPOINT,
D9ExtensionType.MODULE,
]);
```

### Sharing code across extensions

The `plugins/` folder is a pnpm workspace, so the usual pnpm sharing mechanisms
work across extensions:

- **`workspace:` protocol** to depend on a sibling package. The empty-types scaffold
`addExtension('shared', [])` is the canonical case (see [Usage](#usage) for the
full example).
- **`pnpm-workspace.yaml` catalogs** to pin shared dependency versions in one
place, then consume them as `catalog:` from each extension's `deps` / `devDeps`.

## Generated tasks

| Task | Description |
| --- | --- |
| `first-run` | Boot the stack, create admin, start d9 |
| `run` | Start d9 (`docker compose up directus`) |
| `build-extensions` | Install and build all extensions |
| `create-an-admin` | Create the default admin user |

## What gets generated

- `docker-compose.yml`: d9, Postgres (PostGIS), Redis with healthchecks
- `Dockerfile`: Node 22 + pnpm, builds extensions
- `.env.local`: sample for local environment overrides
- GitHub PR and issue templates via
[`@wbce/projen-shared`](https://www.npmjs.com/package/@wbce/projen-shared) (set
`githubConfig: false` to disable)

## Deploying

The generated `Dockerfile` is meant for deployment. Build and push it to your
registry, then run it against your target database and cache:

```sh
docker build -t <registry>/<image>:<tag> .
docker push <registry>/<image>:<tag>
```

Configure the deployed instance via environment variables (database, cache, secrets,
keys) the same way you would any other d9 container. See the
[Config Options](/self-hosted/config-options) page for the full list.

## Options

The full `D9ProjectOptions` reference lives in the
[package's API docs](https://github.com/LaWebcapsule/projen-templates/blob/main/packages/directus/API.md).
Highlights:

- `extensionsFolderName`: folder for extension packages (default: `plugins`)
- `packageVersions.d9`: version of `@wbce-d9/directus9` (default: `12.0.1`)
- `githubConfig`: `GitHubConfigOptions` or `false` to disable

Any option from the projen `TypeScriptProjectOptions` interface is also accepted.

## Source

- npm: [`@wbce/projen-d9`](https://www.npmjs.com/package/@wbce/projen-d9)
- Repository:
[LaWebcapsule/projen-templates](https://github.com/LaWebcapsule/projen-templates/tree/main/packages/directus)
8 changes: 8 additions & 0 deletions docs/self-hosted/quickstart.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,14 @@ readTime: 5 min read
> If you're looking for the fastest way to get up-and-running with d9, this guide will walk you through getting
> things installed, configured, and modeled.

::: tip Building a Backend with Extensions?

If you're using d9 as the backbone of a backend with custom extensions, the
[Projen Template](/self-hosted/projen-d9) scaffolds a complete project
(Dockerfile, Compose stack, extensions folder, tasks) from one command.

:::

## Requirements

- [Docker](https://docs.docker.com/get-docker/)
Expand Down
Loading