Skip to content

feat(actor): add actor command and scaffolding#555

Draft
ImriKochWix wants to merge 13 commits into
mainfrom
feat/realtime-handler
Draft

feat(actor): add actor command and scaffolding#555
ImriKochWix wants to merge 13 commits into
mainfrom
feat/realtime-handler

Conversation

@ImriKochWix

@ImriKochWix ImriKochWix commented Jun 30, 2026

Copy link
Copy Markdown
Contributor

Note

Description

Adds a new actor resource to the CLI (formerly "realtime handler"), enabling users to scaffold, deploy, and type-check stateful realtime actors from the terminal. Actors live in base44/actors/<Name>/ with an entry.ts and optional schema.jsonc message catalog, and are wired into project config, the unified deploy command, and TypeScript type generation. Also pins npm@11 in the publish workflows to fix an EBADENGINE failure on the Node 20 runner.

Related Issue

None

Type of Change

  • Bug fix (non-breaking change which fixes an issue)
  • New feature (non-breaking change which adds functionality)
  • Breaking change (fix or feature that would cause existing functionality to not work as expected)
  • Documentation update
  • Refactoring (no functional changes)
  • Other (please describe): CI fix — pin npm@11 in publish workflows

Changes Made

  • New actor resource (core/resources/actor/): schema, config reader (readAllActors), deploy logic (deployActorsSequentiallyPUT actors/<name>), API client, and Resource<Actor> binding.
  • New CLI commands under base44 actor: new <ActorName> scaffolds an Actor<State, Message> subclass, and deploy [names...] deploys selected or all actors with per-actor status (deployed/unchanged/error) and a summary.
  • Project integration: added actorsDir (default actors) to the config schema, threaded actors through ProjectData, readProjectConfig, hasResourcesToDeploy, and deployAll so the unified deploy command handles actors.
  • Type generation: schema.jsonc message catalogs (types/toClient/toServer) compile into an ActorRegistry discriminated union plus an ActorNameRegistry, replacing the old regex-based extraction with a single-pass compile; SDK package name (@base44/sdk vs @base44-preview/sdk) is auto-detected and a module context guard (export {};) is emitted.
  • Rename: realtime / RealtimeHandler renamed to actor / Actor throughout; schema sections renamed inbound/outboundtoClient/toServer.
  • CI: pinned npm@11 in manual-publish.yml and preview-publish.yml (npm@latest is 12.x, requires Node >=22).

Testing

  • I have tested these changes locally
  • I have added/updated tests as needed
  • All tests pass (npm test)

Checklist

  • My code follows the project's style guidelines
  • I have performed a self-review of my own code
  • I have commented my code, particularly in hard-to-understand areas
  • I have made corresponding changes to the documentation (if applicable)
  • My changes generate no new warnings
  • I have updated docs/ (AGENTS.md) if I made architectural changes

Additional Notes

New tests added: tests/core/types-actor.spec.ts (catalog → discriminated union compilation, shared-type prefixing, name-collision detection) and extended tests/cli/types_generate.spec.ts with ActorNameRegistry/ActorRegistry assertions plus a ChatRoom fixture. Since actors are a new backend resource type, docs/resources.md may warrant an update.


🤖 Generated by Claude | 2026-07-09 13:35 UTC | 3443d0b

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@github-actions

github-actions Bot commented Jun 30, 2026

Copy link
Copy Markdown
Contributor

🚀 Package Preview Available!


Install this PR's preview build with npm:

npm i @base44-preview/cli@0.1.2-pr.555.3443d0b

Prefer not to change any import paths? Install using npm alias so your code still imports base44:

npm i "base44@npm:@base44-preview/cli@0.1.2-pr.555.3443d0b"

Or add it to your package.json dependencies:

{
  "dependencies": {
    "base44": "npm:@base44-preview/cli@0.1.2-pr.555.3443d0b"
  }
}

Preview published to npm registry — try new features instantly!

ImriKochWix and others added 12 commits June 30, 2026 13:54
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
new.ts used project.root but readAllRealtimeHandlers uses dirname(configPath),
causing handlers to be created at realtime/ instead of base44/realtime/.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
'base44' is the CLI package name and has no exported types.
@base44/sdk now exports RealtimeHandler and Conn for type-checking,
and the bundler rewrites the import to the CF shim at deploy time.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- base44 types generate now includes realtime handlers in types.d.ts
- RealtimeHandlerNameRegistry: auto-registers handler names (no manual declare needed)
- RealtimeHandlerRegistry: compiled from schema.jsonc inbound/outbound JSON schemas
- Add schema.jsonc support to realtime-handler resource reader
- Update test fixture with ChatRoom schema and assertions

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Detect @base44/sdk vs @base44-preview/sdk from project's package.json
  so declare module targets the correct package name
- Add export {} to generated types.d.ts to ensure module context,
  preventing ambient module from shadowing the SDK package types

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
- Remove unused RealtimeHandlerConfig type alias
- Replace [^]* regex with [\s\S]* (Biome noEmptyCharacterClassInRegex)
- Auto-format long lines per Biome formatter rules

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
The dedicated endpoint calls ensure_cfw_backend and uses force_per_function
so the bundler runs applyRealtimeCompat instead of the per-app path.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
schema.jsonc is now a catalog of named messages (inbound/outbound maps of
message-name -> full JSON Schema, like entities) plus optional shared `types`.
compileRealtimeHandler emits one named interface per message (direction- and
handler-prefixed to avoid collisions) + shared types, and composes the
inbound/outbound unions in the registry.

Removes the /\{([\s\S]*)\}/ body-scrape, which produced invalid TS whenever
json-schema-to-typescript emitted more than one declaration (unions with
$defs). Because every message is a single flat object, that multi-declaration
case can no longer arise.

Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…lient/toServer

The old names were written from the client's perspective, so handler code
read backwards (InMsg = Reg["outbound"]) and every reader had to do the
double-negative. toClient/toServer read correctly from both sides:
Reg["toServer"] is what the handler receives, Reg["toClient"] is what it
sends. Generated interface prefixes follow (GameRoomToClientInit).

Breaking for schema.jsonc files and the generated registry shape; done now
while there are zero external users.

Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
Rename the Durable-Object abstraction and its CLI surface to the actor model:
- command group `base44 realtime <cmd>` -> `base44 actor <cmd>`
- resource dir src/core/resources/realtime-handler/ -> resources/actor/;
  commands/realtime/ -> commands/actor/
- project config key realtimeDir("realtime") -> actorsDir("actors");
  ProjectData.realtimeHandlers -> actors
- project directory convention base44/realtime/<Name>/ -> base44/actors/<Name>/
  (resource discovery + generated actor message types)
- builder deploy route PUT realtime-handlers/<name> -> PUT actors/<name>
- scaffold template emits `import { Actor } ... extends Actor`

The entity live-update Socket.IO dev-server (dev-server/realtime.ts,
createRealtimeServer) is intentionally left as "realtime" — it's the
entity-change feature, not the Actor DO.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
- Biome organizeImports across the files touched by the actor rename (import
  order shifted when realtime-handler paths became actor paths).
- preview-publish + manual-publish: pin npm@11; npm@latest is now 12.x which
  requires node >=22 and fails EBADENGINE on the node-20 runner (.node-version).

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@ImriKochWix ImriKochWix changed the title feat(realtime): add realtime command and handler scaffolding feat(actor): add actor command and scaffolding Jul 9, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant