@kici-dev/sdk 0.0.0 → 0.1.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (112) hide show
  1. package/LICENSE +202 -0
  2. package/README.md +1 -6
  3. package/dist/api-types.d.ts +47 -0
  4. package/dist/api-types.js +15 -0
  5. package/dist/chunk-gOLHoazu.js +4 -0
  6. package/dist/context.d.ts +185 -0
  7. package/dist/context.js +2 -0
  8. package/dist/dynamic-group.d.ts +29 -0
  9. package/dist/dynamic-group.js +34 -0
  10. package/dist/errors.d.ts +9 -0
  11. package/dist/errors.js +17 -0
  12. package/dist/events/define-event.d.ts +32 -0
  13. package/dist/events/define-event.js +29 -0
  14. package/dist/events/event-payloads.d.ts +396 -0
  15. package/dist/events/event-payloads.js +21 -0
  16. package/dist/events/index.d.ts +6 -0
  17. package/dist/events/index.js +4 -0
  18. package/dist/events/types.d.ts +13 -0
  19. package/dist/events/types.js +2 -0
  20. package/dist/fixture.d.ts +50 -0
  21. package/dist/fixture.js +35 -0
  22. package/dist/hooks/index.d.ts +33 -0
  23. package/dist/hooks/index.js +94 -0
  24. package/dist/hooks/types.d.ts +35 -0
  25. package/dist/hooks/types.js +2 -0
  26. package/dist/idempotent.d.ts +71 -0
  27. package/dist/idempotent.js +77 -0
  28. package/dist/index.d.ts +40 -0
  29. package/dist/index.js +50 -0
  30. package/dist/job.d.ts +31 -0
  31. package/dist/job.js +46 -0
  32. package/dist/matrix/expand.d.ts +32 -0
  33. package/dist/matrix/expand.js +77 -0
  34. package/dist/matrix/index.d.ts +4 -0
  35. package/dist/matrix/index.js +4 -0
  36. package/dist/matrix/types.d.ts +60 -0
  37. package/dist/matrix/types.js +18 -0
  38. package/dist/outputs.d.ts +86 -0
  39. package/dist/outputs.js +180 -0
  40. package/dist/rules/evaluator.d.ts +24 -0
  41. package/dist/rules/evaluator.js +52 -0
  42. package/dist/rules/index.d.ts +6 -0
  43. package/dist/rules/index.js +5 -0
  44. package/dist/rules/rule.d.ts +34 -0
  45. package/dist/rules/rule.js +37 -0
  46. package/dist/rules/types.d.ts +42 -0
  47. package/dist/rules/types.js +2 -0
  48. package/dist/secrets.d.ts +192 -0
  49. package/dist/secrets.js +132 -0
  50. package/dist/step.d.ts +50 -0
  51. package/dist/step.js +78 -0
  52. package/dist/triggers/comment.d.ts +20 -0
  53. package/dist/triggers/comment.js +47 -0
  54. package/dist/triggers/create.d.ts +20 -0
  55. package/dist/triggers/create.js +32 -0
  56. package/dist/triggers/delete.d.ts +20 -0
  57. package/dist/triggers/delete.js +29 -0
  58. package/dist/triggers/dispatch.d.ts +17 -0
  59. package/dist/triggers/dispatch.js +27 -0
  60. package/dist/triggers/fork.d.ts +17 -0
  61. package/dist/triggers/fork.js +26 -0
  62. package/dist/triggers/generic-webhook.d.ts +32 -0
  63. package/dist/triggers/generic-webhook.js +45 -0
  64. package/dist/triggers/index.d.ts +28 -0
  65. package/dist/triggers/index.js +25 -0
  66. package/dist/triggers/job-complete.d.ts +23 -0
  67. package/dist/triggers/job-complete.js +33 -0
  68. package/dist/triggers/kici-event.d.ts +23 -0
  69. package/dist/triggers/kici-event.js +34 -0
  70. package/dist/triggers/lifecycle.d.ts +20 -0
  71. package/dist/triggers/lifecycle.js +29 -0
  72. package/dist/triggers/pr.d.ts +27 -0
  73. package/dist/triggers/pr.js +48 -0
  74. package/dist/triggers/push.d.ts +29 -0
  75. package/dist/triggers/push.js +48 -0
  76. package/dist/triggers/release.d.ts +17 -0
  77. package/dist/triggers/release.js +27 -0
  78. package/dist/triggers/review-comment.d.ts +17 -0
  79. package/dist/triggers/review-comment.js +27 -0
  80. package/dist/triggers/review.d.ts +17 -0
  81. package/dist/triggers/review.js +28 -0
  82. package/dist/triggers/schedule.d.ts +20 -0
  83. package/dist/triggers/schedule.js +29 -0
  84. package/dist/triggers/star.d.ts +17 -0
  85. package/dist/triggers/star.js +27 -0
  86. package/dist/triggers/status.d.ts +17 -0
  87. package/dist/triggers/status.js +28 -0
  88. package/dist/triggers/tag.d.ts +20 -0
  89. package/dist/triggers/tag.js +31 -0
  90. package/dist/triggers/types.d.ts +529 -0
  91. package/dist/triggers/types.js +36 -0
  92. package/dist/triggers/watch.d.ts +17 -0
  93. package/dist/triggers/watch.js +27 -0
  94. package/dist/triggers/webhook.d.ts +19 -0
  95. package/dist/triggers/webhook.js +29 -0
  96. package/dist/triggers/workflow-complete.d.ts +23 -0
  97. package/dist/triggers/workflow-complete.js +32 -0
  98. package/dist/triggers/workflow-run.d.ts +17 -0
  99. package/dist/triggers/workflow-run.js +29 -0
  100. package/dist/types.d.ts +483 -0
  101. package/dist/types.js +35 -0
  102. package/dist/validation/dag.d.ts +42 -0
  103. package/dist/validation/dag.js +70 -0
  104. package/dist/validation/index.d.ts +3 -0
  105. package/dist/validation/index.js +3 -0
  106. package/dist/wait-for.d.ts +109 -0
  107. package/dist/wait-for.js +144 -0
  108. package/dist/workflow.d.ts +3 -0
  109. package/dist/workflow.js +83 -0
  110. package/package.json +42 -6
  111. package/sbom.spdx.json +9150 -0
  112. package/index.js +0 -3
@@ -0,0 +1,180 @@
1
+ import "./chunk-gOLHoazu.js";
2
+ //#region src/outputs.ts
3
+ /**
4
+ * Well-known string property names that should delegate to Reflect rather than throwing.
5
+ * These are accessed by built-in operations like JSON.stringify, console.log, iteration, etc.
6
+ */
7
+ const WELL_KNOWN_STRING_PROPS = new Set([
8
+ "constructor",
9
+ "toString",
10
+ "valueOf",
11
+ "toJSON",
12
+ "then",
13
+ "length",
14
+ "nodeType",
15
+ "tagName",
16
+ "inspect",
17
+ "$$typeof",
18
+ "asymmetricMatch",
19
+ "_tag"
20
+ ]);
21
+ /**
22
+ * Module-global outputs maps. Runners inject fresh maps at execution time
23
+ * via setStepOutputsMap() / setJobOutputsMap().
24
+ */
25
+ let _stepOutputsMap = /* @__PURE__ */ new Map();
26
+ let _jobOutputsMap = /* @__PURE__ */ new Map();
27
+ let _stepRefMap = /* @__PURE__ */ new WeakMap();
28
+ /**
29
+ * Inject a fresh step outputs map for a new execution.
30
+ * Called by workflow runners (compiler test runner, agent sandbox) before execution.
31
+ */
32
+ function setStepOutputsMap(map) {
33
+ _stepOutputsMap = map;
34
+ }
35
+ /**
36
+ * Inject a fresh job outputs map for a new execution.
37
+ */
38
+ function setJobOutputsMap(map) {
39
+ _jobOutputsMap = map;
40
+ }
41
+ /**
42
+ * Inject a fresh step-ref map for bare function -> step name resolution.
43
+ */
44
+ function setStepRefMap(map) {
45
+ _stepRefMap = map;
46
+ }
47
+ /**
48
+ * Get the current step outputs map (for runners to populate).
49
+ */
50
+ function getStepOutputsMap() {
51
+ return _stepOutputsMap;
52
+ }
53
+ /**
54
+ * Get the current job outputs map (for runners to populate).
55
+ */
56
+ function getJobOutputsMap() {
57
+ return _jobOutputsMap;
58
+ }
59
+ /**
60
+ * Get the current step ref map.
61
+ */
62
+ function getStepRefMap() {
63
+ return _stepRefMap;
64
+ }
65
+ /**
66
+ * Create a Proxy over step outputs that resolves property access lazily
67
+ * against the module-global step outputs map.
68
+ *
69
+ * @param stepName - The name of the step whose outputs to proxy
70
+ * @returns A Proxy that resolves property access at runtime
71
+ */
72
+ function createStepOutputProxy(stepName) {
73
+ return new Proxy({}, {
74
+ get(_target, prop, receiver) {
75
+ if (typeof prop === "symbol") return Reflect.get(_target, prop, receiver);
76
+ if (WELL_KNOWN_STRING_PROPS.has(prop)) return Reflect.get(_target, prop, receiver);
77
+ const outputs = _stepOutputsMap.get(stepName);
78
+ if (!outputs) throw new Error(`Step '${stepName}' has not produced outputs yet`);
79
+ return outputs[prop];
80
+ },
81
+ ownKeys() {
82
+ const outputs = _stepOutputsMap.get(stepName);
83
+ if (!outputs) return [];
84
+ return Reflect.ownKeys(outputs);
85
+ },
86
+ has(_target, prop) {
87
+ const outputs = _stepOutputsMap.get(stepName);
88
+ if (!outputs) return false;
89
+ return prop in outputs;
90
+ },
91
+ getOwnPropertyDescriptor(_target, prop) {
92
+ const outputs = _stepOutputsMap.get(stepName);
93
+ if (!outputs) return void 0;
94
+ if (prop in outputs) return {
95
+ configurable: true,
96
+ enumerable: true,
97
+ value: outputs[prop]
98
+ };
99
+ }
100
+ });
101
+ }
102
+ /**
103
+ * Create a Proxy over job outputs that resolves property access lazily
104
+ * against the module-global job outputs map.
105
+ *
106
+ * For multi-step jobs: job.result.stepName.field
107
+ * For single-step (run shorthand) jobs: job.result.field
108
+ *
109
+ * @param jobName - The name of the job whose outputs to proxy
110
+ * @returns A Proxy that resolves property access at runtime
111
+ */
112
+ function createJobOutputProxy(jobName) {
113
+ return new Proxy({}, {
114
+ get(_target, prop, receiver) {
115
+ if (typeof prop === "symbol") return Reflect.get(_target, prop, receiver);
116
+ if (WELL_KNOWN_STRING_PROPS.has(prop)) return Reflect.get(_target, prop, receiver);
117
+ const outputs = _jobOutputsMap.get(jobName);
118
+ if (!outputs) throw new Error(`Job '${jobName}' has not produced outputs yet`);
119
+ return outputs[prop];
120
+ },
121
+ ownKeys() {
122
+ const outputs = _jobOutputsMap.get(jobName);
123
+ if (!outputs) return [];
124
+ return Reflect.ownKeys(outputs);
125
+ },
126
+ has(_target, prop) {
127
+ const outputs = _jobOutputsMap.get(jobName);
128
+ if (!outputs) return false;
129
+ return prop in outputs;
130
+ },
131
+ getOwnPropertyDescriptor(_target, prop) {
132
+ const outputs = _jobOutputsMap.get(jobName);
133
+ if (!outputs) return void 0;
134
+ if (prop in outputs) return {
135
+ configurable: true,
136
+ enumerable: true,
137
+ value: outputs[prop]
138
+ };
139
+ }
140
+ });
141
+ }
142
+ /**
143
+ * Resolve step outputs by step reference (Step object or bare function).
144
+ * Used by ctx.outputsOf() implementation.
145
+ *
146
+ * @param ref - Step object (with _tag: 'Step') or bare function reference
147
+ * @param outputsMap - The outputs map to resolve against (defaults to module-global)
148
+ * @param refMap - The ref map for bare function -> name resolution (defaults to module-global)
149
+ * @returns The step's outputs
150
+ */
151
+ function resolveStepOutputs(ref, outputsMap, refMap) {
152
+ const map = outputsMap ?? _stepOutputsMap;
153
+ const rMap = refMap ?? _stepRefMap;
154
+ let stepName;
155
+ if (typeof ref === "function") {
156
+ stepName = rMap.get(ref);
157
+ if (!stepName) throw new Error("Cannot resolve outputs for bare function: function not registered in step ref map");
158
+ } else if (ref && typeof ref === "object" && "_tag" in ref && ref._tag === "Step") stepName = ref.name;
159
+ else throw new Error("Invalid step reference: expected Step object or bare function");
160
+ const outputs = map.get(stepName);
161
+ if (!outputs) throw new Error(`Step '${stepName}' has not produced outputs yet`);
162
+ return outputs;
163
+ }
164
+ /**
165
+ * Resolve job outputs by job reference.
166
+ * Used by ctx.jobOutputs() implementation.
167
+ *
168
+ * @param ref - Job object reference (needs .name property)
169
+ * @param outputsMap - The outputs map to resolve against (defaults to module-global)
170
+ * @returns The job's outputs
171
+ */
172
+ function resolveJobOutputs(ref, outputsMap) {
173
+ const outputs = (outputsMap ?? _jobOutputsMap).get(ref.name);
174
+ if (!outputs) throw new Error(`Job '${ref.name}' has not produced outputs yet`);
175
+ return outputs;
176
+ }
177
+ //#endregion
178
+ export { createJobOutputProxy, createStepOutputProxy, getJobOutputsMap, getStepOutputsMap, getStepRefMap, resolveJobOutputs, resolveStepOutputs, setJobOutputsMap, setStepOutputsMap, setStepRefMap };
179
+
180
+ //# sourceMappingURL=outputs.js.map
@@ -0,0 +1,24 @@
1
+ import type { Rule, RuleContext, RuleResult } from './types.js';
2
+ /**
3
+ * Result of evaluating rules for a job or workflow.
4
+ * Contains overall pass/fail status and per-rule results.
5
+ */
6
+ export interface RuleEvaluationResult {
7
+ allPassed: boolean;
8
+ results: RuleResult[];
9
+ }
10
+ /**
11
+ * Evaluate rules sequentially with fail-fast behavior.
12
+ *
13
+ * Iterates rules in order, calling each rule's check function with the provided
14
+ * context. Records timing and result for each evaluated rule. Stops evaluation
15
+ * on the first failure (remaining rules are not evaluated).
16
+ *
17
+ * @param rules - Array of Rule objects to evaluate
18
+ * @param context - RuleContext providing event, env, changedFiles, and $
19
+ * @param _label - Human-readable label for logging (e.g., job name) -- reserved for callers
20
+ * @param onRuleResult - Optional callback invoked after each rule evaluation
21
+ * @returns RuleEvaluationResult with allPassed flag and per-rule results
22
+ */
23
+ export declare function evaluateRules(rules: Rule[], context: RuleContext, _label: string, onRuleResult?: (result: RuleResult) => void): Promise<RuleEvaluationResult>;
24
+ //# sourceMappingURL=evaluator.d.ts.map
@@ -0,0 +1,52 @@
1
+ import "../chunk-gOLHoazu.js";
2
+ import { toErrorMessage } from "@kici-dev/shared";
3
+ //#region src/rules/evaluator.ts
4
+ /**
5
+ * Evaluate rules sequentially with fail-fast behavior.
6
+ *
7
+ * Iterates rules in order, calling each rule's check function with the provided
8
+ * context. Records timing and result for each evaluated rule. Stops evaluation
9
+ * on the first failure (remaining rules are not evaluated).
10
+ *
11
+ * @param rules - Array of Rule objects to evaluate
12
+ * @param context - RuleContext providing event, env, changedFiles, and $
13
+ * @param _label - Human-readable label for logging (e.g., job name) -- reserved for callers
14
+ * @param onRuleResult - Optional callback invoked after each rule evaluation
15
+ * @returns RuleEvaluationResult with allPassed flag and per-rule results
16
+ */
17
+ async function evaluateRules(rules, context, _label, onRuleResult) {
18
+ const results = [];
19
+ let allPassed = true;
20
+ for (const rule of rules) {
21
+ const startTime = Date.now();
22
+ let passed = false;
23
+ let error;
24
+ try {
25
+ passed = await rule.check(context);
26
+ } catch (e) {
27
+ passed = false;
28
+ error = toErrorMessage(e);
29
+ }
30
+ const durationMs = Date.now() - startTime;
31
+ const result = {
32
+ label: rule.label,
33
+ passed,
34
+ durationMs,
35
+ error
36
+ };
37
+ results.push(result);
38
+ onRuleResult?.(result);
39
+ if (!passed) {
40
+ allPassed = false;
41
+ break;
42
+ }
43
+ }
44
+ return {
45
+ allPassed,
46
+ results
47
+ };
48
+ }
49
+ //#endregion
50
+ export { evaluateRules };
51
+
52
+ //# sourceMappingURL=evaluator.js.map
@@ -0,0 +1,6 @@
1
+ export { rule, skip } from './rule.js';
2
+ export { evaluateRules, type RuleEvaluationResult } from './evaluator.js';
3
+ export type { Rule, RuleCheckFn, RuleContext, RuleResult, EventPayload } from './types.js';
4
+ export { isEventType } from '../events/event-payloads.js';
5
+ export type { EventBase, PullRequestEventPayload, PushEventPayload, TagEventPayload, CommentEventPayload, ReviewEventPayload, ReviewCommentEventPayload, ReleaseEventPayload, DispatchEventPayload, CreateEventPayload, DeleteEventPayload, StatusEventPayload, WorkflowRunEventPayload, ForkEventPayload, StarEventPayload, WatchEventPayload, WebhookEventPayload, KiciEventPayload, WorkflowCompleteEventPayload, JobCompleteEventPayload, GenericWebhookEventPayload, ScheduleEventPayload, LifecycleEventPayload, GitHubRepository, GitHubUser, GitHubPullRequest, GitHubCommit, GitHubComment, GitHubReview, GitHubRelease, } from '../events/event-payloads.js';
6
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1,5 @@
1
+ import "../chunk-gOLHoazu.js";
2
+ import { rule, skip } from "./rule.js";
3
+ import { evaluateRules } from "./evaluator.js";
4
+ import { isEventType } from "../events/event-payloads.js";
5
+ export { evaluateRules, isEventType, rule, skip };
@@ -0,0 +1,34 @@
1
+ import type { Rule, RuleCheckFn } from './types.js';
2
+ /**
3
+ * Create a rule with just a label (always passes).
4
+ * Useful for markers that appear in the decision trace.
5
+ *
6
+ * @example
7
+ * const marker = rule('ci: required check');
8
+ */
9
+ export declare function rule(label: string): Rule;
10
+ /**
11
+ * Create a rule with a label and check function.
12
+ * The check function determines whether the rule passes.
13
+ *
14
+ * @example
15
+ * const hasFrontend = rule('skip: no frontend changes', async (ctx) => {
16
+ * return ctx.changedFiles.some(f => f.startsWith('src/ui/'));
17
+ * });
18
+ */
19
+ export declare function rule(label: string, check: RuleCheckFn): Rule;
20
+ /**
21
+ * Create a rule that skips when the condition is met.
22
+ * Convenience wrapper around rule() that inverts the check function.
23
+ *
24
+ * When the check returns true (condition met), the rule returns false (skip).
25
+ * When the check returns false (condition not met), the rule returns true (run).
26
+ *
27
+ * @example
28
+ * // Skip when PR only contains docs changes
29
+ * const skipDocsOnly = skip('docs only PR', async (ctx) => {
30
+ * return ctx.changedFiles.every(f => f.endsWith('.md'));
31
+ * });
32
+ */
33
+ export declare function skip(label: string, check: RuleCheckFn): Rule;
34
+ //# sourceMappingURL=rule.d.ts.map
@@ -0,0 +1,37 @@
1
+ import "../chunk-gOLHoazu.js";
2
+ //#region src/rules/rule.ts
3
+ /**
4
+ * Implementation of rule() factory.
5
+ * Creates a Rule with an optional check function (defaults to always-true).
6
+ */
7
+ function rule(label, check) {
8
+ return {
9
+ _tag: "Rule",
10
+ label,
11
+ check: check ?? (() => true)
12
+ };
13
+ }
14
+ /**
15
+ * Create a rule that skips when the condition is met.
16
+ * Convenience wrapper around rule() that inverts the check function.
17
+ *
18
+ * When the check returns true (condition met), the rule returns false (skip).
19
+ * When the check returns false (condition not met), the rule returns true (run).
20
+ *
21
+ * @example
22
+ * // Skip when PR only contains docs changes
23
+ * const skipDocsOnly = skip('docs only PR', async (ctx) => {
24
+ * return ctx.changedFiles.every(f => f.endsWith('.md'));
25
+ * });
26
+ */
27
+ function skip(label, check) {
28
+ return {
29
+ _tag: "Rule",
30
+ label,
31
+ check: async (ctx) => !await check(ctx)
32
+ };
33
+ }
34
+ //#endregion
35
+ export { rule, skip };
36
+
37
+ //# sourceMappingURL=rule.js.map
@@ -0,0 +1,42 @@
1
+ import type { $ as Shell } from 'zx';
2
+ import type { EventPayload } from '../events/event-payloads.js';
3
+ export type { EventPayload } from '../events/event-payloads.js';
4
+ /**
5
+ * Context passed to rule check functions.
6
+ * Provides access to event data, changed files, environment, and shell execution.
7
+ */
8
+ export interface RuleContext {
9
+ /** The triggering event payload */
10
+ event: EventPayload;
11
+ /** List of files changed in this event (e.g., PR diff) */
12
+ changedFiles: string[];
13
+ /** Environment variables */
14
+ env: Record<string, string | undefined>;
15
+ /** zx shell executor for running commands */
16
+ $: typeof Shell;
17
+ }
18
+ /**
19
+ * Function type for rule check functions.
20
+ * Can be sync or async - returns whether the rule passes.
21
+ */
22
+ export type RuleCheckFn = (ctx: RuleContext) => Promise<boolean> | boolean;
23
+ /**
24
+ * Rule definition returned by rule() factory.
25
+ * Rules are labeled conditional checks that appear in the decision trace.
26
+ */
27
+ export interface Rule {
28
+ readonly _tag: 'Rule';
29
+ readonly label: string;
30
+ readonly check: RuleCheckFn;
31
+ }
32
+ /**
33
+ * Result of evaluating a rule (for decision trace).
34
+ * Records whether the rule passed and how long evaluation took.
35
+ */
36
+ export interface RuleResult {
37
+ label: string;
38
+ passed: boolean;
39
+ durationMs: number;
40
+ error?: string;
41
+ }
42
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1,2 @@
1
+ import "../chunk-gOLHoazu.js";
2
+ export {};
@@ -0,0 +1,192 @@
1
+ /**
2
+ * Metadata about a resolved secret -- which backend and scope provided it.
3
+ */
4
+ export interface SecretMeta {
5
+ /** The resolved secret value. */
6
+ value: string;
7
+ /** Backend name that provided the secret (e.g., 'pg', 'openbao-stg'). */
8
+ backend: string;
9
+ /** Full prefixed scope path (e.g., 'pg:production/db'). */
10
+ scope: string;
11
+ }
12
+ /**
13
+ * Options for materialising one or more existing secret values as a file
14
+ * on-disk inside the per-step tmpdir.
15
+ */
16
+ export interface SecretFileOptions {
17
+ /**
18
+ * Names of existing secret keys to concatenate (in order) into the file.
19
+ * Each key must resolve via `ctx.secrets.get(key)`; missing keys cause
20
+ * `SecretNotFoundError` to be thrown (carrying every missing key).
21
+ */
22
+ sources: string[];
23
+ /**
24
+ * Optional separator written between concatenated source values.
25
+ * Default: no divider (values are joined back-to-back).
26
+ */
27
+ divider?: string;
28
+ /**
29
+ * File mode to chmod the materialised file to. Default `0o600`
30
+ * (owner read/write only).
31
+ */
32
+ mode?: number;
33
+ /**
34
+ * Optional filename inside the per-step tmpdir. When omitted, the
35
+ * runtime auto-generates a unique name (`secret-1`, `secret-2`, ...).
36
+ */
37
+ name?: string;
38
+ }
39
+ /**
40
+ * Result of a `mountFile` / `exposeFile` call.
41
+ */
42
+ export interface MountedFile {
43
+ /** Absolute path to the materialised file inside the per-step tmpdir. */
44
+ path: string;
45
+ }
46
+ /**
47
+ * Host-side adapter passed by the agent to back the file-mount API.
48
+ *
49
+ * The SDK owns the public surface (`mountFile` / `exposeFile`) but defers
50
+ * disk and `process.env` operations to the agent so the SDK stays free of
51
+ * any `node:fs` / `node:os` imports. Local-test mode (`kici test`) plugs
52
+ * in the same adapter shape against `os.tmpdir()`.
53
+ */
54
+ export interface StepSecretsFileHost {
55
+ /**
56
+ * Materialise the concatenated content to a file inside the per-step
57
+ * tmpdir. The host is responsible for chmod + masker registration
58
+ * (when applicable) and for remembering the file for cleanup.
59
+ * Returns the absolute path on success.
60
+ */
61
+ writeMountedFile(args: {
62
+ content: string;
63
+ sources: string[];
64
+ mode: number;
65
+ name?: string;
66
+ }): Promise<string>;
67
+ /**
68
+ * Track an env var that was set as part of `exposeFile`, so the
69
+ * runtime can `delete process.env[envVar]` during `dispose()`.
70
+ */
71
+ trackExposedEnv(envVar: string): void;
72
+ }
73
+ /**
74
+ * Async accessor interface for step secrets.
75
+ * Secrets are never automatically injected into environment variables.
76
+ * Use get() to read a secret value, expose() to explicitly inject into env.
77
+ */
78
+ export interface StepSecrets {
79
+ /** Retrieve a secret value by key. Rejects with SecretNotFoundError if not found. */
80
+ get(key: string): Promise<string>;
81
+ /** Inject a secret into the step's environment variables. Rejects if key not found. */
82
+ expose(key: string): Promise<void>;
83
+ /** Check if a secret key exists. Synchronous, never throws. */
84
+ has(key: string): boolean;
85
+ /** Retrieve metadata about a resolved secret (backend name and scope). Returns undefined if key not found. */
86
+ getMeta(key: string): SecretMeta | undefined;
87
+ /**
88
+ * Return every secret key available to this step, sorted alphabetically.
89
+ * Synchronous, never throws. Returns names only -- call `getMeta(key)` to
90
+ * inspect backend / scope for a specific key.
91
+ */
92
+ list(): string[];
93
+ /**
94
+ * Materialise one or more existing secrets as a tmpfile inside a
95
+ * per-step tmpdir. Returns the absolute file path. The file is removed
96
+ * automatically when the step completes (success, failure, or timeout).
97
+ * Rejects with `SecretNotFoundError` if any source key is missing.
98
+ */
99
+ mountFile(opts: SecretFileOptions): Promise<MountedFile>;
100
+ /**
101
+ * Sugar: call `mountFile(opts)`, then set `process.env[envVar]` to the
102
+ * resulting path. The env var is unset and the file is removed when
103
+ * the step completes.
104
+ */
105
+ exposeFile(envVar: string, opts: SecretFileOptions): Promise<MountedFile>;
106
+ }
107
+ /**
108
+ * Extended StepSecrets with access tracking.
109
+ * Tracks which secret keys were accessed via get() or expose() calls.
110
+ * Only key names are recorded -- never values.
111
+ */
112
+ export interface TrackedStepSecrets extends StepSecrets {
113
+ /** Returns sorted array of secret key names accessed via get() or expose(). */
114
+ getAccessLog(): string[];
115
+ /**
116
+ * Returns sorted array of secret key names referenced via `mountFile()` /
117
+ * `exposeFile()`. Mounts are tracked separately from plain `get` / `expose`
118
+ * accesses so the orchestrator can render a distinct audit row.
119
+ */
120
+ getMountedKeys(): string[];
121
+ /**
122
+ * Returns the audit records of every mount call (in order). Used by the
123
+ * agent to emit `step.secret_mount` IPC events. Each record carries
124
+ * `{ sources, target, envVar?, kind }`. `target` is the absolute path the
125
+ * file was materialised to.
126
+ */
127
+ getMountRecords(): readonly StepSecretMountRecord[];
128
+ }
129
+ /**
130
+ * Kinds of secret-file materialisation operations. Surfaced as the `kind`
131
+ * discriminator on the IPC event so the orchestrator can distinguish a
132
+ * plain mount from a mount-with-env-var binding.
133
+ */
134
+ export type StepSecretMountKind = 'mountFile' | 'exposeFile';
135
+ /**
136
+ * Audit record for a single secret-file materialisation operation.
137
+ * Never contains the file content -- only the key names and the
138
+ * resulting path / env var.
139
+ */
140
+ export interface StepSecretMountRecord {
141
+ /** Source secret keys (in concatenation order). */
142
+ sources: string[];
143
+ /** Absolute path the file was materialised to. */
144
+ target: string;
145
+ /** Env var set when `kind === 'exposeFile'`; otherwise undefined. */
146
+ envVar?: string;
147
+ /** Discriminator between `mountFile` and `exposeFile`. */
148
+ kind: StepSecretMountKind;
149
+ }
150
+ /**
151
+ * Result of {@link createStepSecrets}: the secrets surface itself plus a
152
+ * `dispose` callback the agent invokes from the step-loop `finally` to
153
+ * remove materialised files and clear any exposed env vars.
154
+ *
155
+ * `dispose` swallows its own errors -- it never throws. Failures are
156
+ * surfaced via the optional `onDisposeError` callback passed when the
157
+ * file-mount host was wired in.
158
+ */
159
+ export interface StepSecretsHandle {
160
+ /** The secrets surface bound into `ctx.secrets`. */
161
+ secrets: TrackedStepSecrets;
162
+ /** Tear down any materialised files and unset exposed env vars. */
163
+ dispose: () => Promise<void>;
164
+ }
165
+ /**
166
+ * Optional wiring for the file-mount + cleanup path. When omitted, calls
167
+ * to `mountFile` / `exposeFile` throw -- the SDK alone cannot mount files
168
+ * (no `node:fs` dependency). Production wires a host implementation in
169
+ * the agent; local test mode wires a minimal `os.tmpdir`-backed host.
170
+ */
171
+ export interface StepSecretsFileWiring {
172
+ /** The host adapter (see {@link StepSecretsFileHost}). */
173
+ host: StepSecretsFileHost;
174
+ /** Callback for `dispose()` errors. Receives the error for logging. */
175
+ onDisposeError?: (err: unknown) => void;
176
+ /** Tear down callback invoked by `dispose()` (removes the tmpdir, etc.). */
177
+ cleanup: () => Promise<void>;
178
+ }
179
+ /**
180
+ * Create a StepSecrets instance backed by a plain secrets map.
181
+ * The env parameter receives exposed secrets via expose().
182
+ * Tracks which secrets are accessed for audit/observability purposes.
183
+ *
184
+ * @param secretsMap - Flat key-value secrets map
185
+ * @param env - Process environment to inject exposed secrets into
186
+ * @param metaMap - Optional metadata map from resolveForJobWithMeta (backend + scope per key)
187
+ * @param fileWiring - Optional file-mount host adapter. When omitted, `mountFile`
188
+ * and `exposeFile` throw -- callers that don't wire a host can still use the
189
+ * string-only `get` / `expose` / `has` / `list` surface.
190
+ */
191
+ export declare function createStepSecrets(secretsMap: Record<string, string>, env: Record<string, string | undefined>, metaMap?: Record<string, SecretMeta>, fileWiring?: StepSecretsFileWiring): StepSecretsHandle;
192
+ //# sourceMappingURL=secrets.d.ts.map