import { withStore } from "../../git/store";
import type { ActionsPolicy, RepoRow } from "~/lib/types";
import { isBuiltinAction } from "../builtin-actions";
import type { WorkflowSpec } from "../spec";
import { archiveKey, archiveManifest, ensureArchive, resolveActionRef, verifyPin } from "./archive";
import { ActionSourceError } from "./github";
import { parseActionManifest } from "./manifest";
import type { ActionManifest } from "./manifest";
import { isPinned, looksLikeShortSha, parseActionReference } from "./uses";
const MAX_ACTIONS_PER_WORKFLOW = 25;
const MAX_MANIFEST_BYTES = 256 * 1024;
const MANIFEST_NAMES = ["action.yml", "action.yaml"];
/** A `uses:` resolved at scheduling time and stored with the run, so recompiles and retries never refetch. */
export type ResolvedAction = {
uses: string;
local: boolean;
/** `owner/repo` as written, for logs and `GITHUB_ACTION_REPOSITORY`. */
repository: string | null;
ref: string | null;
sha: string | null;
/** Directory of action.yml inside the archive (remote) or the workspace (local); '' is the root. */
path: string;
archive: { key: string; sha256: string } | null;
manifest: ActionManifest;
};
export type ResolvedActions = Record<string, ResolvedAction>;
export class ActionPolicyError extends Error {}
/** Every distinct non-builtin `uses:` in a workflow. */
export function workflowActionUses(spec: WorkflowSpec): string[] {
const uses = new Set<string>();
for (const job of Object.values(spec.jobs)) {
for (const step of job.steps) {
if (step.uses !== undefined && !isBuiltinAction(step)) uses.add(step.uses.trim());
}
}