@enactprotocol/trust 2.0.0 → 2.0.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.
- package/dist/hash.d.ts +53 -0
- package/dist/hash.d.ts.map +1 -0
- package/dist/hash.js +104 -0
- package/dist/hash.js.map +1 -0
- package/dist/index.d.ts +12 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +14 -0
- package/dist/index.js.map +1 -0
- package/dist/keys.d.ts +41 -0
- package/dist/keys.d.ts.map +1 -0
- package/dist/keys.js +130 -0
- package/dist/keys.js.map +1 -0
- package/dist/sigstore/attestation.d.ts +245 -0
- package/dist/sigstore/attestation.d.ts.map +1 -0
- package/dist/sigstore/attestation.js +324 -0
- package/dist/sigstore/attestation.js.map +1 -0
- package/dist/sigstore/cosign.d.ts +90 -0
- package/dist/sigstore/cosign.d.ts.map +1 -0
- package/dist/sigstore/cosign.js +457 -0
- package/dist/sigstore/cosign.js.map +1 -0
- package/dist/sigstore/index.d.ts +17 -0
- package/dist/sigstore/index.d.ts.map +1 -0
- package/dist/sigstore/index.js +21 -0
- package/dist/sigstore/index.js.map +1 -0
- package/dist/sigstore/oauth/client.d.ts +38 -0
- package/dist/sigstore/oauth/client.d.ts.map +1 -0
- package/dist/sigstore/oauth/client.js +71 -0
- package/dist/sigstore/oauth/client.js.map +1 -0
- package/dist/sigstore/oauth/index.d.ts +47 -0
- package/dist/sigstore/oauth/index.d.ts.map +1 -0
- package/dist/sigstore/oauth/index.js +66 -0
- package/dist/sigstore/oauth/index.js.map +1 -0
- package/dist/sigstore/oauth/server.d.ts +29 -0
- package/dist/sigstore/oauth/server.d.ts.map +1 -0
- package/dist/sigstore/oauth/server.js +145 -0
- package/dist/sigstore/oauth/server.js.map +1 -0
- package/dist/sigstore/policy.d.ts +85 -0
- package/dist/sigstore/policy.d.ts.map +1 -0
- package/dist/sigstore/policy.js +351 -0
- package/dist/sigstore/policy.js.map +1 -0
- package/dist/sigstore/signing.d.ts +94 -0
- package/dist/sigstore/signing.d.ts.map +1 -0
- package/dist/sigstore/signing.js +477 -0
- package/dist/sigstore/signing.js.map +1 -0
- package/dist/sigstore/types.d.ts +541 -0
- package/dist/sigstore/types.d.ts.map +1 -0
- package/dist/sigstore/types.js +5 -0
- package/dist/sigstore/types.js.map +1 -0
- package/dist/sigstore/verification.d.ts +66 -0
- package/dist/sigstore/verification.d.ts.map +1 -0
- package/dist/sigstore/verification.js +317 -0
- package/dist/sigstore/verification.js.map +1 -0
- package/dist/types.d.ts +61 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +5 -0
- package/dist/types.js.map +1 -0
- package/package.json +1 -1
|
@@ -0,0 +1,351 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Trust policy evaluation module
|
|
3
|
+
*
|
|
4
|
+
* This module provides functions for creating and evaluating trust policies
|
|
5
|
+
* that determine whether an artifact should be trusted based on its attestations.
|
|
6
|
+
*/
|
|
7
|
+
import { ENACT_AUDIT_TYPE, ENACT_TOOL_TYPE, SLSA_PROVENANCE_TYPE } from "./attestation";
|
|
8
|
+
import { extractIdentityFromBundle } from "./signing";
|
|
9
|
+
import { verifyBundle } from "./verification";
|
|
10
|
+
// ============================================================================
|
|
11
|
+
// Default Policy
|
|
12
|
+
// ============================================================================
|
|
13
|
+
/**
|
|
14
|
+
* Default trust policy - requires publisher attestation
|
|
15
|
+
*/
|
|
16
|
+
export const DEFAULT_TRUST_POLICY = {
|
|
17
|
+
name: "default",
|
|
18
|
+
version: "1.0",
|
|
19
|
+
trustedPublishers: [],
|
|
20
|
+
trustedAuditors: [],
|
|
21
|
+
requiredAttestations: [ENACT_TOOL_TYPE],
|
|
22
|
+
minimumSLSALevel: 0,
|
|
23
|
+
allowUnsigned: false,
|
|
24
|
+
cacheResults: true,
|
|
25
|
+
};
|
|
26
|
+
/**
|
|
27
|
+
* Permissive policy - allows unsigned tools (for development)
|
|
28
|
+
*/
|
|
29
|
+
export const PERMISSIVE_POLICY = {
|
|
30
|
+
name: "permissive",
|
|
31
|
+
version: "1.0",
|
|
32
|
+
trustedPublishers: [],
|
|
33
|
+
trustedAuditors: [],
|
|
34
|
+
requiredAttestations: [],
|
|
35
|
+
minimumSLSALevel: 0,
|
|
36
|
+
allowUnsigned: true,
|
|
37
|
+
cacheResults: false,
|
|
38
|
+
};
|
|
39
|
+
/**
|
|
40
|
+
* Strict policy - requires publisher + auditor attestations and SLSA level 2+
|
|
41
|
+
*/
|
|
42
|
+
export const STRICT_POLICY = {
|
|
43
|
+
name: "strict",
|
|
44
|
+
version: "1.0",
|
|
45
|
+
trustedPublishers: [],
|
|
46
|
+
trustedAuditors: [],
|
|
47
|
+
requiredAttestations: [ENACT_TOOL_TYPE, ENACT_AUDIT_TYPE],
|
|
48
|
+
minimumSLSALevel: 2,
|
|
49
|
+
allowUnsigned: false,
|
|
50
|
+
cacheResults: true,
|
|
51
|
+
};
|
|
52
|
+
// ============================================================================
|
|
53
|
+
// Policy Creation
|
|
54
|
+
// ============================================================================
|
|
55
|
+
/**
|
|
56
|
+
* Create a trust policy
|
|
57
|
+
*
|
|
58
|
+
* @param options - Policy options
|
|
59
|
+
* @returns The trust policy
|
|
60
|
+
*
|
|
61
|
+
* @example
|
|
62
|
+
* ```ts
|
|
63
|
+
* const policy = createTrustPolicy({
|
|
64
|
+
* name: "my-org-policy",
|
|
65
|
+
* trustedPublishers: [
|
|
66
|
+
* { name: "My Team", type: "email", pattern: "*@myorg.com" }
|
|
67
|
+
* ],
|
|
68
|
+
* minimumSLSALevel: 1
|
|
69
|
+
* });
|
|
70
|
+
* ```
|
|
71
|
+
*/
|
|
72
|
+
export function createTrustPolicy(options) {
|
|
73
|
+
return {
|
|
74
|
+
...DEFAULT_TRUST_POLICY,
|
|
75
|
+
...options,
|
|
76
|
+
version: options.version || "1.0",
|
|
77
|
+
};
|
|
78
|
+
}
|
|
79
|
+
/**
|
|
80
|
+
* Create a trusted identity rule
|
|
81
|
+
*
|
|
82
|
+
* @param name - Rule name
|
|
83
|
+
* @param type - Identity type
|
|
84
|
+
* @param pattern - Pattern to match
|
|
85
|
+
* @param options - Additional options
|
|
86
|
+
* @returns The identity rule
|
|
87
|
+
*/
|
|
88
|
+
export function createIdentityRule(name, type, pattern, options = {}) {
|
|
89
|
+
const rule = {
|
|
90
|
+
name,
|
|
91
|
+
type,
|
|
92
|
+
pattern,
|
|
93
|
+
};
|
|
94
|
+
if (options.issuer) {
|
|
95
|
+
rule.issuer = options.issuer;
|
|
96
|
+
}
|
|
97
|
+
if (options.requiredClaims) {
|
|
98
|
+
rule.requiredClaims = options.requiredClaims;
|
|
99
|
+
}
|
|
100
|
+
return rule;
|
|
101
|
+
}
|
|
102
|
+
// ============================================================================
|
|
103
|
+
// Policy Evaluation
|
|
104
|
+
// ============================================================================
|
|
105
|
+
/**
|
|
106
|
+
* Evaluate trust policy for a set of attestations
|
|
107
|
+
*
|
|
108
|
+
* @param attestationBundles - Array of Sigstore bundles containing attestations
|
|
109
|
+
* @param policy - The trust policy to evaluate against
|
|
110
|
+
* @returns The trust policy evaluation result
|
|
111
|
+
*
|
|
112
|
+
* @example
|
|
113
|
+
* ```ts
|
|
114
|
+
* const result = await evaluateTrustPolicy(bundles, myPolicy);
|
|
115
|
+
* if (result.trusted) {
|
|
116
|
+
* console.log(`Trusted at level ${result.trustLevel}`);
|
|
117
|
+
* }
|
|
118
|
+
* ```
|
|
119
|
+
*/
|
|
120
|
+
export async function evaluateTrustPolicy(attestationBundles, policy) {
|
|
121
|
+
const result = {
|
|
122
|
+
trusted: false,
|
|
123
|
+
trustLevel: 0,
|
|
124
|
+
matchedAuditors: [],
|
|
125
|
+
details: {
|
|
126
|
+
attestations: [],
|
|
127
|
+
violations: [],
|
|
128
|
+
warnings: [],
|
|
129
|
+
},
|
|
130
|
+
};
|
|
131
|
+
// If no attestations and unsigned allowed, trust with level 0
|
|
132
|
+
if (attestationBundles.length === 0) {
|
|
133
|
+
if (policy.allowUnsigned) {
|
|
134
|
+
result.trusted = true;
|
|
135
|
+
result.details.warnings.push("No attestations found - trusting unsigned artifact");
|
|
136
|
+
return result;
|
|
137
|
+
}
|
|
138
|
+
result.details.violations.push("No attestations found and policy requires signed artifacts");
|
|
139
|
+
return result;
|
|
140
|
+
}
|
|
141
|
+
// Verify all attestation bundles and extract information
|
|
142
|
+
const verifiedAttestations = [];
|
|
143
|
+
for (const bundle of attestationBundles) {
|
|
144
|
+
try {
|
|
145
|
+
const verificationResult = await verifyBundle(bundle);
|
|
146
|
+
if (!verificationResult.verified) {
|
|
147
|
+
result.details.violations.push(`Attestation verification failed: ${verificationResult.error}`);
|
|
148
|
+
continue;
|
|
149
|
+
}
|
|
150
|
+
// Extract attestation from DSSE envelope
|
|
151
|
+
const attestation = extractAttestationFromBundle(bundle);
|
|
152
|
+
if (!attestation) {
|
|
153
|
+
result.details.warnings.push("Could not extract attestation from bundle");
|
|
154
|
+
continue;
|
|
155
|
+
}
|
|
156
|
+
const identity = extractIdentityFromBundle(bundle);
|
|
157
|
+
if (!identity) {
|
|
158
|
+
result.details.warnings.push("Could not extract identity from bundle");
|
|
159
|
+
continue;
|
|
160
|
+
}
|
|
161
|
+
verifiedAttestations.push({
|
|
162
|
+
type: attestation.predicateType,
|
|
163
|
+
predicateType: attestation.predicateType,
|
|
164
|
+
signer: identity,
|
|
165
|
+
verifiedAt: new Date(),
|
|
166
|
+
attestation,
|
|
167
|
+
});
|
|
168
|
+
}
|
|
169
|
+
catch (error) {
|
|
170
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
171
|
+
result.details.violations.push(`Attestation verification error: ${message}`);
|
|
172
|
+
}
|
|
173
|
+
}
|
|
174
|
+
result.details.attestations = verifiedAttestations;
|
|
175
|
+
// Check required attestation types
|
|
176
|
+
if (policy.requiredAttestations && policy.requiredAttestations.length > 0) {
|
|
177
|
+
const foundTypes = new Set(verifiedAttestations.map((a) => a.predicateType));
|
|
178
|
+
for (const required of policy.requiredAttestations) {
|
|
179
|
+
if (!foundTypes.has(required)) {
|
|
180
|
+
result.details.violations.push(`Required attestation type not found: ${required}`);
|
|
181
|
+
}
|
|
182
|
+
}
|
|
183
|
+
}
|
|
184
|
+
// Find matching publisher
|
|
185
|
+
const publisherAttestation = verifiedAttestations.find((a) => a.predicateType === ENACT_TOOL_TYPE);
|
|
186
|
+
if (publisherAttestation) {
|
|
187
|
+
const matchedPublisher = findMatchingRule(publisherAttestation.signer, policy.trustedPublishers);
|
|
188
|
+
if (matchedPublisher) {
|
|
189
|
+
result.matchedPublisher = matchedPublisher;
|
|
190
|
+
result.trustLevel = Math.max(result.trustLevel, 1);
|
|
191
|
+
}
|
|
192
|
+
else if (policy.trustedPublishers.length > 0) {
|
|
193
|
+
result.details.violations.push("Publisher identity does not match any trusted publisher rule");
|
|
194
|
+
}
|
|
195
|
+
}
|
|
196
|
+
// Find matching auditors
|
|
197
|
+
const auditorAttestations = verifiedAttestations.filter((a) => a.predicateType === ENACT_AUDIT_TYPE);
|
|
198
|
+
for (const auditorAttestation of auditorAttestations) {
|
|
199
|
+
const matchedAuditor = findMatchingRule(auditorAttestation.signer, policy.trustedAuditors);
|
|
200
|
+
if (matchedAuditor) {
|
|
201
|
+
result.matchedAuditors.push(matchedAuditor);
|
|
202
|
+
result.trustLevel = Math.max(result.trustLevel, 2);
|
|
203
|
+
}
|
|
204
|
+
}
|
|
205
|
+
// Check SLSA provenance for higher trust levels
|
|
206
|
+
const provenanceAttestation = verifiedAttestations.find((a) => a.predicateType === SLSA_PROVENANCE_TYPE);
|
|
207
|
+
if (provenanceAttestation) {
|
|
208
|
+
const slsaLevel = determineSLSALevel(provenanceAttestation.attestation);
|
|
209
|
+
result.trustLevel = Math.max(result.trustLevel, slsaLevel);
|
|
210
|
+
}
|
|
211
|
+
// Check minimum SLSA level
|
|
212
|
+
if (policy.minimumSLSALevel && result.trustLevel < policy.minimumSLSALevel) {
|
|
213
|
+
result.details.violations.push(`Trust level ${result.trustLevel} is below minimum required ${policy.minimumSLSALevel}`);
|
|
214
|
+
}
|
|
215
|
+
// Determine final trust status
|
|
216
|
+
result.trusted = result.details.violations.length === 0;
|
|
217
|
+
return result;
|
|
218
|
+
}
|
|
219
|
+
/**
|
|
220
|
+
* Quick check if an artifact should be trusted
|
|
221
|
+
*
|
|
222
|
+
* @param attestationBundles - Array of Sigstore bundles
|
|
223
|
+
* @param policy - Trust policy (defaults to DEFAULT_TRUST_POLICY)
|
|
224
|
+
* @returns True if artifact is trusted
|
|
225
|
+
*/
|
|
226
|
+
export async function isTrusted(attestationBundles, policy = DEFAULT_TRUST_POLICY) {
|
|
227
|
+
const result = await evaluateTrustPolicy(attestationBundles, policy);
|
|
228
|
+
return result.trusted;
|
|
229
|
+
}
|
|
230
|
+
// ============================================================================
|
|
231
|
+
// Helper Functions
|
|
232
|
+
// ============================================================================
|
|
233
|
+
/**
|
|
234
|
+
* Find a matching identity rule for the given identity
|
|
235
|
+
*/
|
|
236
|
+
function findMatchingRule(identity, rules) {
|
|
237
|
+
for (const rule of rules) {
|
|
238
|
+
if (matchesIdentityRule(identity, rule)) {
|
|
239
|
+
return rule;
|
|
240
|
+
}
|
|
241
|
+
}
|
|
242
|
+
return undefined;
|
|
243
|
+
}
|
|
244
|
+
/**
|
|
245
|
+
* Check if an identity matches a rule
|
|
246
|
+
*/
|
|
247
|
+
function matchesIdentityRule(identity, rule) {
|
|
248
|
+
// Check issuer first if specified
|
|
249
|
+
if (rule.issuer && identity.issuer !== rule.issuer) {
|
|
250
|
+
return false;
|
|
251
|
+
}
|
|
252
|
+
// Match based on rule type
|
|
253
|
+
switch (rule.type) {
|
|
254
|
+
case "email":
|
|
255
|
+
return matchesPattern(identity.email || "", rule.pattern);
|
|
256
|
+
case "github-workflow":
|
|
257
|
+
return matchesPattern(identity.workflowRepository || "", rule.pattern);
|
|
258
|
+
case "gitlab-pipeline":
|
|
259
|
+
// GitLab uses subject for pipeline identity
|
|
260
|
+
return matchesPattern(identity.subject, rule.pattern);
|
|
261
|
+
case "uri":
|
|
262
|
+
return matchesPattern(identity.subject, rule.pattern);
|
|
263
|
+
default:
|
|
264
|
+
return false;
|
|
265
|
+
}
|
|
266
|
+
}
|
|
267
|
+
/**
|
|
268
|
+
* Match a value against a glob-like pattern
|
|
269
|
+
* Supports * for any characters and ? for single character
|
|
270
|
+
*/
|
|
271
|
+
function matchesPattern(value, pattern) {
|
|
272
|
+
// Convert glob pattern to regex
|
|
273
|
+
const regexPattern = pattern
|
|
274
|
+
.replace(/[.+^${}()|[\]\\]/g, "\\$&") // Escape regex special chars
|
|
275
|
+
.replace(/\*/g, ".*") // * matches any characters
|
|
276
|
+
.replace(/\?/g, "."); // ? matches single character
|
|
277
|
+
const regex = new RegExp(`^${regexPattern}$`, "i");
|
|
278
|
+
return regex.test(value);
|
|
279
|
+
}
|
|
280
|
+
/**
|
|
281
|
+
* Extract in-toto statement from a Sigstore bundle
|
|
282
|
+
*/
|
|
283
|
+
function extractAttestationFromBundle(bundle) {
|
|
284
|
+
if (!bundle.dsseEnvelope?.payload) {
|
|
285
|
+
return undefined;
|
|
286
|
+
}
|
|
287
|
+
try {
|
|
288
|
+
const payloadJson = Buffer.from(bundle.dsseEnvelope.payload, "base64").toString("utf8");
|
|
289
|
+
return JSON.parse(payloadJson);
|
|
290
|
+
}
|
|
291
|
+
catch {
|
|
292
|
+
return undefined;
|
|
293
|
+
}
|
|
294
|
+
}
|
|
295
|
+
/**
|
|
296
|
+
* Determine SLSA level from provenance attestation
|
|
297
|
+
*/
|
|
298
|
+
function determineSLSALevel(attestation) {
|
|
299
|
+
if (attestation.predicateType !== SLSA_PROVENANCE_TYPE) {
|
|
300
|
+
return 0;
|
|
301
|
+
}
|
|
302
|
+
// biome-ignore lint/suspicious/noExplicitAny: Predicate structure varies
|
|
303
|
+
const predicate = attestation.predicate;
|
|
304
|
+
// SLSA Level 1: Provenance exists
|
|
305
|
+
if (!predicate?.buildDefinition || !predicate?.runDetails) {
|
|
306
|
+
return 0;
|
|
307
|
+
}
|
|
308
|
+
let level = 1;
|
|
309
|
+
// SLSA Level 2: Hosted build platform
|
|
310
|
+
if (predicate.runDetails?.builder?.id) {
|
|
311
|
+
level = 2;
|
|
312
|
+
}
|
|
313
|
+
// SLSA Level 3: Hardened builds (check for specific builder features)
|
|
314
|
+
if (predicate.buildDefinition?.internalParameters &&
|
|
315
|
+
predicate.buildDefinition?.resolvedDependencies) {
|
|
316
|
+
level = 3;
|
|
317
|
+
}
|
|
318
|
+
// SLSA Level 4: Would require additional verification of builder security
|
|
319
|
+
// This is simplified - real implementation would check builder attestations
|
|
320
|
+
return level;
|
|
321
|
+
}
|
|
322
|
+
// ============================================================================
|
|
323
|
+
// Policy Serialization
|
|
324
|
+
// ============================================================================
|
|
325
|
+
/**
|
|
326
|
+
* Serialize a trust policy to JSON
|
|
327
|
+
*/
|
|
328
|
+
export function serializeTrustPolicy(policy) {
|
|
329
|
+
return JSON.stringify(policy, null, 2);
|
|
330
|
+
}
|
|
331
|
+
/**
|
|
332
|
+
* Deserialize a trust policy from JSON
|
|
333
|
+
*/
|
|
334
|
+
export function deserializeTrustPolicy(json) {
|
|
335
|
+
const parsed = JSON.parse(json);
|
|
336
|
+
// Validate required fields
|
|
337
|
+
if (!parsed.name || typeof parsed.name !== "string") {
|
|
338
|
+
throw new Error("Invalid trust policy: missing or invalid name");
|
|
339
|
+
}
|
|
340
|
+
if (!Array.isArray(parsed.trustedPublishers)) {
|
|
341
|
+
throw new Error("Invalid trust policy: trustedPublishers must be an array");
|
|
342
|
+
}
|
|
343
|
+
if (!Array.isArray(parsed.trustedAuditors)) {
|
|
344
|
+
throw new Error("Invalid trust policy: trustedAuditors must be an array");
|
|
345
|
+
}
|
|
346
|
+
return {
|
|
347
|
+
...DEFAULT_TRUST_POLICY,
|
|
348
|
+
...parsed,
|
|
349
|
+
};
|
|
350
|
+
}
|
|
351
|
+
//# sourceMappingURL=policy.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"policy.js","sourceRoot":"","sources":["../../src/sigstore/policy.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,94 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* OIDC-based keyless signing using Sigstore
|
|
3
|
+
*
|
|
4
|
+
* This module provides keyless signing capabilities using OIDC identity tokens.
|
|
5
|
+
* It integrates with Fulcio for certificate issuance and Rekor for transparency logging.
|
|
6
|
+
*
|
|
7
|
+
* For CI environments (GitHub Actions, GitLab CI, etc.), the sigstore library's
|
|
8
|
+
* native OIDC support is used. For interactive local signing, we use a native
|
|
9
|
+
* OAuth implementation that opens a browser for authentication.
|
|
10
|
+
*/
|
|
11
|
+
import { type SignOptions } from "sigstore";
|
|
12
|
+
import type { SigningOptions as EnactSigningOptions, FulcioCertificate, OIDCIdentity, OIDCProvider, SigningResult, SigstoreBundle } from "./types";
|
|
13
|
+
export type { SignOptions };
|
|
14
|
+
/** Public Sigstore Fulcio URL */
|
|
15
|
+
export declare const FULCIO_PUBLIC_URL = "https://fulcio.sigstore.dev";
|
|
16
|
+
/** Public Sigstore Rekor URL */
|
|
17
|
+
export declare const REKOR_PUBLIC_URL = "https://rekor.sigstore.dev";
|
|
18
|
+
/** Public Sigstore TSA URL */
|
|
19
|
+
export declare const TSA_PUBLIC_URL = "https://timestamp.sigstore.dev";
|
|
20
|
+
/** OIDC issuer URLs for known providers */
|
|
21
|
+
export declare const OIDC_ISSUERS: Record<OIDCProvider, string>;
|
|
22
|
+
/**
|
|
23
|
+
* Detect OIDC provider from issuer URL
|
|
24
|
+
*/
|
|
25
|
+
export declare function detectOIDCProvider(issuer: string): OIDCProvider;
|
|
26
|
+
/**
|
|
27
|
+
* Extract identity information from an OIDC token
|
|
28
|
+
*
|
|
29
|
+
* @param token - The OIDC identity token
|
|
30
|
+
* @returns Extracted identity information
|
|
31
|
+
*/
|
|
32
|
+
export declare function extractOIDCIdentity(token: string): OIDCIdentity;
|
|
33
|
+
/**
|
|
34
|
+
* Get OIDC token from environment (for CI/CD environments)
|
|
35
|
+
*
|
|
36
|
+
* @param provider - The OIDC provider
|
|
37
|
+
* @returns The OIDC token if available
|
|
38
|
+
*/
|
|
39
|
+
export declare function getOIDCTokenFromEnvironment(provider: OIDCProvider): string | undefined;
|
|
40
|
+
/**
|
|
41
|
+
* Sign an artifact using keyless (OIDC) signing
|
|
42
|
+
*
|
|
43
|
+
* In CI environments with native OIDC support (GitHub Actions, GitLab CI),
|
|
44
|
+
* uses the sigstore library directly. For interactive local signing,
|
|
45
|
+
* uses native OAuth implementation that opens browser for authentication.
|
|
46
|
+
*
|
|
47
|
+
* @param artifact - The artifact to sign (as a Buffer)
|
|
48
|
+
* @param options - Signing options
|
|
49
|
+
* @returns The signing result including the Sigstore bundle
|
|
50
|
+
*
|
|
51
|
+
* @example
|
|
52
|
+
* ```ts
|
|
53
|
+
* const artifact = Buffer.from(JSON.stringify(manifest));
|
|
54
|
+
* const result = await signArtifact(artifact, {
|
|
55
|
+
* oidc: { provider: "github" }
|
|
56
|
+
* });
|
|
57
|
+
* console.log(result.bundle);
|
|
58
|
+
* ```
|
|
59
|
+
*/
|
|
60
|
+
export declare function signArtifact(artifact: Buffer, options?: EnactSigningOptions): Promise<SigningResult>;
|
|
61
|
+
/**
|
|
62
|
+
* Sign an in-toto attestation using keyless signing
|
|
63
|
+
*
|
|
64
|
+
* In CI environments with native OIDC support, uses the sigstore library.
|
|
65
|
+
* For interactive local signing, uses native OAuth with browser authentication.
|
|
66
|
+
*
|
|
67
|
+
* @param attestation - The attestation to sign (in-toto statement)
|
|
68
|
+
* @param options - Signing options
|
|
69
|
+
* @returns The signing result including the Sigstore bundle
|
|
70
|
+
*
|
|
71
|
+
* @example
|
|
72
|
+
* ```ts
|
|
73
|
+
* const statement = {
|
|
74
|
+
* _type: "https://in-toto.io/Statement/v1",
|
|
75
|
+
* subject: [{ name: "tool.yaml", digest: { sha256: "abc123..." } }],
|
|
76
|
+
* predicateType: "https://slsa.dev/provenance/v1",
|
|
77
|
+
* predicate: { ... }
|
|
78
|
+
* };
|
|
79
|
+
* const result = await signAttestation(statement, { oidc: { provider: "github" } });
|
|
80
|
+
* ```
|
|
81
|
+
*/
|
|
82
|
+
export declare function signAttestation(attestation: Record<string, unknown>, options?: EnactSigningOptions): Promise<SigningResult>;
|
|
83
|
+
/**
|
|
84
|
+
* Extract certificate information from a Sigstore bundle
|
|
85
|
+
*/
|
|
86
|
+
export declare function extractCertificateFromBundle(bundle: SigstoreBundle): FulcioCertificate | undefined;
|
|
87
|
+
/**
|
|
88
|
+
* Extract identity from a signing certificate in a bundle
|
|
89
|
+
*
|
|
90
|
+
* @param bundle - The Sigstore bundle
|
|
91
|
+
* @returns The OIDC identity if it can be extracted
|
|
92
|
+
*/
|
|
93
|
+
export declare function extractIdentityFromBundle(bundle: SigstoreBundle): OIDCIdentity | undefined;
|
|
94
|
+
//# sourceMappingURL=signing.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"signing.d.ts","sourceRoot":"","sources":["../../src/sigstore/signing.ts"],"names":[],"mappings":"AAAA;;;;;;;;;GASG;AAEH,OAAO,EAAE,KAAK,WAAW,EAAgB,MAAM,UAAU,CAAC;AAG1D,OAAO,KAAK,EACV,cAAc,IAAI,mBAAmB,EACrC,iBAAiB,EACjB,YAAY,EACZ,YAAY,EACZ,aAAa,EACb,cAAc,EACf,MAAM,SAAS,CAAC;AAGjB,YAAY,EAAE,WAAW,EAAE,CAAC;AAM5B,iCAAiC;AACjC,eAAO,MAAM,iBAAiB,gCAAgC,CAAC;AAE/D,gCAAgC;AAChC,eAAO,MAAM,gBAAgB,+BAA+B,CAAC;AAE7D,8BAA8B;AAC9B,eAAO,MAAM,cAAc,mCAAmC,CAAC;AAE/D,2CAA2C;AAC3C,eAAO,MAAM,YAAY,EAAE,MAAM,CAAC,YAAY,EAAE,MAAM,CAMrD,CAAC;AA+BF;;GAEG;AACH,wBAAgB,kBAAkB,CAAC,MAAM,EAAE,MAAM,GAAG,YAAY,CAO/D;AAED;;;;;GAKG;AACH,wBAAgB,mBAAmB,CAAC,KAAK,EAAE,MAAM,GAAG,YAAY,CAgC/D;AAED;;;;;GAKG;AACH,wBAAgB,2BAA2B,CAAC,QAAQ,EAAE,YAAY,GAAG,MAAM,GAAG,SAAS,CAUtF;AAoCD;;;;;;;;;;;;;;;;;;;GAmBG;AACH,wBAAsB,YAAY,CAChC,QAAQ,EAAE,MAAM,EAChB,OAAO,GAAE,mBAAwB,GAChC,OAAO,CAAC,aAAa,CAAC,CAgGxB;AAED;;;;;;;;;;;;;;;;;;;;GAoBG;AACH,wBAAsB,eAAe,CACnC,WAAW,EAAE,MAAM,CAAC,MAAM,EAAE,OAAO,CAAC,EACpC,OAAO,GAAE,mBAAwB,GAChC,OAAO,CAAC,aAAa,CAAC,CAmGxB;AA2ED;;GAEG;AACH,wBAAgB,4BAA4B,CAC1C,MAAM,EAAE,cAAc,GACrB,iBAAiB,GAAG,SAAS,CAmD/B;AAED;;;;;GAKG;AACH,wBAAgB,yBAAyB,CAAC,MAAM,EAAE,cAAc,GAAG,YAAY,GAAG,SAAS,CAI1F"}
|