A Dagger module for managing Dagger modules that use the PHP SDK.
SDK-specific module authoring (scaffolding new modules, codegen) lives in
modules like this one. The engine drives the SDK: it records a module scope in
dagger.toml, sets the workspace cwd to it, and asks this module to generate
the scope through findClientRoot and generateScope. This module writes the
template files, the module's dagger-module.toml and the generated SDK files;
the engine owns the workspace bookkeeping. Dependencies between modules are
module clients, which this SDK does not generate yet; see
Module clients.
The PHP library and codegen live under sdk/, vendored from
dagger/dagger; sdk/VENDOR.md records the commit. Generation
writes them into each module with a client generated against
v1.0.0-beta.25.
This module needs an engine from v1.0.0-beta.17, the oldest release the generated
entrypoint passed on, including PHP's ordinary mixed-case enums.
The entrypoint failed on v1.0.0-beta.16. That engine sends an enum argument by its canonical
name, LOW for case Low, which PHP cannot read. dagger/dagger
67f0790ef5
fixes this. The run stopped at that failure, so other modules on that release are
untested and not supported. Modules target v1.0.0-beta.25: the floor only says
which engines the SDK and the entrypoints it generates run on. Those floor results were
for modules targeting v1.0.0-beta.21, and have not run again for v1.0.0-beta.25.
Earlier versions of this module documented v1.0.0-beta.12. On an older engine,
dagger generate and dagger module init now stop with a message that names the
engine, including for a module that keeps the built-in runtime. Upgrade the engine
to generate. The engine resolves its built-in PHP runtime from
github.com/dagger/dagger/sdk/php, not from this module. A module already on the
built-in runtime therefore still loads on that engine, without this module
generating it. An engine below the floor is not supported.
From your workspace root:
dagger module install github.com/dagger/php-sdkThe engine recognizes the SDK interface and records the module as the php SDK
in dagger.toml. After install, the module is also available in dagger call
as php-sdk.
Calls that return a Changeset will print the diff and prompt you to confirm
before writing anything to your workspace.
dagger module init php --name my-moduleThe engine records the module scope in dagger.toml and calls generateScope,
which seeds the starter template, writes dagger-module.toml, the SDK and the
entrypoint in one step. Files already in the module directory are kept.
--template picks a starter template under templates/ (minimal is the
default):
dagger module init php --name my-module --template minimalFor every recorded PHP module scope:
dagger generateFor a single module:
dagger call php-sdk mod --path my-module generatemod walks up from --path to the nearest module config, supporting both CLI
1.0 dagger-module.toml and legacy dagger.json. rootPath is the stable
workspace-root-relative identity; path is relative to the caller's current
directory.
See php-sdk.dang for the full type surface.
Generation writes sdk/ and a Dang entrypoint in sdk/entrypoint/: main.dang,
types.dang, build.dang and dang.toml. dagger-module.toml names the
entrypoint, and the engine runs a function through it. Commit sdk/ and
composer.lock: a module loaded from Git needs them.
A module moves to the entrypoint when it is self-contained. A module that has any
of the following keeps the runtime in its manifest and gets no dang.toml:
[[dependencies]]include,exclude,blueprintortoolchains- a
sourceother than the module directory - no
composer.json, or one without the./sdkpath repository - a Composer path or autoload path outside the module
- a Composer
vendor-dirother thanvendor - a runtime other than
php
To move such a module, remove what keeps it there and run dagger generate. A
custom entrypoint stays as it is.
A module already on the generated entrypoint that gains a Composer path outside the
module, or include rules, fails to generate. A generated entrypoint with
[[dependencies]] and a [runtime] reads as a runtime manifest. With
[[dependencies]] and no [runtime], generation and the engine refuse it, because
an entrypoint has no dependency list.
Generating the entrypoint fails for an enum whose cases the engine would give one name,
such as Low and LOW, because the engine would replace one with the other without
an error. The message names the enum and both cases. The failed generation applies none
of its changes: the module's manifest and sdk/ stay as they were, so a module moving
from the built-in runtime stays on it until you rename one of the cases and update its
references. The engine can still update the workspace's dagger.lock when the session
ends. A generated entrypoint gets this check the next time it is generated.
The engine reads the entrypoint from the module's files, which .gitignore filters.
Generation appends rules to the module's .gitignore and changes no existing rule:
!/sdk/ and !/sdk/** after any rule other than a vendor/ rule, and /vendor/
when no rule ignores vendor/. An ignore rule in a directory above the module still
applies. Remove that rule yourself.
The SDK manages the Dagger version in sdk/entrypoint/dang.toml, and sets it to the
version the module's client is generated against, v1.0.0-beta.25. Generation
replaces dagger = true or an older version on the Dagger import, requires
dang = "2.1", and keeps every other setting. Comments and formatting are lost, and
keys are written in alphabetical order.
Generation fails, and applies none of its changes, in these cases:
dangdeclares another language version.- The
Daggerimport has apathor a non-emptyendpoint. - Another import declares a different Dagger version.
- An import has a
pathinsidesdk/, which generation replaces. sdk/entrypoint/dang.tomlexists and the module's manifest does not name the entrypoint this SDK wrote.sdk/exists and is not this SDK's library.- A
dang.tomlabove the entrypoint within the module holds settings that the generated file would hide. Files are not merged, so move those settings intosdk/entrypoint/dang.toml.
Generation never changes a dang.toml above the entrypoint.
dang = "2.1" is the language version. The version on the import is a Dagger
version, and parsing it needs Dang v2.2.0. Standalone Dang tooling older than v2.2.0
may reject the import.
The generated files carry the same version in two channels:
dang.toml: dagger/dagger#14902 selects the module's API view from itsDaggerimport. The change is on dagger/daggermainas of7e9eaacc, andv1.0.0-beta.25predates it. Its runtime effect is not verified by this SDK's checks.DAGGER_CLIENT_VERSIONon the exec that runs the module: dagger/dagger#14881 makes the engine read it.v1.0.0-beta.22is the first release with that change.
The version stays v1.0.0-beta.25, the last release before the identifier-casing cut,
until the PHP codegen is ported to those rules. dagger/dagger gates the cut at
v1.0.0-beta.26. From v1.0.0-beta.22, each release has an API view of its own, and
the client is generated against the v1.0.0-beta.25 view.
The targetVersion setting, or --target-version, pins a module to another release
from v1.0.0-beta.17 to v1.0.0-beta.25, which the client schema,
DAGGER_CLIENT_VERSION and dang.toml then use. Generation refuses a value that is
not a release, is later than v1.0.0-beta.25 or is below v1.0.0-beta.17, and refuses
a pin on a module that keeps the PHP runtime, which the engine generates for its
manifest's engineVersion. The checks here pin only v1.0.0-beta.24.
Passing checks on a released engine show what generation writes and that calls work.
They do not show that dang.toml selects a view. No check here shows that
DAGGER_CLIENT_VERSION selects one.
findClientRoot detects the PHP client root containing your current directory:
the nearest composer.json at or above it. This is how
dagger module client add finds the module you are standing in. The SDK
vendored under a module's sdk/ has a composer.json of its own; from there
the module that owns it answers.
Detection records nothing. The scopes dagger generate regenerates are the ones
recorded in dagger.toml under [sdks.php.scopes."<path>"].
Generated module clients are not supported yet. dagger module client add in a
PHP scope fails and leaves the workspace unchanged. A module's existing
dependencies are kept as they are.
A workspace set up with a CLI before v1.0.0-beta.12 registers this SDK with a
[modules.php-sdk.as-sdk] table, which newer engines ignore. Convert the table
to the new SDK registration, then regenerate:
dagger ws migrate
dagger generateTo exclude a directory tree from generation, drop an empty
.dagger-php-sdk-skip-generate file at or above the module root. Useful for
fixtures, vendored modules, or anything you don't want regenerated in bulk.
touch some/fixture/.dagger-php-sdk-skip-generate