refactor(project): simplify scaffolding templates (memory, providers, container, empty) - #24
refactor(project): simplify scaffolding templates (memory, providers, container, empty)#24Hweinstock wants to merge 17 commits into
Conversation
| ); | ||
| expect(await Bun.file(join(projectRoot, "app", "my_agent", "main.ts")).exists()).toBe(true); | ||
|
|
||
| // The TypeScript template ships with longAndShortTerm memory pre-configured. |
| // the agent-python-strands template accepts them (enforced by the shortcut | ||
| // resolver). Without a runtime template there is nothing for them to tune. | ||
| if (modelProviderFlag !== undefined || apiKeyFlag !== undefined) { | ||
| const offending = modelProviderFlag !== undefined ? "model-provider" : "api-key"; |
There was a problem hiding this comment.
can we use a list + filter to simplify this? Then just show the first one in the error..
| ["default", [], ["SEMANTIC", "USER_PREFERENCE", "SUMMARIZATION", "EPISODIC"]], | ||
| ["none", ["--memory", "none"], []], | ||
| ["short", ["--memory", "shortTerm"], []], | ||
| test.each<[string, string, string[]]>([ |
There was a problem hiding this comment.
why is each test here duplicating a paramter?
| framework: ScaffoldRuntimeInput["framework"]; | ||
| protocol?: ScaffoldRuntimeInput["protocol"]; | ||
| modelProvider?: ModelProvider; | ||
| /** Ships with longAndShortTerm memory pre-configured. */ |
There was a problem hiding this comment.
lets just say ships with memory.
| * longAndShortTerm memory, the only memory configuration templates ship with: | ||
| * templates that support memory come with it pre-configured and non-overridable. | ||
| */ | ||
| function longAndShortTermMemory(runtimeName: string): Memory { |
There was a problem hiding this comment.
lets simplify create to just say getDefaultMemorySpec and avoid mentioning templates in the comment.
| /** Ships with longAndShortTerm memory pre-configured. */ | ||
| memory: boolean; | ||
| /** Accepts --model-provider / --api-key overrides; Bedrock-only otherwise. */ | ||
| supportsModelProvider: boolean; |
There was a problem hiding this comment.
this should be supportsModelProviderOverride
| "agent-python": { | ||
| runtimeName: "agent_python", | ||
| build: "CodeZip", | ||
| /** |
There was a problem hiding this comment.
lets simplify this to just use the original templates list, and duplicate the entries with -container as explicit different entries, with a different build.
| const CONTAINER_SUFFIX = "-container"; | ||
|
|
||
| export type RuntimeTemplateShortcutName = keyof typeof RUNTIME_TEMPLATE_SHORTCUTS; | ||
| export type RuntimeTemplateShortcutName = |
There was a problem hiding this comment.
this is unnecessary complexity, lets go back to the old approach.
| export type TemplateName = RuntimeTemplateShortcutName | typeof EMPTY_TEMPLATE_NAME; | ||
|
|
||
| /** Every `--template` value: the runtime shortcuts plus the empty project template. */ | ||
| export const TEMPLATE_NAMES = [ |
There was a problem hiding this comment.
can we rename this to PROJECT_TEMPLATE_NAMES.
| ...(overrides?.apiKey !== undefined && { apiKey: overrides.apiKey }), | ||
| ...(memory && { memory }), | ||
| runtimeVersion: build === "CodeZip" ? (template.runtimeVersion ?? "PYTHON_3_14") : undefined, | ||
| ...(template.framework === "strands" && { memory: getDefaultMemorySpec(runtimeName) }), |
There was a problem hiding this comment.
this feels fragile. if we re-introduce the doesSupportMemory flag, can we simplify this?
| EMPTY_TEMPLATE_NAME, | ||
| ] as unknown as readonly [TemplateName, ...TemplateName[]]; | ||
|
|
||
| export function isRuntimeTemplateShortcutName( |
There was a problem hiding this comment.
is there a way to inline this, or do we need it for the type assertion?
cd64e12 to
3ea14df
Compare
…ner only for strands, trim agui
3ea14df to
c545c24
Compare
Summary
Simplifies the project scaffolding templates on the
refactorline:--memoryflag removed fromproject createandproject add runtime. Templates that support memory (agent-python-strands,agent-typescript-strands,a2a-python-strands, + their-containertwins) now ship withlongAndShortTermmemory pre-configured and hardcoded (all 4 strategies).agent-python-minimalandmcp-python-fastmcpremain memory-less.--model-provider/--api-keyrestricted toagent-python-strands(+agent-python-strands-container).a2a-python-strandsandagent-typescript-strandsare now Bedrock-only and reject those flags.agent-pythonrenamed toagent-python-minimal.agent-python-strandsoffers a container build (agent-python-strands-container), resolved from the same source with conditional Dockerfile rendering (build: Container); every other template is CodeZip-only, and their Dockerfiles were removed.emptytemplate creates a project with no runtime and no harness.a2a/typescripthardcode Bedrock in their model loaders.--language/--protocol/--buildremoved;--frameworkremains only as the import strands/langgraph selector onadd runtime.project createsurface reduced to--name,--template,--model-provider,--api-key,--skip-install,--skip-git. Import + harness-tuning flags removed from create; import stays onproject add runtime. Passing only--namescaffolds the default harness (the only harness path).-containervariant andempty.Spec
spec (click to expand)
Problem: On the refactor branch, simplify the templates in a few core areas.
Definition of Done:
longAndShortTermmemory pre-configured.agent-python-strandssupports custom model providers and API keys from the existing flags.-containersuffix. We still resolve the container templates from the same source code with conditional Dockerfile rendering.Verification
agentcore project create --helpagentcore project add runtime --helpkeeps--type/--agent-id/--agent-alias-id(import),--template,--framework(import-only),--model-provider,--api-key, and all infra flags;--build/--language/--protocol/--memoryare gone.Example commands
Strands + Gemini builds (both build types)
--template agent-python-strands --model-provider gemini):agentcore project buildsynthesizes CloudFormation successfully; generated Python (main.py+model/load.pyrenderingGeminiModel) imports cleanly underuv run. Runtime spec:build: CodeZip,runtimeVersion: PYTHON_3_14, no Dockerfile.--template agent-python-strands-container --model-provider gemini): runtime spec isbuild: Containerwithdockerfile: Dockerfile;docker buildof the generated Dockerfile succeeds andpython -c "import main; import model.load"inside the image loads the Gemini strands module.agentcore project buildsynthesizes successfully.TUI
The interactive
agentcore project createwizard steps are now name → type → (model | template) → review — no memory step. The template picker lists all 11 templates including every-containervariant andempty. Template picker — all 8 options: 7 runtime templates (onlyagent-python-strandshas a-containervariant) +empty:Create flow — no memory step (name → type → template → review):
Template picker (transcribed from the screenshot):
Checks
bun run typecheck,bun run lint:check,bun run format:check, andbun test(2801 pass / 0 fail) all clean.End-to-end verification (dev → curl → deploy → invoke)
Every template was exercised through the full pattern, plus strands-python with a real Gemini key. Deploys were batched into one project (
TmplMatrix) — a single ~7-min deploy of 8 runtimes + memories + Gemini credential + a container image — then invoked and torn down (stack + ECR verified gone).dev+curlHello, world!initialize/tools/listmessage/sendtask completedAlso validated: static checks (
typecheck/oxlint/prettier) +bun test(0 failures); create/add--help; template enum; agui is Bedrock-only + memory-less + Dockerfile-less.Review
Three independent reviews (flag/dispatch logic, resolver+assets, TUI+tests) found no blockers. Applied fixes: reworded the
--template/--model-providerhelp; removed a now-deadbedrockAgentImporterdependency from the create handler; addedagui-python-strandstest coverage. Notes intentionally left as-is: the Pythonsession.pyactor-level summaries retrieval namespace (intended), and the pre-existing--api-key -stdin-before-rejection ordering (fixing it would couple the handler to shortcut internals). Separately noted (not this PR): naming a runtime literallymcpcollides with themcpPyPI dependency duringuv sync.How to reproduce