Repository navigation
feat(version): compile and declare actors on every version - #665
Merged
Merged
Conversation
The versions lane now compiles each actor into a module of its own and
declares `actors` on every version, `[]` for an app with none. An absent
field is what a CLI from before actors sends, and the platform refuses it
(409 actors_undeclared) for an app that has them.
- Each actor compiles with the compiler's single-function bundle(), keyed
base44/actors/<Name>/entry.ts (an entry.js too), over the files its
entry reaches among its own folder and base44/shared — as apper
assembles one. Not cfwBundleInput: its flat main.ts loses the path that
makes the entry an actor.
- Declared as name, entry, source, module {size, digest} and static_egress
(the compiler's STATIC_EGRESS_ARTIFACT_MARKER, installed by the actor
prelude). Sorted by name.
- Upload slots come after the bundles', each at actors/<Name>.mjs, which
the client checks the server signed.
- BuildTarget.actorsDir; at most 50 actors, refused before compiling.
Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
Contributor
🚀 Package Preview Available!Install this PR's preview build with npm: npm i @base44-preview/cli@0.1.32-pr.665.9dd49bdPrefer not to change any import paths? Install using npm alias so your code still imports npm i "base44@npm:@base44-preview/cli@0.1.32-pr.665.9dd49bd"Or add it to your {
"dependencies": {
"base44": "npm:@base44-preview/cli@0.1.32-pr.665.9dd49bd"
}
}
Preview published to npm registry — try new features instantly! |
On Windows @deno/loader caches npm packages under USERPROFILE while the compiler allows file reads only under LOCALAPPDATA. The testkit moves USERPROFILE to a temp dir for auth isolation, so every actor compile on windows-latest/npm failed with "filesystem imports are not allowed". DENO_DIR is honoured by both, as in production. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
carmelc
approved these changes
Oct 19, 2026
Contributor
|
One thing I did not understand is how is the cli supposed to work in a fullstack app given that it looks for the backend functions in the base44/functions folder |
Contributor
Author
|
Backend functions can exist also on fullstack app 🙃 |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Note
Description
Extends the versions lane so that publishing an app records its actors alongside its frontend assets, backend bundles, entities and agents. A new
compileActorsstep compiles every actor underbase44/actors/<Name>/entry.tsinto its own Durable Object Worker module via the functions-compiler's single-functionbundle(), declares it in the create-version call, and stages its bytes atactors/<name>.mjs. Until now a version described an app with actors as if it had none, so the platform would drop them.Related Issue
None
Type of Change
Changes Made
core/version/actors.ts(new) —compileActors()reads every actor, compiles each one separately (concurrency 4), and returns anActorArtifactper actor with its name, entry, source as written, module bytes, size, sha256 digest and theSTATIC_EGRESS_ARTIFACT_MARKERcontract. Actors are sorted by name so declared order — and therefore each upload slot — never follows a filesystem walk.base44/shared/**, keyed where the compiler looks; a reach into another actor or a backend function stays unresolved and fails the compile. Anentry.jsis keyed asentry.ts, since that path is how the compiler recognizes an actor (hencebundle()directly rather thancfwBundleInput, which would flatten a no-import entry tomain.ts).build, before anything is declared; more than 50 actors is refused up front withInvalidInputErrorto match the server ceiling. The module is also sanity-checked againstdo_class_nameso a plain Worker is never deployed under an actor's identity.core/version/api.ts— declaresactorsin the create-version body (always sent,[]when the app has none), appends actor upload slots after the asset, site-worker and bundle slots so adding actors moves no existing slot, verifies each signed slot path matchesactors/<name>.mjs, and uploads each module withputPresignedBody.core/version/schema.ts— adds theActorArtifactinterface andactorstoArtifactSet.core/version/functions.ts— exportsrequireCompilerRuntime(now parameterized so the message reads "Actors…" or "Backend functions…"),describeFailureandsha256for reuse.core/project/target.ts—BuildTargetresolvesactorsDir(defaultactors).core/version/artifacts.ts— collects actors during thebuildstep.docs/versions.md, updated declare/slot-order description and keywords.tests/core/version-actors.spec.ts(entry keying, shared-module reach, scope isolation, deterministic digests, set-wide failure, the 50-actor cap) and a newpublishsuite covering declaration shape, per-actor upload slots, slot ordering alongside bundles, the empty-actorscase, compile failure, and the standalone binary refusing an app with actors.TestAPIServersigns actor slots; thewith-actorsfixture gained abase44/shared/limits.tsimport so the shared path is exercised end to end, and the actor publish specs pinDENO_DIRfor the npm cache (Windows@deno/loadercompatibility).Testing
npm test)Checklist
docs/(AGENTS.md) if I made architectural changesAdditional Notes
The whole lane stays behind the
BASE44_VERSIONS_APIenv gate. Like backend functions, actor compilation needs the externalesbuild/@deno/loaderruntime packages, so the standalone binary refuses an app with actors withDEPENDENCY_NOT_FOUNDat stepbuildrather than silently publishing without them — both the npm-mode and binary-mode specs assert nothing is declared in that case.🤖 Generated by Claude | 2026-10-19 06:48 UTC | 9dd49bd