Documentation
¶
Overview ¶
Package pack provides the build pipeline, SBOM, signing, and secret scanning.
Index ¶
- Constants
- Variables
- func CleanupLocalRegistry(ctx context.Context) error
- func ComputeBuildInputDigest(projectDir string, ignore *IgnoreMatcher) (string, error)
- func ComputeBuildInputDigestFromFiles(files []BuildFile) (string, error)
- func ComputePolicyDigest(yamlBytes []byte) (string, error)
- func ContainsExportSentinel(data []byte) bool
- func CreateBuildContext(projectDir string, ignore *IgnoreMatcher) (io.Reader, error)
- func DefaultAgentPaasIgnore() string
- func DefaultAgentYAML(runtime RuntimeType, projectName string) string
- func DefaultIgnorePatterns() []string
- func DefaultMainPy() string
- func DefaultPolicyYAML() string
- func DeployedAgentPath(homeDir, agentName string) string
- func EnsureLocalRegistry(ctx context.Context) (string, error)
- func FormatProvenance(report *ProvenanceReport) string
- func GenerateSBOM(ctx context.Context, imageRef string) (sbom []byte, digest string, err error)
- func InitFromCode(projectDir string, runtime RuntimeType) error
- func InitPolicy(projectDir string) error
- func InitScaffold(projectDir string, runtime RuntimeType) error
- func IsDeployed(homeDir, agentName string) bool
- func IsRegistryPortConflict(err error) bool
- func LoadPolicy(projectDir string) (*policy.Policy, error)
- func LocalImageRef(agentName, imageDigest string) string
- func LockDigest(lock *AgentLock) string
- func LockfileCanonicalJSON(lock *AgentLock) ([]byte, error)
- func PublicKeyFingerprint(pub *ecdsa.PublicKey) string
- func PublicKeyFromPEM(pemBytes []byte) (*ecdsa.PublicKey, error)
- func PushImageToLocalRegistry(ctx context.Context, sourceTag, agentName, agentVersion string) (string, error)
- func RecordDeployment(homeDir, agentName string, lock *AgentLock) error
- func RepairHint(err *OCILayoutError) string
- func ResolveDependencies(ctx context.Context, projectDir string, runtime RuntimeType) ([]string, error)
- func SignImage(ctx context.Context, imageRef string, keyPath string) (referrer string, err error)
- func SignLockfileWithKey(lock *AgentLock, key *ecdsa.PrivateKey) error
- func SignProvenanceEntryWithKey(e *ProvenanceEntry, key *ecdsa.PrivateKey) error
- func SignPublisherWithKey(lock *AgentLock, key *ecdsa.PrivateKey) error
- func ValidateLLMEgress(agentConfig *AgentYAML, policyFile *policy.Policy) error
- func ValidateOCILayout(layoutPath string) error
- func VerifyAgentLock(lock *AgentLock, imageRef string) error
- func VerifyBuildOutput(ctx context.Context, imageRef string, cfg BuildConfig) error
- func VerifyDeployedIntegrity(homeDir, agentName string, auditAppender audit.AuditAppender) error
- func VerifyLineageParentProvenance(parent *LineageParent) error
- func VerifyLockfileSignature(lock *AgentLock) error
- func VerifyProvenanceSignatures(lock *AgentLock) error
- func VerifyPublisherSignature(lock *AgentLock) error
- func WriteAgentLock(lock *AgentLock, path string) error
- type AdvisoryFinding
- type AdvisoryReport
- type AgentLock
- func CreateAgentLock(ctx context.Context, cfg LockConfig) (*AgentLock, error)
- func LoadDeployedLock(homeDir, agentName string) (*AgentLock, error)
- func NewSignedTestLock(agentName string, policyYAML []byte) (*AgentLock, error)
- func NewSignedTestLockWithLLM(agentName string, policyYAML []byte, llmCredentialName string) (*AgentLock, error)
- func ReadAgentLock(path string) (*AgentLock, error)
- type AgentYAML
- type AuditAppender
- type BuildConfig
- type BuildFile
- type BuildResult
- type DeployedAgent
- type DetectionResult
- type IgnoreMatcher
- type LLMConfig
- type LineageFile
- type LineageParent
- type LockConfig
- type OCILayoutError
- type PolicyDelta
- type ProvenanceEntry
- type ProvenanceEntrySummary
- type ProvenanceReport
- type PublisherInfo
- type ReproducibilityMeta
- type RuntimeType
- type ScanConfig
- type ScanResult
- type SecretFinding
- type VerificationResult
Constants ¶
const ( AdvisorySeverityCritical = "CRITICAL" AdvisorySeverityHigh = "HIGH" AdvisorySeverityMedium = "MEDIUM" AdvisorySeverityLow = "LOW" AdvisorySeverityNone = "NONE" )
AdvisorySeverity levels for OSV findings.
const LockSchemaVersion = 2
LockSchemaVersion is the current agent.lock schema version.
Variables ¶
var ErrImmutableViolation = errors.New("immutable violation: deployed agent artifacts cannot be modified in place")
ErrImmutableViolation is returned when an in-place mutation of a deployed agent artifact is attempted.
var ErrLineageNotFound = errors.New("lineage.json not found")
ErrLineageNotFound indicates lineage.json is absent from the project directory.
var ErrOCILayoutCorrupt = errors.New("local OCI layout is missing or corrupt")
ErrOCILayoutCorrupt is returned when the local OCI layout is missing or corrupt.
Functions ¶
func CleanupLocalRegistry ¶
CleanupLocalRegistry stops and removes the agentpaas-registry test container.
func ComputeBuildInputDigest ¶
func ComputeBuildInputDigest(projectDir string, ignore *IgnoreMatcher) (string, error)
ComputeBuildInputDigest computes SHA-256 over the canonical build context. Canonical = sorted file paths (relative to ProjectDir, forward slashes) + each file's content. Respects .agentpaasignore exclusions. Symlink-safe: uses os.Lstat, rejects symlinks.
func ComputeBuildInputDigestFromFiles ¶ added in v0.2.0
ComputeBuildInputDigestFromFiles computes SHA-256 over the canonical build context represented by sorted BuildFile entries (path, size, content). Shared by pack and bundle verification — do not duplicate this logic.
func ComputePolicyDigest ¶ added in v0.2.0
ComputePolicyDigest parses, validates, and computes the SHA-256 digest of the policy YAML. Returns empty string if yamlBytes is nil/empty (no policy in project — backward compat). Returns error if parsing fails or validation finds errors.
func ContainsExportSentinel ¶ added in v0.2.0
ContainsExportSentinel reports whether data contains the red-team sentinel string.
func CreateBuildContext ¶
func CreateBuildContext(projectDir string, ignore *IgnoreMatcher) (io.Reader, error)
CreateBuildContext creates a deterministic tar reader of the build context. Files are added in sorted path order. Uses ignore matcher to exclude files. Symlink-safe.
func DefaultAgentPaasIgnore ¶
func DefaultAgentPaasIgnore() string
DefaultAgentPaasIgnore returns the default .agentpaasignore content.
func DefaultAgentYAML ¶
func DefaultAgentYAML(runtime RuntimeType, projectName string) string
DefaultAgentYAML returns the minimal agent.yaml content for scaffolding. The agent name is derived from the project directory basename.
func DefaultIgnorePatterns ¶
func DefaultIgnorePatterns() []string
DefaultIgnorePatterns returns the default exclude patterns used when .agentpaasignore is absent.
func DefaultMainPy ¶
func DefaultMainPy() string
DefaultMainPy returns the default main.py entry point stub. Uses the AgentPaaS SDK @agent.on_invoke pattern — plain app()/main() functions will NOT work with the harness.
func DefaultPolicyYAML ¶ added in v0.1.1
func DefaultPolicyYAML() string
DefaultPolicyYAML returns a default-deny policy.yaml — no egress allowed until the agent onboarding flow adds explicit domain rules.
func DeployedAgentPath ¶
DeployedAgentPath returns the deployed agent state directory.
func EnsureLocalRegistry ¶
EnsureLocalRegistry ensures a local OCI registry is running and returns its URL.
func FormatProvenance ¶ added in v0.2.0
func FormatProvenance(report *ProvenanceReport) string
FormatProvenance renders a ProvenanceReport as a terminal-display string.
func GenerateSBOM ¶
GenerateSBOM runs syft to produce an SPDX-json SBOM for the built image. Returns the SBOM content and its SHA-256 digest.
func InitFromCode ¶
func InitFromCode(projectDir string, runtime RuntimeType) error
InitFromCode reconciles an agent.yaml from existing source files. If agent.yaml exists, it is left untouched. If not, a minimal one is created with the detected runtime and agent name derived from the dir.
func InitPolicy ¶
InitPolicy writes a minimal default-deny policy.yaml if one does not exist. If policy.yaml already exists, it is left untouched (never overwrite policy).
func InitScaffold ¶
func InitScaffold(projectDir string, runtime RuntimeType) error
InitScaffold creates a new agent project in the given directory. If the directory does not exist, it is created. If agent.yaml already exists, return an error (don't overwrite). Files created:
- agent.yaml (minimal template with name, version, runtime)
- main.py (entry point stub using @agent.on_invoke SDK pattern)
- requirements.txt (empty, with a comment)
- .agentpaasignore (default excludes)
Policy is created separately by InitPolicy or `policy init`.
func IsDeployed ¶
IsDeployed returns true if the agent has been deployed.
func IsRegistryPortConflict ¶
IsRegistryPortConflict reports whether err indicates the configured registry host port is already bound by a non-agentpaas process.
func LoadPolicy ¶ added in v0.2.0
LoadPolicy reads and parses policy.yaml from the project directory. Returns nil, nil if policy.yaml does not exist (not an error).
func LocalImageRef ¶
LocalImageRef returns a digest-pinned image ref for the local registry.
func LockDigest ¶ added in v0.2.0
LockDigest returns the SHA-256 digest of the full canonical lockfile JSON including both signatures. This is the value that fork entries reference as parent_lock_digest.
func LockfileCanonicalJSON ¶ added in v0.2.0
LockfileCanonicalJSON returns canonical JSON bytes for agent.lock as stored in bundles.
func PublicKeyFingerprint ¶
PublicKeyFingerprint computes the SHA-256 fingerprint of a public key.
func PublicKeyFromPEM ¶
PublicKeyFromPEM parses a PEM-encoded ECDSA P-256 public key.
func PushImageToLocalRegistry ¶
func PushImageToLocalRegistry(ctx context.Context, sourceTag, agentName, agentVersion string) (string, error)
PushImageToLocalRegistry tags and pushes a locally built image to the local registry, returning a digest-pinned image ref suitable for cosign signing.
func RecordDeployment ¶
RecordDeployment writes the deployed agent metadata to disk atomically.
func RepairHint ¶
func RepairHint(err *OCILayoutError) string
RepairHint returns a human-readable repair hint for the given OCILayoutError.
func ResolveDependencies ¶
func ResolveDependencies(ctx context.Context, projectDir string, runtime RuntimeType) ([]string, error)
ResolveDependencies runs uv to lock dependencies. For requirements.txt: `uv pip compile requirements.txt -o /tmp/locked.txt` For pyproject.toml: `uv lock` Returns the list of locked package@version strings. Returns error with verbatim uv output on conflict.
func SignImage ¶
SignImage signs the built image with cosign using the package identity key. Returns the signature referrer path.
func SignLockfileWithKey ¶ added in v0.2.0
func SignLockfileWithKey(lock *AgentLock, key *ecdsa.PrivateKey) error
SignLockfileWithKey sets lockfile_signature on lock using the package AID private key. The lock must have LockfileSignature cleared before calling. Intended for tests and bundle fixtures that mutate lock fields after creation.
func SignProvenanceEntryWithKey ¶ added in v0.2.0
func SignProvenanceEntryWithKey(e *ProvenanceEntry, key *ecdsa.PrivateKey) error
SignProvenanceEntryWithKey sets entry_signature on e using the publisher private key. Intended for tests and bundle fixtures.
func SignPublisherWithKey ¶ added in v0.2.0
func SignPublisherWithKey(lock *AgentLock, key *ecdsa.PrivateKey) error
SignPublisherWithKey sets publisher_signature on lock using the publisher private key. The lock must have a publisher block. Intended for tests and bundle fixtures.
func ValidateLLMEgress ¶ added in v0.2.0
ValidateLLMEgress checks that if the agent has an LLM provider configured, the provider's domain is present in the egress policy. This is a hard error at pack time — the agent WILL fail at runtime without the egress.
Returns nil if: - The agent has no LLM provider configured - The LLM provider's domain is present in the egress policy - The LLM provider is unknown (non-standard provider)
Returns an error if: - The LLM provider's domain is NOT in the egress policy
func ValidateOCILayout ¶
ValidateOCILayout checks that a local OCI layout directory is valid.
func VerifyAgentLock ¶
VerifyAgentLock verifies an agent.lock manifest.
func VerifyBuildOutput ¶ added in v0.2.1
func VerifyBuildOutput(ctx context.Context, imageRef string, cfg BuildConfig) error
VerifyBuildOutput runs post-build verification on a built agent image. It checks that all required components are present and functional. Returns nil if all checks pass, or an error describing the first failure.
func VerifyDeployedIntegrity ¶
func VerifyDeployedIntegrity(homeDir, agentName string, auditAppender audit.AuditAppender) error
VerifyDeployedIntegrity checks that the deployed agent.lock and image.digest on disk have NOT been modified since deployment.
func VerifyLineageParentProvenance ¶ added in v0.2.0
func VerifyLineageParentProvenance(parent *LineageParent) error
VerifyLineageParentProvenance checks structural rules and signatures for the embedded parent provenance chain. The last entry signer must match parent.PublisherFingerprint (parent lock tail rule, not the new lock).
func VerifyLockfileSignature ¶
VerifyLockfileSignature verifies the lockfile's ECDSA signature against the AID public key embedded in the lockfile.
func VerifyProvenanceSignatures ¶ added in v0.2.0
VerifyProvenanceSignatures verifies that each provenance entry's entry_signature is valid against its publisher's public key. This checks the integrity of each provenance entry independently.
func VerifyPublisherSignature ¶ added in v0.2.0
VerifyPublisherSignature verifies the publisher signature in a v2+ lockfile. It verifies the ECDSA signature over the canonical JSON (excluding both lockfile_signature and publisher_signature) using the publisher's public key.
func WriteAgentLock ¶
WriteAgentLock writes the agent.lock manifest as canonical JSON to a file.
Types ¶
type AdvisoryFinding ¶
type AdvisoryFinding struct {
ID string `json:"id"`
Package string `json:"package"`
Version string `json:"version"`
Severity string `json:"severity"`
Summary string `json:"summary"`
FixedIn string `json:"fixed_in,omitempty"`
References []string `json:"references,omitempty"`
}
AdvisoryFinding represents a single OSV advisory.
type AdvisoryReport ¶
type AdvisoryReport struct {
Total int `json:"total"`
Critical int `json:"critical"`
High int `json:"high"`
Medium int `json:"medium"`
Low int `json:"low"`
Findings []AdvisoryFinding `json:"findings"`
Scanned bool `json:"scanned"`
RawOutput string `json:"raw_output,omitempty"`
}
AdvisoryReport is the summary of OSV scan results.
func ScanAdvisories ¶
func ScanAdvisories(ctx context.Context, sbomPath string) (*AdvisoryReport, error)
ScanAdvisories runs osv-scanner on the SBOM and returns an advisory summary.
func (*AdvisoryReport) ShouldFailBuild ¶
func (r *AdvisoryReport) ShouldFailBuild(failOnCritical bool) bool
ShouldFailBuild returns true when configured critical/high advisories exist.
func (*AdvisoryReport) Summary ¶
func (r *AdvisoryReport) Summary() string
Summary returns a human-readable summary string for CLI output.
type AgentLock ¶
type AgentLock struct {
// SBOM is the generated SPDX document retained for bundle export. It is
// deployed as a sidecar and intentionally excluded from signed JSON.
SBOM []byte `json:"-"`
// SchemaVersion is the agent.lock schema version (currently 1).
SchemaVersion int `json:"schema_version"`
// AgentName is the agent name from agent.yaml.
AgentName string `json:"agent_name"`
// AgentVersion is the agent version from agent.yaml.
AgentVersion string `json:"agent_version"`
// Runtime is the detected/explicit runtime type (python, langgraph, crewai).
Runtime string `json:"runtime"`
// Platform is the target platform (e.g. "linux/arm64").
Platform string `json:"platform"`
// BaseImageDigest is the digest-pinned distroless base image.
BaseImageDigest string `json:"base_image_digest"`
// HarnessVersion is the version of the harness binary embedded as PID 1.
HarnessVersion string `json:"harness_version"`
// BuildInputDigest is the SHA-256 over the canonical build context.
BuildInputDigest string `json:"build_input_digest"`
// ImageDigest is the SHA-256 digest of the built OCI image.
ImageDigest string `json:"image_digest"`
// SBOMDigest is the SHA-256 digest of the SBOM (SPDX-json).
SBOMDigest string `json:"sbom_digest"`
// PolicyDigest is the SHA-256 digest of the policy.yaml.
// Computed at pack time from the project's policy.yaml.
PolicyDigest string `json:"policy_digest"`
// PolicyYAML is the raw policy.yaml content. Stored in the deployed directory
// as a separate file (NOT in the signed lockfile JSON — it would change the
// canonical signature map). Used at run time to compile the gateway config.
// NOT included in lockCanonicalMap — it is deployed as a sidecar file.
PolicyYAML []byte `json:"policy_yaml,omitempty"`
// PackageAID is the Agent Identity Document - the public key PEM.
PackageAID string `json:"package_aid"`
// PublicKeyFingerprint is the SHA-256 fingerprint of the public key.
PublicKeyFingerprint string `json:"public_key_fingerprint"`
// SBOMReferrer is the OCI referrer path for the SBOM artifact.
SBOMReferrer string `json:"sbom_referrer,omitempty"`
// SignatureReferrer is the OCI referrer path for the cosign signature.
SignatureReferrer string `json:"signature_referrer,omitempty"`
// Reproducibility holds build reproducibility metadata.
Reproducibility ReproducibilityMeta `json:"reproducibility"`
// LockfileSignature is the ECDSA signature over the canonical JSON
// of this struct (with LockfileSignature omitted). Base64-encoded.
LockfileSignature string `json:"lockfile_signature"`
// CreatedAt is the wall-clock time the lockfile was created.
// For reproducibility, this is set to SOURCE_DATE_EPOCH, not time.Now().
CreatedAt time.Time `json:"created_at"`
// AgentYAML is the parsed agent.yaml (including LLM config). Stored as part
// of the lockfile for runtime LLM credential resolution. nil when absent.
AgentYAML *AgentYAML `json:"agent_yaml,omitempty"`
// Publisher holds the publisher identity block (schema v2+). nil when
// the pack was performed without a publisher identity (local-only pack).
Publisher *PublisherInfo `json:"publisher,omitempty"`
// PublisherSignature is the ECDSA signature over the canonical JSON
// of the lock (excluding both lockfile_signature and publisher_signature),
// signed by the publisher identity key. Base64-encoded. Empty when no
// publisher identity is configured.
PublisherSignature string `json:"publisher_signature,omitempty"`
// Provenance is the ordered list of provenance entries recording the
// full lifecycle of this lockfile (created, updated, etc.). Empty for
// local-only packs or pre-v2 schema. Each entry carries its own
// signature from the publisher that created it.
Provenance []ProvenanceEntry `json:"provenance,omitempty"`
}
AgentLock is the canonical, signed manifest for a packed agent. This is the exact review unit consumed by `agent run` and promotion.
func CreateAgentLock ¶
func CreateAgentLock(ctx context.Context, cfg LockConfig) (*AgentLock, error)
CreateAgentLock creates the canonical, signed agent.lock manifest.
func LoadDeployedLock ¶ added in v0.2.0
LoadDeployedLock reads the deployed agent.lock from disk.
func NewSignedTestLock ¶ added in v0.2.0
NewSignedTestLock generates an ECDSA P-256 key pair and creates a signed AgentLock with the given agent name and optional policy YAML bytes. If policyYAML is non-empty, it is parsed, validated, and its canonical digest is stored in lock.PolicyDigest. The PolicyYAML sidecar is NOT set on the lock — callers must write it separately via RecordDeployment.
This is exported for use by external test packages (e.g., internal/daemon).
func NewSignedTestLockWithLLM ¶ added in v0.2.0
func NewSignedTestLockWithLLM(agentName string, policyYAML []byte, llmCredentialName string) (*AgentLock, error)
NewSignedTestLockWithLLM creates a signed test lock that includes an AgentYAML with an LLM credential. This is for testing installed-agent flows where the signed lock's LLM credential must be present.
func ReadAgentLock ¶
ReadAgentLock reads and parses an agent.lock file.
type AgentYAML ¶
type AgentYAML struct {
Name string `yaml:"name"`
Version string `yaml:"version"`
Runtime string `yaml:"runtime"`
Entry string `yaml:"entry"`
Description string `yaml:"description"`
LLM LLMConfig `yaml:"llm"`
Metadata struct {
Name string `yaml:"name"`
Version string `yaml:"version"`
Description string `yaml:"description"`
} `yaml:"metadata"`
Spec struct {
Runtime string `yaml:"runtime"`
Entrypoint string `yaml:"entrypoint"`
Entry string `yaml:"entry"`
} `yaml:"spec"`
}
AgentYAML is a minimal subset of agent.yaml fields needed for detection and packaging. The runtime field overrides auto-detection. Both flat fields and the v1 metadata/spec schema are supported.
func LoadAgentYAML ¶
LoadAgentYAML reads and parses agent.yaml from the project directory. Returns nil, nil if agent.yaml does not exist (not an error).
type AuditAppender ¶
type AuditAppender = audit.AuditAppender
AuditAppender is implemented by audit sinks that accept audit records.
type BuildConfig ¶
type BuildConfig struct {
// ProjectDir is the agent project directory to build.
ProjectDir string
// Runtime is the detected/explicit runtime type.
Runtime RuntimeType
// BaseImage is the distroless base image ref (digest-pinned).
// Default: "gcr.io/distroless/python3-debian12@sha256:2fdb05402a2cf21cf78fdb3ba4c5db167241e9e498140f5bf689d7efb773731f"
BaseImage string
// BuilderImage is the image used to install Python deps in a multi-stage build.
// Default: "python:3.11-slim"
BuilderImage string
// HarnessPath is the path to the pre-built harness binary to embed as PID 1.
// If empty, uses the standard harness binary location.
HarnessPath string
// SDKDir is the path to the Python SDK directory to embed. If empty, uses the standard location.
SDKDir string
// SourceDateEpoch is the fixed timestamp for reproducible builds.
// Default: time.Unix(0, 0) (epoch).
SourceDateEpoch time.Time
// NonRootUID is the uid for the non-root user. Default: 64000.
NonRootUID int
// ImageTag is the tag for the built image (e.g. "agentpaas/myagent:0.1.0").
ImageTag string
}
BuildConfig controls the image build process.
type BuildFile ¶ added in v0.2.0
BuildFile represents a collected file from the build context.
func CollectBuildFiles ¶ added in v0.2.0
func CollectBuildFiles(projectDir string, ignore *IgnoreMatcher) ([]BuildFile, error)
CollectBuildFiles walks projectDir and returns all regular files that are not excluded by the ignore matcher. Files are returned sorted by relative path. Symlinks are rejected. If ignore is nil, it falls back to LoadIgnore(projectDir).
type BuildResult ¶
type BuildResult struct {
ImageDigest string `json:"image_digest"`
ImageRef string `json:"image_ref"`
BuildTime time.Time `json:"build_time"`
// BuildInputDigest is the SHA-256 over the canonical build context
// (sorted file list + file contents). Same input -> same digest -> same image.
BuildInputDigest string `json:"build_input_digest"`
// DepsLocked is the resolved/locked dependency list from uv.
DepsLocked []string `json:"deps_locked"`
}
BuildResult holds the outcome of an image build.
func BuildImage ¶
func BuildImage(ctx context.Context, cfg BuildConfig) (*BuildResult, error)
BuildImage builds a deterministic OCI image for the agent project.
type DeployedAgent ¶
type DeployedAgent struct {
AgentName string `json:"agent_name"`
ImageDigest string `json:"image_digest"`
SourceDigest string `json:"source_digest"`
LockfileSig string `json:"lockfile_signature"`
DeployedAt time.Time `json:"deployed_at"`
}
DeployedAgent is the metadata of a deployed agent on disk.
func LoadDeployedAgent ¶
func LoadDeployedAgent(homeDir, agentName string) (*DeployedAgent, error)
LoadDeployedAgent reads the deployed agent metadata from disk. Returns os.ErrNotExist if the agent was never deployed.
type DetectionResult ¶
type DetectionResult struct {
Runtime RuntimeType `json:"runtime"`
HasAgentYAML bool `json:"has_agent_yaml"`
ProjectDir string `json:"project_dir"`
ExplicitRuntime bool `json:"explicit_runtime"`
}
DetectionResult holds the outcome of project type detection.
func DetectProject ¶
func DetectProject(projectDir string) (*DetectionResult, error)
DetectProject examines a project directory and returns the runtime type. If agent.yaml exists and has a runtime: field, that overrides detection. Otherwise, scan requirements.txt, pyproject.toml, and .py files for langgraph or crewai imports.
type IgnoreMatcher ¶
type IgnoreMatcher struct {
// contains filtered or unexported fields
}
IgnoreMatcher implements .agentpaasignore pattern matching. It supports:
- Exact filename matches (e.g. ".git")
- Glob patterns (e.g. "*.pyc", "__pycache__")
- Directory patterns (e.g. "node_modules/")
- Comments (lines starting with #)
- Negation patterns (lines starting with !)
func LoadIgnore ¶
func LoadIgnore(projectDir string) (*IgnoreMatcher, error)
LoadIgnore reads .agentpaasignore from projectDir and returns a matcher. Default patterns (including build artifacts like *.agentpaas) are ALWAYS applied, then user patterns are appended on top. This ensures build artifacts never contaminate the source context even when the user's .agentpaasignore doesn't list them.
func NewIgnoreMatcher ¶
func NewIgnoreMatcher(content string) *IgnoreMatcher
NewIgnoreMatcher creates a matcher from the given .agentpaasignore content.
func (*IgnoreMatcher) Match ¶
func (m *IgnoreMatcher) Match(filePath string) bool
Match returns true if the given path should be ignored (excluded from build context).
type LLMConfig ¶
type LLMConfig struct {
Provider string `yaml:"provider"` // openai|anthropic|xai
Model string `yaml:"model"` // e.g. "gpt-4o", "claude-sonnet-4", "grok-beta"
Credential string `yaml:"credential"` // Keychain secret name (e.g. "openai-key")
}
LLMConfig defines the LLM provider and credential binding for the agent. This is used by the harness to route agent.llm() calls through the gateway as credentialed HTTP egress (Option B unified egress).
type LineageFile ¶ added in v0.2.0
type LineageFile struct {
Version int `json:"version"`
Parent LineageParent `json:"parent"`
ForkedAt string `json:"forked_at"`
}
LineageFile is the fork lineage record written beside an editable project.
func ReadLineage ¶ added in v0.2.0
func ReadLineage(projectDir string) (*LineageFile, error)
ReadLineage parses lineage.json from projectDir when present.
type LineageParent ¶ added in v0.2.0
type LineageParent struct {
AgentName string `json:"agent_name"`
AgentVersion string `json:"agent_version"`
PublisherFingerprint string `json:"publisher_fingerprint"`
PublisherName string `json:"publisher_name"`
LockDigest string `json:"lock_digest"`
BundleDigest string `json:"bundle_digest"`
PolicyDigest string `json:"policy_digest"`
PolicyYAMLB64 string `json:"policy_yaml_b64"`
Provenance []ProvenanceEntry `json:"provenance"`
}
LineageParent captures installed parent lock metadata for fork-aware pack.
type LockConfig ¶
type LockConfig struct {
// BuildResult is the result from BuildImage (T02).
BuildResult *BuildResult
// ScanResult is the result from ScanSecrets (T03).
ScanResult *ScanResult
// AgentYAML is the parsed agent.yaml.
AgentYAML *AgentYAML
// Runtime is the detected runtime type.
Runtime RuntimeType
// BaseImageDigest is the digest-pinned base image.
BaseImageDigest string
// HarnessVersion is the harness binary version.
HarnessVersion string
// Platform is the target platform.
Platform string
// SourceDateEpoch is the fixed timestamp.
SourceDateEpoch time.Time
// KeyStore is the identity keystore for package identity key signing.
KeyStore identityKeyStore
// KeyID is the package identity key ID to use for signing.
KeyID string
// PolicyYAML is the raw policy.yaml file contents. If nil/empty (no policy.yaml
// in the project), the lockfile's PolicyDigest is left empty for backward compat.
PolicyYAML []byte
// PublisherKeyStore is the identity keystore for publisher identity
// operations (signing the publisher block and provenance entries). If nil,
// the lock is produced without a publisher block (local-only pack).
// This may be the same underlying store as KeyStore since the identity
// keystore holds all key types.
PublisherKeyStore identity.KeyStore
// ProjectDir is the agent project directory; used to detect lineage.json
// for fork-aware provenance chain append.
ProjectDir string
}
LockConfig controls the agent.lock generation process.
type OCILayoutError ¶
OCILayoutError provides an actionable repair hint when the OCI layout is missing or corrupt.
func (*OCILayoutError) Error ¶
func (e *OCILayoutError) Error() string
func (*OCILayoutError) Is ¶
func (e *OCILayoutError) Is(target error) bool
func (*OCILayoutError) Unwrap ¶
func (e *OCILayoutError) Unwrap() error
type PolicyDelta ¶ added in v0.2.0
type PolicyDelta struct {
// EgressAdded is the list of egress destinations added.
EgressAdded []string `json:"egress_added,omitempty"`
// EgressRemoved is the list of egress destinations removed.
EgressRemoved []string `json:"egress_removed,omitempty"`
// CredentialsAdded is the list of credential names added.
CredentialsAdded []string `json:"credentials_added,omitempty"`
// CredentialsRemoved is the list of credential names removed.
CredentialsRemoved []string `json:"credentials_removed,omitempty"`
// MCPToolsAdded is the list of MCP tools added.
MCPToolsAdded []string `json:"mcp_tools_added,omitempty"`
// MCPToolsRemoved is the list of MCP tools removed.
MCPToolsRemoved []string `json:"mcp_tools_removed,omitempty"`
}
PolicyDelta records additions and removals to policy between a parent lock and its child (update).
type ProvenanceEntry ¶ added in v0.2.0
type ProvenanceEntry struct {
// Action is the lifecycle action (e.g. "created", "updated").
Action string `json:"action"`
// PublisherFingerprint is the fingerprint of the publisher that
// performed the action.
PublisherFingerprint string `json:"publisher_fingerprint"`
// PublisherName is the display name of the publisher.
PublisherName string `json:"publisher_name"`
// PublisherPublicKeyPEM is the public key PEM of the publisher.
PublisherPublicKeyPEM string `json:"publisher_public_key_pem"`
// AgentName is the agent name at the time of the action.
AgentName string `json:"agent_name"`
// AgentVersion is the agent version at the time of the action.
AgentVersion string `json:"agent_version"`
// ParentLockDigest is the LockDigest of the parent lock this entry
// was built on top of. Empty for the initial "created" action.
ParentLockDigest string `json:"parent_lock_digest"`
// ParentBundleDigest is the SHA-256 of the parent shared bundle.
// Empty for the initial "created" action.
ParentBundleDigest string `json:"parent_bundle_digest"`
// ParentPolicyDigest is the policy digest of the parent lock.
// Empty for the initial "created" action.
ParentPolicyDigest string `json:"parent_policy_digest"`
// PolicyDelta records changes to policy between parent and child.
// nil when there is no change or for the initial "created" action.
PolicyDelta *PolicyDelta `json:"policy_delta,omitempty"`
// Timestamp is the wall-clock time the action was performed.
Timestamp time.Time `json:"timestamp"`
// EntrySignature is the ECDSA signature over the canonical
// representation of this entry (excluding entry_signature), signed by
// the publisher that performed the action. Base64-encoded.
EntrySignature string `json:"entry_signature"`
}
ProvenanceEntry records a single lifecycle event for an agent lockfile (created, updated, etc.). Each entry is independently signed by the publisher that performed the action.
type ProvenanceEntrySummary ¶ added in v0.2.0
type ProvenanceEntrySummary struct {
Index int `json:"index"`
Action string `json:"action"`
PublisherName string `json:"publisher_name"`
PublisherFingerprint string `json:"publisher_fingerprint"`
AgentName string `json:"agent_name"`
AgentVersion string `json:"agent_version"`
Timestamp time.Time `json:"timestamp"`
PolicyDelta *PolicyDelta `json:"policy_delta,omitempty"`
// ParentLockDigest is the parent lock digest for forked entries (local verification).
ParentLockDigest string `json:"parent_lock_digest,omitempty"`
}
ProvenanceEntrySummary is a display-oriented summary of a provenance entry.
type ProvenanceReport ¶ added in v0.2.0
type ProvenanceReport struct {
// Verified is true when all structural and cryptographic rules pass.
Verified bool `json:"verified"`
// Warnings holds non-fatal issues (e.g. clock skew).
Warnings []string `json:"warnings,omitempty"`
// Entries is the list of provenance entry summaries.
Entries []ProvenanceEntrySummary `json:"entries"`
// ChainSemantics is a fixed string explaining what provenance entries mean.
ChainSemantics string `json:"chain_semantics"`
}
ProvenanceReport is the result of verifying a provenance chain.
func VerifyProvenance ¶ added in v0.2.0
func VerifyProvenance(lock *AgentLock) (*ProvenanceReport, error)
VerifyProvenance performs full structural and cryptographic verification of a lock's provenance chain. It returns a report; the error return is reserved for programming errors (nil lock, etc.). Structural and signature failures set Verified=false.
type PublisherInfo ¶ added in v0.2.0
type PublisherInfo struct {
// Name is the display label (GitHub-style slug).
Name string `json:"name"`
// Fingerprint is the hex-encoded SHA-256 of the DER-encoded SPKI of
// the publisher's ECDSA P-256 public key.
Fingerprint string `json:"fingerprint"`
// PublicKeyPEM is the PEM-encoded SPKI public key.
PublicKeyPEM string `json:"public_key_pem"`
// SignedAt is the wall-clock time the publisher signature was created.
SignedAt time.Time `json:"signed_at"`
}
PublisherInfo holds the public-facing identity information for the publisher who signed this lockfile. It is embedded in the lockfile's publisher block (schema v2+).
type ReproducibilityMeta ¶
type ReproducibilityMeta struct {
// SourceDateEpoch is the fixed timestamp used for the build.
SourceDateEpoch time.Time `json:"source_date_epoch"`
// BaseImagePinned is true if the base image is digest-pinned.
BaseImagePinned bool `json:"base_image_pinned"`
// DepsLocked is true if dependencies were locked via uv.
DepsLocked bool `json:"deps_locked"`
// TarOrder is "sorted" for deterministic tar order.
TarOrder string `json:"tar_order"`
}
ReproducibilityMeta holds metadata for verifying build reproducibility.
type RuntimeType ¶
type RuntimeType string
RuntimeType represents the detected agent runtime/framework.
const ( RuntimePython RuntimeType = "python" RuntimeLangGraph RuntimeType = "langgraph" RuntimeCrewAI RuntimeType = "crewai" RuntimeUnknown RuntimeType = "unknown" )
type ScanConfig ¶
type ScanConfig struct {
// ProjectDir is the agent project directory to scan.
ProjectDir string
// Ignore is the .agentpaasignore matcher (from T01).
Ignore *IgnoreMatcher
// AllowPatterns are regex patterns for secrets that are explicitly allowed.
// Each requires a successful audit append (see AuditAppend below).
AllowPatterns []string
// AuditAppend is called to record an allow-pattern justification.
// If nil, --allow-secret-pattern aborts with an error.
AuditAppend AuditAppender
}
ScanConfig controls the secret scan process.
type ScanResult ¶
type ScanResult struct {
// Findings from source tree scan.
SourceFindings []SecretFinding `json:"source_findings"`
// Findings from build context scan (after .agentpaasignore applied).
ContextFindings []SecretFinding `json:"context_findings"`
// ContextSize is the total build context size in bytes.
ContextSize int64 `json:"context_size"`
// ContextSizeWarning is true if ContextSize > 100MB.
ContextSizeWarning bool `json:"context_size_warning"`
}
ScanResult holds the outcome of a secret scan.
func ScanSecrets ¶
func ScanSecrets(ctx context.Context, cfg ScanConfig) (*ScanResult, error)
ScanSecrets runs gitleaks over the source tree and effective build context. Steps: 1. Run gitleaks on the full source tree (no ignore filtering). 2. Run gitleaks on the effective build context (after .agentpaasignore). 3. Compute build context size (sum of non-ignored file sizes). 4. Warn if context >100MB. 5. Apply allow-patterns (with audit append requirement). Returns ScanResult with findings. Does NOT fail itself — caller checks findings.
func (*ScanResult) FailClosed ¶
func (r *ScanResult) FailClosed() bool
FailClosed returns true if the scan should fail (secrets found that are not allow-patterned with audit append).
func (*ScanResult) HasSecrets ¶
func (r *ScanResult) HasSecrets() bool
HasSecrets returns true if any findings exist (source or context).
type SecretFinding ¶
type SecretFinding struct {
// File is the relative path from ProjectDir.
File string `json:"file"`
// Line is the 1-based line number.
Line int `json:"line"`
// Rule is the gitleaks rule ID that matched.
Rule string `json:"rule"`
// Secret is the masked secret value (first 4 chars + *** + last 4 chars).
Secret string `json:"secret"`
// contains filtered or unexported fields
}
SecretFinding represents a detected secret in the source or build context.
func ScanDirectorySecrets ¶ added in v0.2.0
func ScanDirectorySecrets(ctx context.Context, dir string) ([]SecretFinding, error)
ScanDirectorySecrets runs gitleaks on the exact directory tree (export fileset).