Copyright © 2026 Appstrate contributors. This specification is licensed under CC-BY-4.0. Code and examples are licensed under MIT.
Agent Flow Definition (AFD) is an open specification for declaring portable AI workflow packages. It defines a JSON-based manifest format for four package types — flows, skills, extensions, and providers — along with their dependency model, schema system, archive layout, and provider authentication metadata. AFD standardizes package definition and composition; it does not define tool-calling protocols, agent-to-agent transport, or runtime execution APIs.
This document is a draft of the AFD v1.0 specification. It is published for community review and early implementation feedback.
This draft was extracted from the Appstrate reference implementation. It is expected to evolve based on implementation experience and community input before reaching a stable release.
Agent Flow Definition (AFD) defines a declarative package format for AI workflows and closely related package types.
The central artifact in AFD is the flow — a package that captures the user’s intent (via a prompt.md companion file) together with everything the agent needs to fulfill it: skills, extensions, provider connections, input and output schemas, and execution settings. Where other standards define agent capabilities (what an agent can do), an AFD flow defines an objective (what the agent should accomplish).
AFD also defines three supporting package types — skills (reusable instructions), extensions (runtime tools), and providers (service connectors) — that flows compose as dependencies.
The goal of AFD is to let producers publish portable artifacts that describe:
AFD is intentionally centered on package definition. It standardizes package metadata and package layout, not runtime execution APIs.
This specification defines:
flow, skill, extension, provider;input, output, config, and selected credential definitions; andThis specification does not define:
AFD is transport-agnostic: it does not prescribe how packages are fetched, transferred, or cached.
AFD operates at a different abstraction level than existing AI agent standards. The key distinction is between goal (what should be accomplished) and capability (how to accomplish a specific task):
┌─────────────────────────────────────────────────────────┐
│ Goal layer AFD Flow │
│ "Process my inbox and create │
│ a summary of support requests" │
│ = the user's intent, packaged │
├─────────────────────────────────────────────────────────┤
│ Capability layer AFD Skills / Extensions │
│ "Rewrite text in a professional │
│ tone" / "Fetch JSON from a URL" │
│ = reusable abilities the agent │
│ can draw on to reach the goal │
├─────────────────────────────────────────────────────────┤
│ Connection layer AFD Providers │
│ "Gmail via OAuth2" │
│ = authenticated access to │
│ external services │
└─────────────────────────────────────────────────────────┘
A flow’s prompt.md replaces what a human would type to give an agent its objective. Skills, extensions, and providers are the resources the agent uses to fulfill that objective. AFD packages all of these together into a portable, versioned artifact.
Existing standards address different concerns:
SKILL.md format for declaring reusable agent capabilities. AFD skill packages (§3.3) adopt this convention. However, skills define capabilities, not goals — the goal comes from the AFD flow that composes them.x- convention (§10).These standards are complementary and operate at different layers:
Discovery MCP Registry / A2A Agent Cards "where to find agents and tools"
Transport MCP JSON-RPC / A2A Tasks "how agents communicate at runtime"
Capability Agent Skills / MCP Tools "what an agent knows how to do"
Goal AFD Flow "what the agent should accomplish"
Packaging AFD "how it is all declared and distributed"
manifest.json file contained in every AFD package archive.prompt.md, SKILL.md, or a TypeScript source file.requires, used by a flow to name packages it expects at execution time.registryDependencies, used to declare installable package dependencies with semver ranges.The key words “MUST”, “MUST NOT”, “REQUIRED”, “SHOULD”, “SHOULD NOT”, and “MAY” in this document are to be interpreted as described in BCP 14 [RFC 2119] [RFC 8174] when, and only when, they appear in all capitals, as shown here.
Conforming producers MUST emit manifests and package archives that satisfy the requirements in this document. Conforming consumers MUST reject malformed packages and SHOULD preserve unknown fields when round-tripping manifests. AFD v1.0 intentionally allows extensibility: manifests and several nested objects accept additional fields unless this specification explicitly forbids them. Extension fields MUST follow the naming convention defined in §10.
AFD defines four package types:
flow: a complete workflow package consisting of manifest metadata and a prompt.md companion file;skill: a declarative capability package consisting of a minimal manifest and SKILL.md;extension: a runtime tooling package consisting of a manifest and at least one root-level TypeScript source file;provider: a service connector package described entirely by manifest.json.A package’s type field is the dispatch key used by validators and archive parsers. Producers MUST set it to exactly one of the values above.
Every AFD package MUST have a scoped name of the form @scope/name. The scope and name segments MUST each match SLUG_PATTERN:
[a-z0-9]([a-z0-9-]*[a-z0-9])?
As a consequence:
The full scoped-name pattern is:
^@[a-z0-9]([a-z0-9-]*[a-z0-9])?\/[a-z0-9]([a-z0-9-]*[a-z0-9])?$
The top-level version field MUST be a valid semantic version string accepted by the semver.valid() algorithm. Registry dependency values MUST be valid semantic version ranges accepted by semver.validRange().
AFD itself does not define its own range syntax. It delegates version parsing and range parsing to widely used semantic-version semantics. In practice:
1.0.0;^1.0.0, ~2.1, >=3.0.0, or *;If a registry supports non-version queries, it MAY resolve queries in the order exact version, dist-tag, then semver range. Exact version lookups MAY resolve yanked entries; dist-tags and ranges SHOULD prefer non-yanked versions.
When a consumer encounters a manifest whose schemaVersion has a higher MAJOR number than the highest version it supports, it MUST reject the manifest and SHOULD report an error identifying the unsupported schema version. Processing a manifest with an unknown major version could lead to silent data loss or incorrect behavior.
When a consumer encounters a manifest whose schemaVersion has the same MAJOR number but a higher MINOR number than the highest version it supports, it SHOULD process the manifest on a best-effort basis. Unknown fields SHOULD be preserved. Consumers MAY emit a warning indicating that some fields may not be fully understood.
When schemaVersion is absent from a skill, extension, or provider manifest (where the field is optional), consumers SHOULD treat the package as targeting schema version 1.0.
AFD packages are distributed as ZIP archives.
Every package archive MUST contain manifest.json at the archive root. Additional required files depend on manifest.type:
| Type | Required companion content |
|---|---|
flow |
prompt.md at archive root, non-empty |
skill |
SKILL.md at archive root |
extension |
at least one root-level .ts file other than .d.ts |
provider |
no companion file beyond manifest.json |
Consumers SHOULD sanitize ZIP entries before processing them. At minimum, entries with path traversal segments (..), absolute paths, null bytes, backslashes, __MACOSX/ prefixes, or directory-only entries SHOULD be ignored.
All manifests are JSON objects. Unknown top-level fields and unknown nested fields in extensible objects are allowed by the validation model and SHOULD be preserved by tooling unless a tool intentionally normalizes the manifest.
name^@${SLUG_PATTERN}\/${SLUG_PATTERN}$@example/customer-intakeversion1.2.0typeflow, skill, extension, providerflowdisplayNameflow; SHOULD for skill, extension, and providerCustomer Intake AssistantdescriptionCollects inbound requests and produces a structured summary.keywords["workflow", "email", "support"]licenseMITrepositoryhttps://example.com/afd/customer-intakeschemaVersionflow; MAY for other package typesMAJOR.MINOR where both segments are non-negative integers (e.g., 1.0, 2.1). The format follows a subset of semantic versioning without the patch component. A change in MAJOR indicates a breaking manifest model change; a change in MINOR indicates an additive, backwards-compatible revision.1.0 for packages targeting this draft.1.0registryDependenciesskills, extensions, and providers mapsregistryDependencies and the flow-specific requires field.{ "skills": { "@example/rewrite-tone": "^1.0.0" } }Flow manifests extend the common fields above. A conforming flow manifest MUST include schemaVersion, displayName, author, and requires.
authorflowAFD Examplesrequiresflowproviders, skills, and extensions maps{ "providers": { "@example/gmail": "1.0.0" } }providersConfiguration{ "@example/gmail": { "scopes": ["gmail.readonly"], "connectionMode": "admin" } }inputschema member{ "schema": { "type": "object", "properties": { "query": { "type": "string" } } } }outputschema member{ "schema": { "type": "object", "properties": { "summary": { "type": "string" } } } }configschema member{ "schema": { "type": "object", "properties": { "language": { "type": "string" } } } }executiontimeout and outputRetries{ "timeout": 300, "outputRetries": 2 }A skill package MUST contain manifest.json and SKILL.md at the archive root. The manifest MUST validate as a common manifest with type: "skill".
SKILL.md SHOULD begin with a YAML frontmatter block. For interoperable skill packages:
name SHOULD be present;description SHOULD be present; andCurrent ZIP parsing behavior treats a missing frontmatter name as invalid content. A missing frontmatter description is tolerated but SHOULD be avoided.
An extension package MUST contain manifest.json and at least one root-level .ts file. The validator selects the first root-level .ts file that is not a declaration file.
Normative structural constraints:
export default;name values MUST NOT be empty strings;execute MUST declare at least two parameters (toolCallId, params) or three (toolCallId, params, signal).Reference validator heuristics (informational — consumers MAY use different detection strategies):
pi.registerTool(...);{ content: [...] } is strongly recommended;A provider package is manifest-only. It MUST contain a definition object describing authentication mode and related metadata. It MAY additionally contain presentation fields such as displayName, description, iconUrl, categories, and docsUrl, plus an optional setupGuide.
definitionproviderauthMode{ "authMode": "oauth2", "authorizationUrl": "https://example.com/oauth/authorize", "tokenUrl": "https://example.com/oauth/token" }setupGuidecallbackUrlHint and optional steps{ "callbackUrlHint": "Set the redirect URI to ", "steps": [{ "label": "Create an OAuth app" }] }The following diagram illustrates how a flow composes its dependencies:
┌────────────────────────────────┐
│ @acme/customer-intake │
│ type: flow │
│ prompt.md (objective) │
└──────┬─────────────────────────┘
│
┌──────────────┼──────────────┐
│ │ │
▼ ▼ ▼
┌──────────────┐ ┌────────────┐ ┌────────────┐
│ @acme/gmail │ │ @acme/ │ │ @acme/ │
│ provider │ │ rewrite- │ │ http-tools │
│ (OAuth2) │ │ tone │ │ extension │
│ │ │ skill │ │ (.ts) │
└──────────────┘ └────────────┘ └────────────┘
requires requires requires
+ registryDeps + registryDeps + registryDeps
AFD distinguishes two dependency mechanisms that serve different audiences and operate at different times:
requires expresses runtime composition inside a flow package. It tells a flow runner which packages MUST be present when the flow executes. Values are opaque strings (typically exact versions or *). Only flow packages use requires.registryDependencies expresses installable registry dependencies for any package type. It tells a registry which packages to resolve and auto-install when a package is imported or published. Values MUST be valid semver ranges.The distinction exists because these mechanisms address different concerns:
| Aspect | requires |
registryDependencies |
|---|---|---|
| Scope | Flows only | All package types |
| Value format | Opaque strings (exact versions, *) |
Semver ranges (^1.0.0, ~2.1) |
| Audience | Flow runner / executor | Registry / installer |
| Timing | Runtime — validated at execution | Publish-time — resolved at installation |
| Purpose | “What must be loaded to run?” | “What must be installed to distribute?” |
For a typical flow, the same packages appear in both fields: registryDependencies ensures they can be installed from a registry, and requires ensures they are loaded at runtime. However, the two are not redundant:
registryDependencies but has no requires;require a package that is pre-installed in the runtime and does not need registry resolution;registryDependencies supports transitive dependency resolution and cycle detection, while requires is a flat declaration.The registryDependencies maps are the source of truth for dependency extraction and cycle detection.
Values under requires.providers, requires.skills, and requires.extensions are strings but are not semver-validated by the core manifest schema. For interoperability, producers SHOULD use exact versions or *.
Registries that automatically install provider dependencies for flows SHOULD require every provider listed in requires.providers to also appear in registryDependencies.providers.
When resolving a registry dependency:
Self-reference is a cycle. Transitive cycle detection SHOULD traverse registry dependencies breadth-first so that a registry can:
A cycle report SHOULD include the publishing package id and the discovered cycle path, for example:
@example/a -> @example/b -> @example/a
providersConfiguration is keyed by provider package id. The interoperable keys defined in AFD v1.0 are:
scopes: array of strings;connectionMode: user or admin.If connectionMode is omitted, many consumers treat it as user, but no manifest-level default is injected by validation.
AFD uses a constrained JSON-object schema model rather than the full JSON Schema vocabulary. The container schema MUST be an object with type: "object" and a properties record. Property definitions are intentionally small and extensible.
typestring, number, boolean, array, object, filestringdescriptionSearch querydefault20enum["en", "fr"]formatdate-time.date-timeplaceholderlabel:inbox newer_than:7daccepttype is file..pdf,.docxmaxSize10485760 (10 MB)multipletruemaxFilesmultiple is enabled.5An AFD schema container MUST have:
type: "object";properties object whose values are AFD property definitions.It MAY also contain:
required: an array of property names;propertyOrder: an array of property names used as a presentation hint. Listed properties SHOULD be rendered first, in the given order. Properties present in properties but absent from propertyOrder SHOULD be appended after the listed ones, in their natural object-key order.AFD v1.0 does not define nested property schemas, array item schemas, or full JSON Schema composition keywords. Properties with type: "object" or type: "array" are therefore shallow hints unless a consumer defines additional behavior.
Because the schema validator is extensible, consumers SHOULD preserve unknown property keywords that they do not understand.
input, output, and config all use the same wrapper shape:
{
"schema": {
"type": "object",
"properties": {}
}
}
The wrapper object is required when any of these sections are present. A bare schema object is not valid in those locations.
A flow package MUST include a non-empty prompt.md companion file. That file is the primary executable content of the archive.
A consumer MAY construct an execution context from:
prompt.md;input and config data;providersConfiguration.AFD does not define prompt templating, state persistence, scheduling, or transport semantics. Those concerns are out of scope.
execution.timeout is a numeric timeout hint expressed in seconds. execution.outputRetries is a numeric retry hint constrained to the inclusive range 0..5.
AFD v1.0 does not impose manifest-level defaults for either field. If a consumer chooses local defaults, it SHOULD document them separately from the manifest itself.
definition.authMode MUST be one of:
oauth2oauth1api_keybasiccustomFor oauth2 providers:
definition.authorizationUrl MUST be present;definition.tokenUrl MUST be present;definition.refreshUrl MAY be present;definition.defaultScopes MAY be present;definition.scopeSeparator MAY be present;definition.pkceEnabled MAY be present;definition.tokenAuthMethod MAY be present;definition.authorizationParams MAY be present; anddefinition.tokenParams MAY be present.For oauth1 providers:
definition.requestTokenUrl MUST be present;definition.accessTokenUrl MUST be present.For api_key, basic, and custom providers:
definition.credentialSchema MUST be present.The credentialSchema object SHOULD follow the AFD schema format defined in §5 (Schema System) — that is, type: "object" with a properties record — but the manifest validator accepts any JSON object. Each property defines a credential field the user must supply.
The optional fields credentialFieldName, credentialHeaderName, and credentialHeaderPrefix MAY be used to describe how credentials are transmitted.
authorizedUris MAY restrict which upstream URIs a provider is intended to access. allowAllUris MAY be used as an explicit override. If omitted, common consumers resolve allowAllUris as false.
setupGuide.callbackUrlHint MAY provide a human-facing callback hint, often including a placeholder such as ``.
setupGuide.steps MAY contain an ordered list of setup steps. Each step MUST have a label and MAY have a url.
For interoperability, availableScopes SHOULD be an array of objects with value and label keys, even though the manifest validator accepts any JSON values in that array.
AFD packages describe AI workflows that may access external services, process user data, and execute code. Implementers MUST consider the following threats.
ZIP archives are a well-known vector for path traversal and denial-of-service attacks. Consumers MUST:
.. path segments, absolute paths, null bytes, or backslash separators (see §2.4);Consumers SHOULD ignore __MACOSX/ directories and other platform-specific metadata entries.
Extension packages (§3.4) contain TypeScript source code that is loaded and executed by flow runners. This is the highest-risk surface in the AFD model:
Extension code that registers tools via registerTool() can access parameters supplied at runtime. Implementers MUST validate tool parameters before passing them to extension functions.
Provider packages (§3.5, §7) describe authentication configurations that involve OAuth tokens, API keys, and other secrets:
authorizedUris field (§7.5) SHOULD be enforced at runtime to prevent credential leakage to unintended endpoints;allowAllUris: true as a security-sensitive configuration and warn users accordingly.Flow packages include a prompt.md companion file whose content is typically sent to a language model. Malicious or compromised packages can embed prompt injection attacks:
input data before interpolating it into prompts;requires.Packages distributed through registries are subject to supply chain attacks including typosquatting, dependency confusion, and malicious updates:
Provider definitions include authorizedUris to restrict which upstream endpoints a provider can access:
allowAllUris is explicitly true;https://api.example.com/*) SHOULD be matched strictly — consumers MUST NOT allow pattern bypass via URL encoding, fragment injection, or open redirects.AFD packages may process personally identifiable information (PII) through flow inputs, provider connections, and execution outputs:
requires and providersConfiguration declarations;author field.Implementers operating in jurisdictions with data protection regulations (e.g., GDPR, CCPA) SHOULD consult their compliance requirements for the handling of user data within AI workflows.
AFD manifests and several nested objects (such as requires, execution, registryDependencies, and definition) accept additional fields beyond those defined in this specification. This design allows producers and consumers to experiment with new metadata without requiring a specification revision.
Fields that are not defined by this specification MUST use a name prefixed with x- followed by a vendor or project identifier, for example:
{
"name": "@example/my-flow",
"version": "1.0.0",
"type": "flow",
"x-acme-priority": "high",
"x-acme-cost-center": "engineering"
}
The x- prefix signals that the field is an extension and is not part of the normative AFD vocabulary. This convention:
Producers MUST NOT use the x- prefix for fields that are defined by this specification. Consumers MUST NOT reject manifests that contain x--prefixed fields. Consumers MAY ignore extension fields they do not understand.
When an extension field gains broad adoption across multiple implementations, it MAY be promoted to a standard field in a future specification revision. Upon promotion, the unprefixed field name becomes normative and the x--prefixed version becomes deprecated.
| Field | Context | Type | Requirement | Constraints / Notes | Default |
|---|---|---|---|---|---|
name |
all manifests | string | MUST | scoped name | none |
version |
all manifests | string | MUST | valid semver version | none |
type |
all manifests | string | MUST | flow\|skill\|extension\|provider |
none |
displayName |
all manifests | string | MUST for flow; SHOULD for skill, extension, and provider | flow value min length 1 | none |
description |
all manifests | string | MAY | free text | none |
keywords |
all manifests | string[] | MAY | arbitrary strings | none |
license |
all manifests | string | MAY | free text | none |
repository |
all manifests | string | MAY | URI recommended | none |
registryDependencies |
all manifests | object | MAY | optional dependency maps | none |
registryDependencies.skills |
all manifests | map | MAY | keys scoped names, values valid semver ranges | none |
registryDependencies.extensions |
all manifests | map | MAY | keys scoped names, values valid semver ranges | none |
registryDependencies.providers |
all manifests | map | MAY | keys scoped names, values valid semver ranges | none |
author |
flow | string | MUST | free text | none |
requires |
flow | object | MUST | optional providers, skills, extensions maps |
none |
requires.providers |
flow | map | MAY | keys scoped names, values opaque strings | none |
requires.skills |
flow | map | MAY | keys scoped names, values opaque strings | none |
requires.extensions |
flow | map | MAY | keys scoped names, values opaque strings | none |
providersConfiguration |
flow | map | MAY | keyed by provider id | none |
providersConfiguration.<id>.scopes |
flow | string[] | MAY | requested scopes | none |
providersConfiguration.<id>.connectionMode |
flow | string | MAY | user\|admin |
consumer-defined |
input |
flow | object | MAY | requires schema child |
none |
input.schema |
flow | object | MUST if input present |
AFD schema object | none |
output |
flow | object | MAY | requires schema child |
none |
output.schema |
flow | object | MUST if output present |
AFD schema object | none |
config |
flow | object | MAY | requires schema child |
none |
config.schema |
flow | object | MUST if config present |
AFD schema object | none |
execution |
flow | object | MAY | extensible | none |
schemaVersion |
all manifests | string | MUST for flow; MAY for all others | MAJOR.MINOR format; producers MUST emit 1.0 for this draft |
none |
execution.timeout |
flow | number | MAY | numeric timeout hint, in seconds | none |
execution.outputRetries |
flow | number | MAY | integer, inclusive range 0..5 |
none |
definition |
provider | object | MUST | extensible; contains auth metadata | none |
definition.authMode |
provider | string | MUST | oauth2\|oauth1\|api_key\|basic\|custom |
none |
definition.authorizationUrl |
provider | string | MUST for oauth2 | URI recommended | none |
definition.tokenUrl |
provider | string | MUST for oauth2 | URI recommended | none |
definition.refreshUrl |
provider | string | MAY | URI recommended | consumer-defined |
definition.defaultScopes |
provider | string[] | MAY | default requested scopes | consumer-defined |
definition.scopeSeparator |
provider | string | MAY | OAuth scope separator | consumer-defined |
definition.pkceEnabled |
provider | boolean | MAY | PKCE flag | consumer-defined |
definition.tokenAuthMethod |
provider | string | MAY | token endpoint auth hint | none |
definition.authorizationParams |
provider | object | MAY | free-form parameter map | consumer-defined |
definition.tokenParams |
provider | object | MAY | free-form parameter map | consumer-defined |
definition.credentialSchema |
provider | object | MUST for api_key, basic, custom |
SHOULD follow AFD schema format; validator accepts any object | none |
definition.credentialFieldName |
provider | string | MAY | logical credential field | none |
definition.credentialHeaderName |
provider | string | MAY | HTTP header name | none |
definition.credentialHeaderPrefix |
provider | string | MAY | HTTP header prefix | none |
definition.authorizedUris |
provider | string[] | MAY | allowed upstream URI patterns | none |
definition.allowAllUris |
provider | boolean | MAY | unrestricted upstream access | consumer-defined |
definition.requestTokenUrl |
provider | string | MUST for oauth1 | URI recommended | none |
definition.accessTokenUrl |
provider | string | MUST for oauth1 | URI recommended | none |
definition.availableScopes |
provider | array | MAY | interoperable form is { value, label }[] |
none |
iconUrl |
provider | string | MAY | URI recommended | none |
categories |
provider | string[] | MAY | arbitrary strings | consumer-defined |
docsUrl |
provider | string | MAY | URI recommended | none |
setupGuide |
provider | object | MAY | setup metadata | none |
setupGuide.callbackUrlHint |
provider | string | MAY | callback placeholder text | none |
setupGuide.steps |
provider | object[] | MAY | ordered setup steps | none |
setupGuide.steps[].label |
provider | string | MUST if step present | non-empty recommended | none |
setupGuide.steps[].url |
provider | string | MAY | URI recommended | none |
SKILL.md frontmatter name |
skill content | string | SHOULD | current ZIP parser requires it | none |
SKILL.md frontmatter description |
skill content | string | SHOULD | missing value warns | none |
root .ts source file |
extension content | file | MUST | root-level, not .d.ts |
none |
export default |
extension content | source construct | MUST | required by validator | none |
registerTool().name |
extension content | string | SHOULD | empty string invalid | none |
execute |
extension content | function | SHOULD | 2 or 3 params recommended; 1 param invalid | none |
x-* |
any extensible object | any | MAY | extension fields MUST use x- prefix (§10) |
none |
SLUG_PATTERN = [a-z0-9]([a-z0-9-]*[a-z0-9])?
SLUG_REGEX = ^[a-z0-9]([a-z0-9-]*[a-z0-9])?$
SCOPED_NAME_REGEX = ^@[a-z0-9]([a-z0-9-]*[a-z0-9])?\/[a-z0-9]([a-z0-9-]*[a-z0-9])?$
SCHEMA_VERSION_REGEX = ^(0|[1-9][0-9]*)\.(0|[1-9][0-9]*)$
EXTENSION_FIELD = ^x-.+$
Semantic-version and range validation are delegated to semver parsing functions rather than regexes.
AFD v1.0 validation does not inject manifest defaults. Omitted optional fields remain omitted.
Common consumer-side defaults observed in interoperable implementations include:
| Field | Resolved default | Notes |
|---|---|---|
definition.authMode |
oauth2 |
provider resolution default when absent in raw extraction |
definition.defaultScopes |
[] |
resolved provider definition |
definition.scopeSeparator |
" " |
resolved provider definition |
definition.pkceEnabled |
true |
resolved provider definition |
definition.authorizationParams |
{} |
resolved provider definition |
definition.tokenParams |
{} |
resolved provider definition |
definition.allowAllUris |
false |
resolved provider definition |
categories |
[] |
resolved provider definition |
providersConfiguration.<id>.connectionMode |
user |
common runtime/editor default |
schemaVersion |
1.0 |
common editor default for new flows |
execution.timeout |
300 |
common editor default for new flows |
execution.outputRetries |
2 |
common editor default for new flows |
These defaults are non-normative unless a producer explicitly writes them into the manifest.
This draft was extracted from the Appstrate reference implementation, primarily:
core/src/validation.tscore/src/naming.tscore/src/dependencies.tscore/src/semver.tscore/src/zip.tsregistry/apps/api/src/services/dependencies.tsThe examples in this repository are intended to remain valid against that implementation’s validateManifest() and related package-content validators.