@highstate/pulumi 0.9.14 → 0.9.16

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.
@@ -1,5 +1,5 @@
1
1
  {
2
2
  "sourceHashes": {
3
- "./dist/index.js": "ca5a8f5fbd4902dafff12ecf47d4fce297408be2286d8e8cf6e1d42abd2c9624"
3
+ "./dist/index.js": 2152865667
4
4
  }
5
5
  }
package/dist/index.js CHANGED
@@ -1,24 +1,11 @@
1
- // src/index.ts
2
- export * from "@pulumi/pulumi";
3
-
4
- // src/unit.ts
5
- import {
6
- parseInstanceId,
7
- getInstanceId
8
- } from "@highstate/contract";
9
- import { Type } from "@sinclair/typebox";
10
- import { mapValues, pickBy, pipe } from "remeda";
11
- import {
12
- Config,
13
- getStack,
14
- output,
15
- secret as secret2,
16
- StackReference
17
- } from "@pulumi/pulumi";
18
- import { Ajv } from "ajv";
1
+ import { getStack, secret, Config, output, all, StackReference } from '@pulumi/pulumi';
2
+ export * from '@pulumi/pulumi';
3
+ import { getInstanceId, camelCaseToHumanReadable, HighstateSignature, parseInstanceId } from '@highstate/contract';
4
+ import { Type } from '@sinclair/typebox';
5
+ import { mapValues, pipe, pickBy } from 'remeda';
6
+ import { Ajv } from 'ajv';
19
7
 
20
- // src/secret.ts
21
- import { secret } from "@pulumi/pulumi";
8
+ // src/index.ts
22
9
  var createdSecrets = {};
23
10
  function getOrCreateSecret(secrets, key, create) {
24
11
  return secrets[key].apply((value) => {
@@ -68,12 +55,16 @@ function getOutput(unit, input, refs) {
68
55
  const _getOutput = (ref) => {
69
56
  const value = getStackRef(ref).requireOutput(ref.output);
70
57
  return value.apply((value2) => {
71
- let schema = entity.schema;
72
- if (input.multiple) {
73
- schema = Type.Union([schema, Type.Array(schema)]);
74
- }
75
- if (!ajv.validate(schema, value2)) {
76
- throw new Error(`Invalid output for '${input.type}': ${ajv.errorsText()}`);
58
+ if (Array.isArray(value2)) {
59
+ for (const [index, item] of value2.entries()) {
60
+ if (!ajv.validate(entity.schema, item)) {
61
+ throw new Error(`Invalid output for '${input.type}[${index}]': ${ajv.errorsText()}`);
62
+ }
63
+ }
64
+ } else {
65
+ if (!ajv.validate(entity.schema, value2)) {
66
+ throw new Error(`Invalid output for '${input.type}': ${ajv.errorsText()}`);
67
+ }
77
68
  }
78
69
  if (Array.isArray(value2)) {
79
70
  return value2;
@@ -127,15 +118,38 @@ function forUnit(unit) {
127
118
  const args = mapValues(unit.model.args, (arg, argName) => {
128
119
  switch (true) {
129
120
  case isStringSchema(arg.schema): {
130
- return arg.required ? config.require(argName) : config.get(argName) ?? arg.schema.default;
121
+ if (arg.required) {
122
+ return config.require(argName);
123
+ }
124
+ return config.get(argName) || arg.schema.default;
131
125
  }
132
126
  case isNumberSchema(arg.schema): {
133
- return arg.required ? config.requireNumber(argName) : config.getNumber(argName) ?? arg.schema.default;
127
+ if (arg.required) {
128
+ return config.requireNumber(argName);
129
+ }
130
+ const value = config.get(argName);
131
+ if (!value) {
132
+ return arg.schema.default;
133
+ }
134
+ return config.getNumber(argName) ?? arg.schema.default;
134
135
  }
135
136
  case isBooleanSchema(arg.schema): {
136
- return arg.required ? config.requireBoolean(argName) : config.getBoolean(argName) ?? arg.schema.default;
137
+ if (arg.required) {
138
+ return config.requireBoolean(argName);
139
+ }
140
+ const value = config.get(argName);
141
+ if (!value) {
142
+ return arg.schema.default;
143
+ }
144
+ return config.getBoolean(argName) ?? arg.schema.default;
137
145
  }
138
146
  default: {
147
+ if (!arg.required) {
148
+ const value2 = config.get(argName);
149
+ if (!value2) {
150
+ return arg.schema.default;
151
+ }
152
+ }
139
153
  const value = arg.required ? config.requireObject(argName) : config.getObject(argName);
140
154
  if (value === void 0) return arg.schema.default;
141
155
  if (!ajv.validate(arg.schema, value)) {
@@ -189,15 +203,12 @@ function forUnit(unit) {
189
203
  invokedTriggers: config.getObject("$invokedTriggers") ?? [],
190
204
  outputs: async (outputs = {}) => {
191
205
  const result = mapValues(outputs, (outputValue, outputName) => {
192
- if (outputName === "$status") {
193
- return output(outputValue).apply(mapStatus);
206
+ if (outputName === "$statusFields") {
207
+ return output(outputValue).apply(mapStatusFields);
194
208
  }
195
209
  if (outputName === "$pages") {
196
210
  return output(outputValue).apply(mapPages);
197
211
  }
198
- if (outputName === "$files") {
199
- return output(outputValue).apply(mapFiles);
200
- }
201
212
  if (outputName === "$terminals") {
202
213
  return output(outputValue).apply(mapTerminals);
203
214
  }
@@ -235,6 +246,19 @@ function forUnit(unit) {
235
246
  if (Object.keys(createdSecrets).length > 0) {
236
247
  result.$secrets = createdSecrets;
237
248
  }
249
+ const artifactsMap = {};
250
+ for (const [outputName, outputValue] of Object.entries(outputs)) {
251
+ if (!outputName.startsWith("$")) {
252
+ const resolvedValue = await outputToPromise(outputValue);
253
+ const artifacts = extractArtifactsFromValue(resolvedValue);
254
+ if (artifacts.length > 0) {
255
+ artifactsMap[outputName] = artifacts;
256
+ }
257
+ }
258
+ }
259
+ if (Object.keys(artifactsMap).length > 0) {
260
+ result.$artifacts = artifactsMap;
261
+ }
238
262
  return result;
239
263
  }
240
264
  };
@@ -242,21 +266,42 @@ function forUnit(unit) {
242
266
  function outputToPromise(o) {
243
267
  return new Promise((resolve) => output(o).apply(resolve));
244
268
  }
245
- function mapStatus(status) {
269
+ function mapStatusFields(status) {
246
270
  if (!status) {
247
271
  return [];
248
272
  }
249
273
  if (Array.isArray(status)) {
250
- return status.filter((field) => !!field?.value);
274
+ return status.filter((field) => !!field?.value).map((field) => {
275
+ return {
276
+ name: field.name,
277
+ meta: {
278
+ title: field.meta?.title ?? camelCaseToHumanReadable(field.name)
279
+ },
280
+ value: field.value
281
+ };
282
+ });
251
283
  }
252
284
  return Object.entries(status).map(([name, field]) => {
253
285
  if (!field) {
254
286
  return void 0;
255
287
  }
256
288
  if (typeof field === "string" || typeof field === "number" || typeof field === "boolean" || Array.isArray(field)) {
257
- return { name, value: field };
289
+ return {
290
+ name,
291
+ meta: {
292
+ title: camelCaseToHumanReadable(name)
293
+ },
294
+ value: field
295
+ };
258
296
  }
259
- return { ...field, name };
297
+ return {
298
+ ...field,
299
+ meta: {
300
+ ...field.meta,
301
+ title: field.meta?.title ?? camelCaseToHumanReadable(name)
302
+ },
303
+ name
304
+ };
260
305
  }).filter((field) => !!field?.value);
261
306
  }
262
307
  function mapPages(pages) {
@@ -275,7 +320,10 @@ function fileFromString(name, content, contentType = "text/plain", isSecret = fa
275
320
  contentType,
276
321
  size: Buffer.byteLength(content, "utf8")
277
322
  },
278
- content: isSecret ? secret2(content) : content
323
+ content: {
324
+ type: "embedded",
325
+ value: isSecret ? secret(content) : content
326
+ }
279
327
  };
280
328
  }
281
329
  function fileFromBuffer(name, content, contentType = "application/octet-stream", isSecret = false) {
@@ -286,12 +334,12 @@ function fileFromBuffer(name, content, contentType = "application/octet-stream",
286
334
  size: content.byteLength,
287
335
  isBinary: true
288
336
  },
289
- content: isSecret ? secret2(content.toString("base64")) : content.toString("base64")
337
+ content: {
338
+ type: "embedded",
339
+ value: isSecret ? secret(content.toString("base64")) : content.toString("base64")
340
+ }
290
341
  };
291
342
  }
292
- function mapFiles(files) {
293
- return files?.filter((file) => !!file) ?? [];
294
- }
295
343
  function mapTerminals(terminals) {
296
344
  if (!terminals) {
297
345
  return [];
@@ -305,21 +353,34 @@ function mapTerminals(terminals) {
305
353
  });
306
354
  }
307
355
  return terminals.filter((terminal) => !!terminal).map((terminal) => {
308
- if (!terminal.files) {
356
+ if (!terminal.spec.files) {
309
357
  return terminal;
310
358
  }
311
359
  return {
312
360
  ...terminal,
313
- files: pipe(
314
- terminal.files,
315
- mapValues((file) => {
316
- if (typeof file === "string") {
317
- return { content: file };
318
- }
319
- return file;
320
- }),
321
- pickBy((value) => !!value?.content)
322
- )
361
+ spec: {
362
+ ...terminal.spec,
363
+ files: pipe(
364
+ terminal.spec.files,
365
+ mapValues((file) => {
366
+ if (typeof file === "string") {
367
+ return {
368
+ meta: {
369
+ name: "content",
370
+ contentType: "text/plain",
371
+ size: Buffer.byteLength(file, "utf8")
372
+ },
373
+ content: {
374
+ type: "embedded",
375
+ value: file
376
+ }
377
+ };
378
+ }
379
+ return file;
380
+ }),
381
+ pickBy((value) => !!value)
382
+ )
383
+ }
323
384
  };
324
385
  });
325
386
  }
@@ -332,9 +393,32 @@ function mapTriggers(triggers) {
332
393
  }
333
394
  return Object.entries(triggers).filter(([, trigger]) => !!trigger).map(([name, trigger]) => ({ ...trigger, name }));
334
395
  }
335
-
336
- // src/utils.ts
337
- import { output as output2, all } from "@pulumi/pulumi";
396
+ function extractArtifactsFromValue(data) {
397
+ const artifacts = [];
398
+ function traverse(obj) {
399
+ if (obj === null || obj === void 0 || typeof obj !== "object") {
400
+ return;
401
+ }
402
+ if (Array.isArray(obj)) {
403
+ for (const item of obj) {
404
+ traverse(item);
405
+ }
406
+ return;
407
+ }
408
+ const record = obj;
409
+ if (HighstateSignature.Artifact in record) {
410
+ const artifactData = record[HighstateSignature.Artifact];
411
+ artifacts.push(artifactData);
412
+ record[HighstateSignature.Artifact] = { hash: artifactData.hash };
413
+ return;
414
+ }
415
+ for (const value of Object.values(record)) {
416
+ traverse(value);
417
+ }
418
+ }
419
+ traverse(data);
420
+ return artifacts;
421
+ }
338
422
  function flattenInputs(...values) {
339
423
  return all(values).apply((allValues) => {
340
424
  const result = [];
@@ -349,7 +433,7 @@ function flattenInputs(...values) {
349
433
  });
350
434
  }
351
435
  function mapInputs(array, fn) {
352
- return output2(array).apply((array2) => {
436
+ return output(array).apply((array2) => {
353
437
  return array2?.map((v, index) => fn(v, index, array2)) ?? [];
354
438
  });
355
439
  }
@@ -365,7 +449,7 @@ function mapOptional(input, func) {
365
449
  return func(input);
366
450
  }
367
451
  function toPromise(input) {
368
- return new Promise((resolve) => output2(input).apply(resolve));
452
+ return new Promise((resolve) => output(input).apply(resolve));
369
453
  }
370
454
  function singleton(factory) {
371
455
  let instance;
@@ -386,7 +470,7 @@ function providerFactory(factory) {
386
470
  };
387
471
  }
388
472
  function mergeInputObjects(...objects) {
389
- return output2(objects).apply((array) => {
473
+ return output(objects).apply((array) => {
390
474
  return Object.assign({}, ...array);
391
475
  });
392
476
  }
@@ -400,30 +484,12 @@ function normalize(item, collection) {
400
484
  return collection ?? [];
401
485
  }
402
486
  function apply(fn) {
403
- return (input) => output2(input).apply(fn);
487
+ return (input) => output(input).apply(fn);
404
488
  }
405
489
  function applyMap(fn) {
406
- return (input) => output2(input).apply((array) => array.map(fn));
490
+ return (input) => output(input).apply((array) => array.map(fn));
407
491
  }
408
- export {
409
- apply,
410
- applyMap,
411
- fileFromBuffer,
412
- fileFromString,
413
- flatMapInput,
414
- flattenInputs,
415
- forUnit,
416
- getOrCreateSecret,
417
- getResourceComment,
418
- getUnitInstanceId,
419
- getUnitInstanceName,
420
- mapInputs,
421
- mapOptional,
422
- mergeInputObjects,
423
- normalize,
424
- providerFactory,
425
- singleton,
426
- storeSecret,
427
- toPromise
428
- };
492
+
493
+ export { apply, applyMap, fileFromBuffer, fileFromString, flatMapInput, flattenInputs, forUnit, getOrCreateSecret, getResourceComment, getUnitInstanceId, getUnitInstanceName, mapInputs, mapOptional, mergeInputObjects, normalize, providerFactory, singleton, storeSecret, toPromise };
494
+ //# sourceMappingURL=index.js.map
429
495
  //# sourceMappingURL=index.js.map
package/dist/index.js.map CHANGED
@@ -1 +1 @@
1
- {"version":3,"sources":["../src/index.ts","../src/unit.ts","../src/secret.ts","../src/utils.ts"],"sourcesContent":["export * from \"@pulumi/pulumi\"\nexport * from \"./unit\"\nexport * from \"./utils\"\nexport { getOrCreateSecret, storeSecret } from \"./secret\"\n","/* eslint-disable @typescript-eslint/no-unsafe-assignment */\n/* eslint-disable @typescript-eslint/no-unsafe-member-access */\n/* eslint-disable @typescript-eslint/no-unsafe-argument */\n/* eslint-disable @typescript-eslint/no-unsafe-return */\n/* eslint-disable @typescript-eslint/no-explicit-any */\n\nimport type { DeepInput, InputArray, InputMap } from \"./utils\"\nimport {\n type ArgumentValue,\n type ComponentInputSpec,\n type Entity,\n type Unit,\n type ComponentInput,\n type InstanceInput,\n parseInstanceId,\n type ArgumentValueSchema,\n getInstanceId,\n type ComponentArgumentSpec,\n type ComponentArgumentSpecToStatic,\n} from \"@highstate/contract\"\nimport { Type, type Static } from \"@sinclair/typebox\"\nimport { mapValues, pickBy, pipe } from \"remeda\"\nimport {\n Config,\n getStack,\n Output,\n output,\n secret,\n StackReference,\n type Input,\n type Unwrap,\n} from \"@pulumi/pulumi\"\nimport { Ajv } from \"ajv\"\nimport { createdSecrets } from \"./secret\"\n\nconst ajv = new Ajv({ strict: false })\n\nexport type InstanceTerminalFile = {\n content: Input<string | undefined>\n mode?: Input<number | undefined>\n isBinary?: Input<boolean>\n}\n\nexport type InstanceTerminal = {\n name: Input<string>\n title: Input<string>\n description?: Input<string>\n image: Input<string>\n command: InputArray<string>\n cwd?: Input<string | undefined>\n env?: InputMap<string | undefined>\n files?: InputMap<InstanceTerminalFile | string | undefined>\n}\n\nexport type StatusFieldValue = string | number | boolean | string[]\n\nexport type StatusField<TArgName extends string = string> = {\n name: Input<string>\n value?: Input<StatusFieldValue | undefined>\n displayName?: Input<string | undefined>\n sensitive?: Input<boolean | undefined>\n url?: Input<string | undefined>\n complementaryTo?: Input<TArgName | undefined>\n}\n\nexport type InstanceFileMeta = {\n name: Input<string>\n contentType: Input<string>\n isBinary?: Input<boolean>\n size: Input<number>\n}\n\nexport type InstanceFile = {\n meta: Input<InstanceFileMeta>\n content: Input<string>\n}\n\nexport type InstancePageBlock =\n | { type: \"markdown\"; content: Input<string> }\n | { type: \"qr\"; content: Input<string>; showContent?: boolean; language?: string }\n | { type: \"file\"; fileMeta: Input<InstanceFileMeta> }\n\nexport type InstancePage = {\n name: Input<string>\n title: Input<string>\n content: InputArray<InstancePageBlock>\n}\n\nexport type InstanceTriggerSpec =\n | {\n type: \"before-destroy\"\n }\n | {\n type: \"schedule\"\n schedule: string\n }\n\nexport type InstanceTrigger = {\n name: Input<string>\n title: Input<string>\n description?: Input<string>\n spec: Input<InstanceTriggerSpec>\n}\n\nexport type ExtraOutputs<TArgName extends string = string> = {\n $status?:\n | InputMap<Omit<StatusField<TArgName>, \"name\"> | StatusFieldValue | undefined>\n | InputArray<StatusField<TArgName> | undefined>\n\n $terminals?:\n | InputMap<Omit<InstanceTerminal, \"name\"> | undefined>\n | InputArray<InstanceTerminal | undefined>\n\n $pages?: InputMap<Omit<InstancePage, \"name\"> | undefined> | InputArray<InstancePage | undefined>\n $files?: InputArray<InstanceFile | undefined>\n\n $triggers?:\n | InputMap<Omit<InstanceTrigger, \"name\"> | undefined>\n | InputArray<InstanceTrigger | undefined>\n}\n\nexport type InstanceTriggerInvocation = {\n name: string\n}\n\ntype OutputMapToDeepInputMap<T extends Record<string, unknown>, TArgName extends string> =\n T extends Record<string, never>\n ? ExtraOutputs\n : { [K in keyof T]: DeepInput<T[K]> } & ExtraOutputs<TArgName>\n\nexport interface UnitContext<\n TArgs extends Record<string, ArgumentValue>,\n TInputs extends Record<string, unknown>,\n TOutputs extends Record<string, unknown>,\n TSecrets extends Record<string, ArgumentValue>,\n> {\n args: TArgs\n instanceId: string\n type: string\n name: string\n secrets: Output<TSecrets>\n\n inputs: TInputs extends Record<string, never>\n ? never\n : {\n [K in keyof TInputs]: undefined extends TInputs[K]\n ? Output<NonNullable<TInputs[K]>> | undefined\n : Output<TInputs[K]>\n }\n\n invokedTriggers: InstanceTriggerInvocation[]\n\n outputs(\n this: void,\n outputs?: OutputMapToDeepInputMap<TOutputs, keyof TArgs & string>,\n ): Promise<unknown>\n}\n\ntype InputSpecToValue<T extends ComponentInputSpec> = T[2] extends true\n ? Static<T[0][\"schema\"]>[]\n : T[1] extends true\n ? Static<T[0][\"schema\"]>\n : Static<T[0][\"schema\"]> | undefined\n\ntype InputSpecMapToValueMap<T extends Record<string, ComponentInputSpec>> =\n T extends Record<string, never>\n ? Record<string, never>\n : { [K in keyof T]: InputSpecToValue<T[K]> }\n\nconst stackRefMap = new Map<string, StackReference>()\nconst [projectId, instanceName] = getStack().split(\"_\")\n\nlet instanceId: string | undefined\n\nexport function getUnitInstanceId(): string {\n if (!instanceId) {\n throw new Error(\"Instance id is not set. Did you call 'forUnit' function?\")\n }\n\n return instanceId\n}\n\nexport function getResourceComment(): string {\n return `Managed by Highstate Unit (${getUnitInstanceId()})`\n}\n\nexport function getUnitInstanceName(): string {\n return instanceName\n}\n\nfunction getStackRef(input: InstanceInput) {\n const [instanceType, instanceName] = parseInstanceId(input.instanceId)\n const key = `organization/${instanceType}/${projectId}_${instanceName}`\n\n if (!stackRefMap.has(key)) {\n stackRefMap.set(key, new StackReference(key))\n }\n\n return stackRefMap.get(key)!\n}\n\nfunction getOutput(unit: Unit, input: ComponentInput, refs: InstanceInput[]) {\n const entity = unit.entities.get(input.type)\n if (!entity) {\n throw new Error(`Entity '${input.type}' not found in the unit '${unit.model.type}'.`)\n }\n\n const _getOutput = (ref: InstanceInput) => {\n const value = getStackRef(ref).requireOutput(ref.output)\n\n return value.apply(value => {\n let schema = entity.schema\n\n if (input.multiple) {\n schema = Type.Union([schema, Type.Array(schema)])\n }\n\n if (!ajv.validate(schema, value)) {\n throw new Error(`Invalid output for '${input.type}': ${ajv.errorsText()}`)\n }\n\n if (Array.isArray(value)) {\n return value as unknown\n }\n\n return input.multiple ? [value] : value\n })\n }\n\n const values = output(refs.map(ref => _getOutput(ref))).apply(values => values.flat())\n\n if (!input.multiple) {\n return values.apply(values => values[0])\n }\n\n return values\n}\n\nfunction isAnyOfSchema(schema: ArgumentValueSchema, itemType: string): boolean {\n if (schema.anyOf) {\n return Object.values(schema.anyOf).every(schema =>\n isAnyOfSchema(schema as ArgumentValueSchema, itemType),\n )\n }\n\n return schema.type === itemType\n}\n\nfunction isStringSchema(schema: ArgumentValueSchema): boolean {\n if (schema.type === \"string\") {\n return true\n }\n\n if (isAnyOfSchema(schema, \"string\")) {\n return true\n }\n\n return false\n}\n\nfunction isNumberSchema(schema: ArgumentValueSchema): boolean {\n if (schema.type === \"number\") {\n return true\n }\n\n if (isAnyOfSchema(schema, \"number\")) {\n return true\n }\n\n return false\n}\n\nfunction isBooleanSchema(schema: ArgumentValueSchema): boolean {\n if (schema.type === \"boolean\") {\n return true\n }\n\n if (isAnyOfSchema(schema, \"boolean\")) {\n return true\n }\n\n return false\n}\n\nexport function forUnit<\n TArgs extends Record<string, ComponentArgumentSpec>,\n TInputs extends Record<string, ComponentInputSpec>,\n TOutputs extends Record<string, ComponentInputSpec>,\n TSecrets extends Record<string, ComponentArgumentSpec>,\n>(\n unit: Unit<TArgs, TInputs, TOutputs, TSecrets>,\n): UnitContext<\n //\n ComponentArgumentSpecToStatic<TArgs>,\n InputSpecMapToValueMap<TInputs>,\n InputSpecMapToValueMap<TOutputs>,\n ComponentArgumentSpecToStatic<TSecrets>\n> {\n const config = new Config()\n\n const args = mapValues(unit.model.args, (arg, argName) => {\n switch (true) {\n case isStringSchema(arg.schema): {\n return arg.required ? config.require(argName) : (config.get(argName) ?? arg.schema.default)\n }\n case isNumberSchema(arg.schema): {\n return arg.required\n ? config.requireNumber(argName)\n : (config.getNumber(argName) ?? arg.schema.default)\n }\n case isBooleanSchema(arg.schema): {\n return arg.required\n ? config.requireBoolean(argName)\n : (config.getBoolean(argName) ?? arg.schema.default)\n }\n default: {\n const value = arg.required ? config.requireObject(argName) : config.getObject(argName)\n if (value === undefined) return arg.schema.default\n\n if (!ajv.validate(arg.schema, value)) {\n throw new Error(`Invalid config for '${argName}': ${ajv.errorsText()}`)\n }\n\n return value\n }\n }\n }) as ComponentArgumentSpecToStatic<TArgs>\n\n const secrets = output(\n mapValues(unit.model.secrets, (secret, secretName) => {\n switch (true) {\n case isStringSchema(secret.schema): {\n return secret.required ? config.requireSecret(secretName) : config.getSecret(secretName)\n }\n case isNumberSchema(secret.schema): {\n return secret.required\n ? config.requireSecretNumber(secretName)\n : config.getSecretNumber(secretName)\n }\n case isBooleanSchema(secret.schema): {\n return secret.required\n ? config.requireSecretBoolean(secretName)\n : config.getSecretBoolean(secretName)\n }\n default: {\n const value = secret.required\n ? config.requireSecretObject(secretName)\n : config.getSecretObject(secretName)\n\n if (!ajv.validate(secret.schema, value)) {\n throw new Error(`Invalid secret for '${secretName}': ${ajv.errorsText()}`)\n }\n\n return value\n }\n }\n }),\n ) as unknown as Output<ComponentArgumentSpecToStatic<TSecrets>>\n\n const inputs = mapValues(unit.model.inputs, (input, inputName) => {\n const value = input.required\n ? config.requireObject<InstanceInput[]>(`input.${inputName}`)\n : config.getObject<InstanceInput[]>(`input.${inputName}`)\n\n if (!value) {\n if (input.multiple) {\n return output([])\n }\n\n return undefined\n }\n\n return getOutput(unit as unknown as Unit, input, value)\n })\n\n const type = unit.model.type\n instanceId = getInstanceId(type, instanceName)\n\n return {\n args,\n instanceId,\n type,\n name: instanceName,\n secrets,\n inputs: inputs as any,\n invokedTriggers: config.getObject<InstanceTriggerInvocation[]>(\"$invokedTriggers\") ?? [],\n\n outputs: async (outputs: any = {}) => {\n const result: any = mapValues(outputs, (outputValue, outputName) => {\n if (outputName === \"$status\") {\n return output(outputValue).apply(mapStatus)\n }\n\n if (outputName === \"$pages\") {\n return output(outputValue).apply(mapPages)\n }\n\n if (outputName === \"$files\") {\n return output(outputValue).apply(mapFiles)\n }\n\n if (outputName === \"$terminals\") {\n return output(outputValue).apply(mapTerminals)\n }\n\n if (outputName === \"$triggers\") {\n return output(outputValue).apply(mapTriggers)\n }\n\n if (outputName.startsWith(\"$\")) {\n throw new Error(`Unknown extra output '${outputName}'.`)\n }\n\n const outputModel = unit.model.outputs[outputName]\n if (!outputModel) {\n throw new Error(`Output '${outputName}' not found in the unit '${unit.model.type}'.`)\n }\n\n const entity = unit.entities.get(outputModel.type)\n if (!entity) {\n throw new Error(\n `Entity '${outputModel.type}' not found in the unit '${unit.model.type}'.`,\n )\n }\n\n return output(outputValue).apply(value => {\n if (value === undefined) {\n if (outputModel.required) {\n throw new Error(`Output '${outputName}' is required.`)\n }\n\n return undefined\n }\n\n const schema = outputModel.multiple ? Type.Array(entity.schema) : entity.schema\n\n if (!ajv.validate(schema, value)) {\n throw new Error(`Invalid output for '${outputName}': ${ajv.errorsText()}`)\n }\n\n return value\n })\n }) as Record<string, Output<unknown>> & ExtraOutputs\n\n await Promise.all(Object.values(result).map(o => outputToPromise(o)))\n\n if (Object.keys(createdSecrets).length > 0) {\n result.$secrets = createdSecrets\n }\n\n return result\n },\n }\n}\n\nexport type EntityValue<T extends Entity> = Static<T[\"schema\"]>\nexport type EntityInput<T extends Entity> = Output<EntityValue<T>>\n\nfunction outputToPromise(o: unknown): Promise<unknown> {\n return new Promise(resolve => (output(o) as Output<unknown>).apply(resolve))\n}\n\nfunction mapStatus(status: Unwrap<ExtraOutputs[\"$status\"]>): StatusField[] {\n if (!status) {\n return []\n }\n\n if (Array.isArray(status)) {\n return status.filter(field => !!field?.value) as StatusField[]\n }\n\n return Object.entries(status)\n .map(([name, field]) => {\n if (!field) {\n return undefined\n }\n\n if (\n typeof field === \"string\" ||\n typeof field === \"number\" ||\n typeof field === \"boolean\" ||\n Array.isArray(field)\n ) {\n return { name, value: field }\n }\n\n return { ...(field as StatusField), name }\n })\n .filter(field => !!field?.value) as StatusField[]\n}\n\nfunction mapPages(pages: Unwrap<ExtraOutputs[\"$pages\"]>): InstancePage[] {\n if (!pages) {\n return []\n }\n\n if (Array.isArray(pages)) {\n return pages.filter(page => !!page)\n }\n\n return Object.entries(pages)\n .filter(([, page]) => !!page)\n .map(([name, page]) => ({ ...page!, name }))\n}\n\nexport function fileFromString(\n name: string,\n content: string,\n contentType = \"text/plain\",\n isSecret = false,\n): InstanceFile {\n return {\n meta: {\n name,\n contentType,\n size: Buffer.byteLength(content, \"utf8\"),\n },\n content: isSecret ? secret(content) : content,\n }\n}\n\nexport function fileFromBuffer(\n name: string,\n content: Buffer,\n contentType = \"application/octet-stream\",\n isSecret = false,\n): InstanceFile {\n return {\n meta: {\n name,\n contentType,\n size: content.byteLength,\n isBinary: true,\n },\n content: isSecret ? secret(content.toString(\"base64\")) : content.toString(\"base64\"),\n }\n}\n\nfunction mapFiles(files: Unwrap<ExtraOutputs[\"$files\"]>): InstanceFile[] {\n return files?.filter(file => !!file) ?? []\n}\n\nfunction mapTerminals(terminals: Unwrap<ExtraOutputs[\"$terminals\"]>): InstanceTerminal[] {\n if (!terminals) {\n return []\n }\n\n if (!Array.isArray(terminals)) {\n terminals = Object.entries(terminals).map(([name, terminal]) => {\n if (!terminal) {\n return undefined\n }\n\n return { ...terminal, name }\n })\n }\n\n return terminals\n .filter(terminal => !!terminal)\n .map(terminal => {\n if (!terminal.files) {\n return terminal\n }\n\n return {\n ...terminal,\n\n files: pipe(\n terminal.files,\n mapValues(file => {\n if (typeof file === \"string\") {\n return { content: file }\n }\n\n return file\n }),\n pickBy(value => !!value?.content),\n ),\n }\n })\n}\n\nfunction mapTriggers(triggers: Unwrap<ExtraOutputs[\"$triggers\"]>): InstanceTrigger[] {\n if (!triggers) {\n return []\n }\n\n if (Array.isArray(triggers)) {\n return triggers.filter(trigger => !!trigger)\n }\n\n return Object.entries(triggers)\n .filter(([, trigger]) => !!trigger)\n .map(([name, trigger]) => ({ ...(trigger as InstanceTrigger), name }))\n}\n","import { secret, type Input, type Output } from \"@pulumi/pulumi\"\n\nexport const createdSecrets: Record<string, Output<unknown>> = {}\n\nexport function getOrCreateSecret<\n TSecrets extends Record<string, unknown>,\n TResult extends TSecrets[keyof TSecrets],\n>(secrets: Output<TSecrets>, key: keyof TSecrets, create: () => Input<TResult>): Output<TResult> {\n // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access, @typescript-eslint/no-explicit-any\n return secrets[key as any].apply(value => {\n if (value !== undefined) {\n // if the secret is accessed via \"getOrCreateSecret\" with assume it automatically created (even if it was not)\n // in order to provide stable stack outputs\n createdSecrets[key as string] = value as Output<unknown>\n return value as TResult\n }\n\n const secretValue = createdSecrets[key as string] ?? secret(create())\n createdSecrets[key as string] = secretValue\n\n return secretValue\n }) as Output<TResult>\n}\n\nexport function storeSecret<\n TSecrets extends Record<string, unknown>,\n TResult extends TSecrets[keyof TSecrets],\n>(_secrets: Output<TSecrets>, key: keyof TSecrets, value: Input<TResult>): void {\n createdSecrets[key as string] = value as Output<unknown>\n}\n","import { type Input, type Unwrap, type Output, output, all } from \"@pulumi/pulumi\"\n\n/**\n * The input type for an array of inputs.\n * The same as `Input<Input<T>[]>`, but more readable.\n */\nexport type InputArray<T> = Input<Input<T>[]>\n\n/**\n * The input type for a map of inputs.\n * The same as `Input<Record<string, Input<T>>>`, but more readable.\n */\nexport type InputMap<T> = Input<Readonly<Record<string, Input<T>>>>\n\n/**\n * The input or input array type for a value.\n */\nexport type InputOrArray<T> = Input<T> | InputArray<T>\n\n/**\n * The input of inputs of inputs of inputs, so you got the idea.\n */\nexport type DeepInput<T> = [T] extends [Record<string, unknown> | undefined]\n ? [T] extends [infer U | undefined]\n ? Input<{ [K in keyof U]: DeepInput<U[K]> } | undefined>\n : Input<{ [K in keyof T]: DeepInput<T[K]> }>\n : [T] extends [Array<unknown> | undefined]\n ? [T] extends [(infer U)[] | undefined]\n ? Input<DeepInput<U>[] | undefined>\n : Input<DeepInput<T>[]>\n : Input<T>\n\n/**\n * Merges the given array of `InputOrArray` values into a single flat output array.\n *\n * @param values The values to merge.\n * @returns The merged output array.\n */\nexport function flattenInputs<T>(...values: (InputOrArray<T> | undefined)[]): Output<T[]> {\n return all(values).apply(allValues => {\n const result: T[] = []\n for (const value of allValues) {\n if (Array.isArray(value)) {\n result.push(...(value as T[]))\n } else if (value) {\n result.push(value as T)\n }\n }\n return result\n })\n}\n\n/**\n * Maps each element of an input array to a new value.\n * Produces an output array with the same length.\n *\n * @param array The input array.\n * @param fn The mapping function.\n * @returns The output array.\n */\nexport function mapInputs<T, U>(\n array: InputArray<T>,\n fn: (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U,\n): Output<U[]> {\n return output(array).apply(array => {\n return array?.map((v, index) => fn(v as Unwrap<T>, index, array as Unwrap<T>[])) ?? []\n })\n}\n\nexport function flatMapInput<T, U>(\n v1: InputOrArray<T>,\n v2: InputOrArray<T>,\n fn: (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U,\n): Output<U[]>\n\nexport function flatMapInput<T, U>(\n v1: InputOrArray<T>,\n v2: InputOrArray<T>,\n v3: InputOrArray<T>,\n fn: (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U,\n): Output<U[]>\n\n/**\n * Merges the given array of `InputOrArray` values into a single flat output array and maps each element to a new value.\n *\n * @param values The values to merge.\n * @param fn The mapping function.\n */\nexport function flatMapInput<T, U>(\n ...args: (InputOrArray<T> | ((v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U))[]\n): Output<U[]> {\n const fn = args.pop() as (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U\n const values = args as InputOrArray<T>[]\n\n return mapInputs(flattenInputs(...values), fn)\n}\n\n/**\n * Map an optional value to another optional value.\n *\n * @param input The input value.\n * @param func The function to apply to the input value.\n * @returns The output value, or `undefined` if the input value is `undefined`.\n */\nexport function mapOptional<T, U>(input: T | undefined, func: (value: T) => U): U | undefined {\n if (input === undefined) {\n return undefined\n }\n\n return func(input)\n}\n\nexport function toPromise<T>(input: Input<T>): Promise<Unwrap<T>> {\n return new Promise(resolve => output(input).apply(resolve))\n}\n\nexport function singleton<T>(factory: () => T): () => T {\n let instance: T | undefined\n return () => {\n if (instance === undefined) {\n instance = factory()\n }\n\n return instance\n }\n}\n\nexport function providerFactory<TInput>(\n factory: (name: string) => TInput,\n): (name: string) => TInput {\n const instances = new Map<string, TInput>()\n return name => {\n if (!instances.has(name)) {\n instances.set(name, factory(name))\n }\n\n return instances.get(name)!\n }\n}\n\nexport function mergeInputObjects<\n T1 extends Record<string, unknown>,\n T2 extends Record<string, unknown>,\n>(obj1: Input<T1 | undefined> | undefined, obj2: Input<T2 | undefined> | undefined): Output<T1 & T2>\n\nexport function mergeInputObjects<\n T1 extends Record<string, unknown>,\n T2 extends Record<string, unknown>,\n T3 extends Record<string, unknown>,\n>(\n obj1: Input<T1 | undefined> | undefined,\n obj2: Input<T2 | undefined> | undefined,\n obj3: Input<T3 | undefined> | undefined,\n): Output<T1 & T2 & T3>\n\n/**\n * Merges the given input objects into a single output object.\n *\n * @param objects The input objects.\n * @returns The output object.\n */\nexport function mergeInputObjects(\n ...objects: Input<Record<string, unknown>>[]\n): Output<Record<string, unknown>> {\n return output(objects).apply(array => {\n return Object.assign({}, ...array) as Record<string, unknown>\n })\n}\n\nexport function normalize<T>(item: T | undefined, collection: T[] | undefined): T[] {\n if (item && collection) {\n return [item, ...collection]\n }\n\n if (item) {\n return [item]\n }\n\n return collection ?? []\n}\n\nexport function apply<T, U>(fn: (value: Unwrap<T>) => U): (input: Input<T>) => Output<U> {\n return input => output(input).apply(fn)\n}\n\nexport function applyMap<T, U>(fn: (value: Unwrap<T>) => U): (input: Input<T[]>) => Output<U[]> {\n return input => output(input).apply(array => array.map(fn))\n}\n"],"mappings":"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","names":["secret","instanceName","value","values","schema","secret","output","array"]}
1
+ {"version":3,"sources":["../src/secret.ts","../src/unit.ts","../src/utils.ts"],"names":["instanceName","value","values","schema","secret","output","array"],"mappings":"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","file":"index.js","sourcesContent":["import { secret, type Input, type Output } from \"@pulumi/pulumi\"\n\nexport const createdSecrets: Record<string, Output<unknown>> = {}\n\nexport function getOrCreateSecret<\n TSecrets extends Record<string, unknown>,\n TResult extends TSecrets[keyof TSecrets],\n>(secrets: Output<TSecrets>, key: keyof TSecrets, create: () => Input<TResult>): Output<TResult> {\n // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access, @typescript-eslint/no-explicit-any\n return secrets[key as any].apply(value => {\n if (value !== undefined) {\n // if the secret is accessed via \"getOrCreateSecret\" with assume it automatically created (even if it was not)\n // in order to provide stable stack outputs\n createdSecrets[key as string] = value as Output<unknown>\n return value as TResult\n }\n\n const secretValue = createdSecrets[key as string] ?? secret(create())\n createdSecrets[key as string] = secretValue\n\n return secretValue\n }) as Output<TResult>\n}\n\nexport function storeSecret<\n TSecrets extends Record<string, unknown>,\n TResult extends TSecrets[keyof TSecrets],\n>(_secrets: Output<TSecrets>, key: keyof TSecrets, value: Input<TResult>): void {\n createdSecrets[key as string] = value as Output<unknown>\n}\n","/* eslint-disable @typescript-eslint/no-unsafe-assignment */\n/* eslint-disable @typescript-eslint/no-unsafe-member-access */\n/* eslint-disable @typescript-eslint/no-unsafe-argument */\n/* eslint-disable @typescript-eslint/no-unsafe-return */\n/* eslint-disable @typescript-eslint/no-explicit-any */\n\nimport type { DeepInput, InputArray, InputMap } from \"./utils\"\nimport {\n type ArgumentValue,\n type ComponentInputSpec,\n type Entity,\n type Unit,\n type ComponentInput,\n type InstanceInput,\n parseInstanceId,\n type ArgumentValueSchema,\n getInstanceId,\n type ComponentArgumentSpec,\n type ComponentArgumentSpecToStatic,\n HighstateSignature,\n camelCaseToHumanReadable,\n} from \"@highstate/contract\"\nimport { Type, type Static } from \"@sinclair/typebox\"\nimport { mapValues, pickBy, pipe } from \"remeda\"\nimport {\n Config,\n getStack,\n Output,\n output,\n secret,\n StackReference,\n type Input,\n type Unwrap,\n} from \"@pulumi/pulumi\"\nimport { Ajv } from \"ajv\"\nimport { createdSecrets } from \"./secret\"\n\nconst ajv = new Ajv({ strict: false })\n\nexport type ObjectMeta = {\n title?: Input<string | undefined>\n description?: Input<string | undefined>\n icon?: Input<string | undefined>\n iconColor?: Input<string | undefined>\n}\n\nexport type InstanceFileMeta = {\n name: Input<string>\n contentType?: Input<string>\n size?: Input<number>\n isBinary?: Input<boolean>\n mode?: Input<number>\n}\n\nexport type UnitArtifact = {\n hash: Input<string>\n meta?: Input<ObjectMeta>\n}\n\nexport type InstanceFile = {\n meta: Input<InstanceFileMeta>\n content:\n | { type: \"embedded\"; value: Input<string> }\n | {\n type: \"artifact\"\n [HighstateSignature.Artifact]: UnitArtifact\n }\n}\n\nexport type InstanceTerminalSpec = {\n image: Input<string>\n command: InputArray<string>\n cwd?: Input<string | undefined>\n env?: InputMap<string | undefined>\n files?: InputMap<InstanceFile | string | undefined>\n}\n\nexport type InstanceTerminal = {\n name: Input<string>\n meta: Input<ObjectMeta>\n spec: Input<InstanceTerminalSpec>\n}\n\nexport type StatusFieldValue = string | number | boolean | string[]\n\nexport type StatusField<TArgName extends string = string> = {\n name: Input<string>\n meta?: Input<ObjectMeta>\n complementaryTo?: Input<TArgName | undefined>\n value?: Input<StatusFieldValue | undefined>\n}\n\nexport type InstancePageBlock =\n | { type: \"markdown\"; content: Input<string> }\n | { type: \"qr\"; content: Input<string>; showContent?: boolean; language?: string }\n | ({ type: \"file\" } & InstanceFile)\n\nexport type InstancePage = {\n name: Input<string>\n meta: Input<ObjectMeta>\n content: InputArray<InstancePageBlock>\n}\n\nexport type InstanceTriggerSpec =\n | {\n type: \"before-destroy\"\n }\n | {\n type: \"schedule\"\n schedule: string\n }\n\nexport type InstanceTrigger = {\n name: Input<string>\n title: Input<string>\n description?: Input<string>\n spec: Input<InstanceTriggerSpec>\n}\n\nexport type ExtraOutputs<TArgName extends string = string> = {\n $statusFields?:\n | InputMap<Omit<StatusField<TArgName>, \"name\"> | StatusFieldValue | undefined>\n | InputArray<StatusField<TArgName> | undefined>\n\n $terminals?:\n | InputMap<Omit<InstanceTerminal, \"name\"> | undefined>\n | InputArray<InstanceTerminal | undefined>\n\n $pages?: InputMap<Omit<InstancePage, \"name\"> | undefined> | InputArray<InstancePage | undefined>\n\n $triggers?:\n | InputMap<Omit<InstanceTrigger, \"name\"> | undefined>\n | InputArray<InstanceTrigger | undefined>\n}\n\nexport type InstanceTriggerInvocation = {\n name: string\n}\n\ntype OutputMapToDeepInputMap<T extends Record<string, unknown>, TArgName extends string> =\n T extends Record<string, never>\n ? ExtraOutputs\n : { [K in keyof T]: DeepInput<T[K]> } & ExtraOutputs<TArgName>\n\nexport interface UnitContext<\n TArgs extends Record<string, ArgumentValue>,\n TInputs extends Record<string, unknown>,\n TOutputs extends Record<string, unknown>,\n TSecrets extends Record<string, ArgumentValue>,\n> {\n args: TArgs\n instanceId: string\n type: string\n name: string\n secrets: Output<TSecrets>\n\n inputs: TInputs extends Record<string, never>\n ? never\n : {\n [K in keyof TInputs]: undefined extends TInputs[K]\n ? Output<NonNullable<TInputs[K]>> | undefined\n : Output<TInputs[K]>\n }\n\n invokedTriggers: InstanceTriggerInvocation[]\n\n outputs(\n this: void,\n outputs?: OutputMapToDeepInputMap<TOutputs, keyof TArgs & string>,\n ): Promise<unknown>\n}\n\ntype InputSpecToValue<T extends ComponentInputSpec> = T[2] extends true\n ? Static<T[0][\"schema\"]>[]\n : T[1] extends true\n ? Static<T[0][\"schema\"]>\n : Static<T[0][\"schema\"]> | undefined\n\ntype InputSpecMapToValueMap<T extends Record<string, ComponentInputSpec>> =\n T extends Record<string, never>\n ? Record<string, never>\n : { [K in keyof T]: InputSpecToValue<T[K]> }\n\nconst stackRefMap = new Map<string, StackReference>()\nconst [projectId, instanceName] = getStack().split(\"_\")\n\nlet instanceId: string | undefined\n\nexport function getUnitInstanceId(): string {\n if (!instanceId) {\n throw new Error(\"Instance id is not set. Did you call 'forUnit' function?\")\n }\n\n return instanceId\n}\n\nexport function getResourceComment(): string {\n return `Managed by Highstate Unit (${getUnitInstanceId()})`\n}\n\nexport function getUnitInstanceName(): string {\n return instanceName\n}\n\nfunction getStackRef(input: InstanceInput) {\n const [instanceType, instanceName] = parseInstanceId(input.instanceId)\n const key = `organization/${instanceType}/${projectId}_${instanceName}`\n\n if (!stackRefMap.has(key)) {\n stackRefMap.set(key, new StackReference(key))\n }\n\n return stackRefMap.get(key)!\n}\n\nfunction getOutput(unit: Unit, input: ComponentInput, refs: InstanceInput[]) {\n const entity = unit.entities.get(input.type)\n if (!entity) {\n throw new Error(`Entity '${input.type}' not found in the unit '${unit.model.type}'.`)\n }\n\n const _getOutput = (ref: InstanceInput) => {\n const value = getStackRef(ref).requireOutput(ref.output)\n\n return value.apply(value => {\n if (Array.isArray(value)) {\n for (const [index, item] of value.entries()) {\n if (!ajv.validate(entity.schema, item)) {\n throw new Error(`Invalid output for '${input.type}[${index}]': ${ajv.errorsText()}`)\n }\n }\n } else {\n if (!ajv.validate(entity.schema, value)) {\n throw new Error(`Invalid output for '${input.type}': ${ajv.errorsText()}`)\n }\n }\n\n if (Array.isArray(value)) {\n return value\n }\n\n return input.multiple ? [value] : value\n })\n }\n\n const values = output(refs.map(ref => _getOutput(ref))).apply(values => values.flat())\n\n if (!input.multiple) {\n return values.apply(values => values[0])\n }\n\n return values\n}\n\nfunction isAnyOfSchema(schema: ArgumentValueSchema, itemType: string): boolean {\n if (schema.anyOf) {\n return Object.values(schema.anyOf).every(schema =>\n isAnyOfSchema(schema as ArgumentValueSchema, itemType),\n )\n }\n\n return schema.type === itemType\n}\n\nfunction isStringSchema(schema: ArgumentValueSchema): boolean {\n if (schema.type === \"string\") {\n return true\n }\n\n if (isAnyOfSchema(schema, \"string\")) {\n return true\n }\n\n return false\n}\n\nfunction isNumberSchema(schema: ArgumentValueSchema): boolean {\n if (schema.type === \"number\") {\n return true\n }\n\n if (isAnyOfSchema(schema, \"number\")) {\n return true\n }\n\n return false\n}\n\nfunction isBooleanSchema(schema: ArgumentValueSchema): boolean {\n if (schema.type === \"boolean\") {\n return true\n }\n\n if (isAnyOfSchema(schema, \"boolean\")) {\n return true\n }\n\n return false\n}\n\nexport function forUnit<\n TArgs extends Record<string, ComponentArgumentSpec>,\n TInputs extends Record<string, ComponentInputSpec>,\n TOutputs extends Record<string, ComponentInputSpec>,\n TSecrets extends Record<string, ComponentArgumentSpec>,\n>(\n unit: Unit<TArgs, TInputs, TOutputs, TSecrets>,\n): UnitContext<\n //\n ComponentArgumentSpecToStatic<TArgs>,\n InputSpecMapToValueMap<TInputs>,\n InputSpecMapToValueMap<TOutputs>,\n ComponentArgumentSpecToStatic<TSecrets>\n> {\n const config = new Config()\n\n const args = mapValues(unit.model.args, (arg, argName) => {\n switch (true) {\n case isStringSchema(arg.schema): {\n if (arg.required) {\n return config.require(argName)\n }\n\n // handle empty strings as undefined\n return config.get(argName) || arg.schema.default\n }\n case isNumberSchema(arg.schema): {\n if (arg.required) {\n return config.requireNumber(argName)\n }\n\n // handle empty strings as undefined\n const value = config.get(argName)\n if (!value) {\n return arg.schema.default\n }\n\n return config.getNumber(argName) ?? arg.schema.default\n }\n case isBooleanSchema(arg.schema): {\n if (arg.required) {\n return config.requireBoolean(argName)\n }\n\n // handle empty strings as undefined\n const value = config.get(argName)\n if (!value) {\n return arg.schema.default\n }\n\n return config.getBoolean(argName) ?? arg.schema.default\n }\n default: {\n if (!arg.required) {\n const value = config.get(argName)\n // handle empty strings as undefined\n if (!value) {\n return arg.schema.default\n }\n }\n\n const value = arg.required ? config.requireObject(argName) : config.getObject(argName)\n if (value === undefined) return arg.schema.default\n\n if (!ajv.validate(arg.schema, value)) {\n throw new Error(`Invalid config for '${argName}': ${ajv.errorsText()}`)\n }\n\n return value\n }\n }\n }) as ComponentArgumentSpecToStatic<TArgs>\n\n const secrets = output(\n mapValues(unit.model.secrets, (secret, secretName) => {\n switch (true) {\n case isStringSchema(secret.schema): {\n return secret.required ? config.requireSecret(secretName) : config.getSecret(secretName)\n }\n case isNumberSchema(secret.schema): {\n return secret.required\n ? config.requireSecretNumber(secretName)\n : config.getSecretNumber(secretName)\n }\n case isBooleanSchema(secret.schema): {\n return secret.required\n ? config.requireSecretBoolean(secretName)\n : config.getSecretBoolean(secretName)\n }\n default: {\n const value = secret.required\n ? config.requireSecretObject(secretName)\n : config.getSecretObject(secretName)\n\n if (!ajv.validate(secret.schema, value)) {\n throw new Error(`Invalid secret for '${secretName}': ${ajv.errorsText()}`)\n }\n\n return value\n }\n }\n }),\n ) as unknown as Output<ComponentArgumentSpecToStatic<TSecrets>>\n\n const inputs = mapValues(unit.model.inputs, (input, inputName) => {\n const value = input.required\n ? config.requireObject<InstanceInput[]>(`input.${inputName}`)\n : config.getObject<InstanceInput[]>(`input.${inputName}`)\n\n if (!value) {\n if (input.multiple) {\n return output([])\n }\n\n return undefined\n }\n\n return getOutput(unit as unknown as Unit, input, value)\n })\n\n const type = unit.model.type\n instanceId = getInstanceId(type, instanceName)\n\n return {\n args,\n instanceId,\n type,\n name: instanceName,\n secrets,\n inputs: inputs as any,\n invokedTriggers: config.getObject<InstanceTriggerInvocation[]>(\"$invokedTriggers\") ?? [],\n\n outputs: async (outputs: any = {}) => {\n const result: any = mapValues(outputs, (outputValue, outputName) => {\n if (outputName === \"$statusFields\") {\n return output(outputValue).apply(mapStatusFields)\n }\n\n if (outputName === \"$pages\") {\n return output(outputValue).apply(mapPages)\n }\n\n if (outputName === \"$terminals\") {\n return output(outputValue).apply(mapTerminals)\n }\n\n if (outputName === \"$triggers\") {\n return output(outputValue).apply(mapTriggers)\n }\n\n if (outputName.startsWith(\"$\")) {\n throw new Error(`Unknown extra output '${outputName}'.`)\n }\n\n const outputModel = unit.model.outputs[outputName]\n if (!outputModel) {\n throw new Error(`Output '${outputName}' not found in the unit '${unit.model.type}'.`)\n }\n\n const entity = unit.entities.get(outputModel.type)\n if (!entity) {\n throw new Error(\n `Entity '${outputModel.type}' not found in the unit '${unit.model.type}'.`,\n )\n }\n\n return output(outputValue).apply(value => {\n if (value === undefined) {\n if (outputModel.required) {\n throw new Error(`Output '${outputName}' is required.`)\n }\n\n return undefined\n }\n\n const schema = outputModel.multiple ? Type.Array(entity.schema) : entity.schema\n\n if (!ajv.validate(schema, value)) {\n throw new Error(`Invalid output for '${outputName}': ${ajv.errorsText()}`)\n }\n\n return value\n })\n }) as Record<string, Output<unknown>> & ExtraOutputs\n\n await Promise.all(Object.values(result).map(o => outputToPromise(o)))\n\n if (Object.keys(createdSecrets).length > 0) {\n result.$secrets = createdSecrets\n }\n\n // collect artifacts from all outputs\n const artifactsMap: Record<string, UnitArtifact[]> = {}\n for (const [outputName, outputValue] of Object.entries(outputs)) {\n if (!outputName.startsWith(\"$\")) {\n const resolvedValue = await outputToPromise(outputValue)\n const artifacts = extractArtifactsFromValue(resolvedValue)\n if (artifacts.length > 0) {\n artifactsMap[outputName] = artifacts\n }\n }\n }\n\n if (Object.keys(artifactsMap).length > 0) {\n result.$artifacts = artifactsMap\n }\n\n return result\n },\n }\n}\n\nexport type EntityValue<T extends Entity> = Static<T[\"schema\"]>\nexport type EntityInput<T extends Entity> = Output<EntityValue<T>>\n\nfunction outputToPromise(o: unknown): Promise<unknown> {\n return new Promise(resolve => (output(o) as Output<unknown>).apply(resolve))\n}\n\nfunction mapStatusFields(status: Unwrap<ExtraOutputs[\"$statusFields\"]>): StatusField[] {\n if (!status) {\n return []\n }\n\n if (Array.isArray(status)) {\n return status\n .filter(field => !!field?.value)\n .map(field => {\n return {\n name: field!.name,\n meta: {\n title: field!.meta?.title ?? camelCaseToHumanReadable(field!.name),\n },\n value: field!.value,\n } as StatusField\n })\n }\n\n return Object.entries(status)\n .map(([name, field]) => {\n if (!field) {\n return undefined\n }\n\n if (\n typeof field === \"string\" ||\n typeof field === \"number\" ||\n typeof field === \"boolean\" ||\n Array.isArray(field)\n ) {\n return {\n name,\n meta: {\n title: camelCaseToHumanReadable(name),\n },\n value: field,\n }\n }\n\n return {\n ...(field as StatusField),\n meta: {\n ...field.meta,\n title: field.meta?.title ?? camelCaseToHumanReadable(name),\n },\n name,\n }\n })\n .filter(field => !!field?.value) as StatusField[]\n}\n\nfunction mapPages(pages: Unwrap<ExtraOutputs[\"$pages\"]>): InstancePage[] {\n if (!pages) {\n return []\n }\n\n if (Array.isArray(pages)) {\n return pages.filter(page => !!page)\n }\n\n return Object.entries(pages)\n .filter(([, page]) => !!page)\n .map(([name, page]) => ({ ...page!, name }))\n}\n\nexport function fileFromString(\n name: string,\n content: string,\n contentType = \"text/plain\",\n isSecret = false,\n): InstanceFile {\n return {\n meta: {\n name,\n contentType,\n size: Buffer.byteLength(content, \"utf8\"),\n },\n content: {\n type: \"embedded\",\n value: isSecret ? secret(content) : content,\n },\n }\n}\n\nexport function fileFromBuffer(\n name: string,\n content: Buffer,\n contentType = \"application/octet-stream\",\n isSecret = false,\n): InstanceFile {\n return {\n meta: {\n name,\n contentType,\n size: content.byteLength,\n isBinary: true,\n },\n content: {\n type: \"embedded\",\n value: isSecret ? secret(content.toString(\"base64\")) : content.toString(\"base64\"),\n },\n }\n}\n\nfunction mapTerminals(terminals: Unwrap<ExtraOutputs[\"$terminals\"]>): InstanceTerminal[] {\n if (!terminals) {\n return []\n }\n\n if (!Array.isArray(terminals)) {\n terminals = Object.entries(terminals).map(([name, terminal]) => {\n if (!terminal) {\n return undefined\n }\n\n return { ...terminal, name }\n })\n }\n\n return terminals\n .filter(terminal => !!terminal)\n .map(terminal => {\n if (!terminal.spec.files) {\n return terminal\n }\n\n return {\n ...terminal,\n\n spec: {\n ...terminal.spec,\n\n files: pipe(\n terminal.spec.files,\n mapValues(file => {\n if (typeof file === \"string\") {\n return {\n meta: {\n name: \"content\",\n contentType: \"text/plain\",\n size: Buffer.byteLength(file, \"utf8\"),\n },\n content: {\n type: \"embedded\" as const,\n value: file,\n },\n }\n }\n\n return file\n }),\n pickBy(value => !!value),\n ),\n },\n }\n })\n}\n\nfunction mapTriggers(triggers: Unwrap<ExtraOutputs[\"$triggers\"]>): InstanceTrigger[] {\n if (!triggers) {\n return []\n }\n\n if (Array.isArray(triggers)) {\n return triggers.filter(trigger => !!trigger)\n }\n\n return Object.entries(triggers)\n .filter(([, trigger]) => !!trigger)\n .map(([name, trigger]) => ({ ...(trigger as InstanceTrigger), name }))\n}\n\n/**\n * Extracts artifact objects from a value by traversing the object tree\n * looking for properties with HighstateSignature.Artifact.\n */\nfunction extractArtifactsFromValue(data: unknown): UnitArtifact[] {\n const artifacts: UnitArtifact[] = []\n\n function traverse(obj: unknown): void {\n if (obj === null || obj === undefined || typeof obj !== \"object\") {\n return\n }\n\n if (Array.isArray(obj)) {\n for (const item of obj) {\n traverse(item)\n }\n return\n }\n\n const record = obj as Record<string, unknown>\n\n // check if this object has an artifact signature\n if (HighstateSignature.Artifact in record) {\n const artifactData = record[HighstateSignature.Artifact] as UnitArtifact\n artifacts.push(artifactData)\n\n // strip all other properties except the artifact hash\n record[HighstateSignature.Artifact] = { hash: artifactData.hash }\n return\n }\n\n // recursively traverse all properties\n for (const value of Object.values(record)) {\n traverse(value)\n }\n }\n\n traverse(data)\n return artifacts\n}\n","import { type Input, type Unwrap, type Output, output, all } from \"@pulumi/pulumi\"\n\n/**\n * The input type for an array of inputs.\n * The same as `Input<Input<T>[]>`, but more readable.\n */\nexport type InputArray<T> = Input<Input<T>[]>\n\n/**\n * The input type for a map of inputs.\n * The same as `Input<Record<string, Input<T>>>`, but more readable.\n */\nexport type InputMap<T> = Input<Readonly<Record<string, Input<T>>>>\n\n/**\n * The input or input array type for a value.\n */\nexport type InputOrArray<T> = Input<T> | InputArray<T>\n\n/**\n * The input of inputs of inputs of inputs, so you got the idea.\n */\nexport type DeepInput<T> = [T] extends [Record<string, unknown> | undefined]\n ? [T] extends [infer U | undefined]\n ? Input<{ [K in keyof U]: DeepInput<U[K]> } | undefined>\n : Input<{ [K in keyof T]: DeepInput<T[K]> }>\n : [T] extends [Array<unknown> | undefined]\n ? [T] extends [(infer U)[] | undefined]\n ? Input<DeepInput<U>[] | undefined>\n : Input<DeepInput<T>[]>\n : Input<T>\n\n/**\n * Merges the given array of `InputOrArray` values into a single flat output array.\n *\n * @param values The values to merge.\n * @returns The merged output array.\n */\nexport function flattenInputs<T>(...values: (InputOrArray<T> | undefined)[]): Output<T[]> {\n return all(values).apply(allValues => {\n const result: T[] = []\n for (const value of allValues) {\n if (Array.isArray(value)) {\n result.push(...(value as T[]))\n } else if (value) {\n result.push(value as T)\n }\n }\n return result\n })\n}\n\n/**\n * Maps each element of an input array to a new value.\n * Produces an output array with the same length.\n *\n * @param array The input array.\n * @param fn The mapping function.\n * @returns The output array.\n */\nexport function mapInputs<T, U>(\n array: InputArray<T>,\n fn: (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U,\n): Output<U[]> {\n return output(array).apply(array => {\n return array?.map((v, index) => fn(v as Unwrap<T>, index, array as Unwrap<T>[])) ?? []\n })\n}\n\nexport function flatMapInput<T, U>(\n v1: InputOrArray<T>,\n v2: InputOrArray<T>,\n fn: (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U,\n): Output<U[]>\n\nexport function flatMapInput<T, U>(\n v1: InputOrArray<T>,\n v2: InputOrArray<T>,\n v3: InputOrArray<T>,\n fn: (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U,\n): Output<U[]>\n\n/**\n * Merges the given array of `InputOrArray` values into a single flat output array and maps each element to a new value.\n *\n * @param values The values to merge.\n * @param fn The mapping function.\n */\nexport function flatMapInput<T, U>(\n ...args: (InputOrArray<T> | ((v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U))[]\n): Output<U[]> {\n const fn = args.pop() as (v: Unwrap<T>, index: number, all: Unwrap<T>[]) => U\n const values = args as InputOrArray<T>[]\n\n return mapInputs(flattenInputs(...values), fn)\n}\n\n/**\n * Map an optional value to another optional value.\n *\n * @param input The input value.\n * @param func The function to apply to the input value.\n * @returns The output value, or `undefined` if the input value is `undefined`.\n */\nexport function mapOptional<T, U>(input: T | undefined, func: (value: T) => U): U | undefined {\n if (input === undefined) {\n return undefined\n }\n\n return func(input)\n}\n\nexport function toPromise<T>(input: Input<T>): Promise<Unwrap<T>> {\n return new Promise(resolve => output(input).apply(resolve))\n}\n\nexport function singleton<T>(factory: () => T): () => T {\n let instance: T | undefined\n return () => {\n if (instance === undefined) {\n instance = factory()\n }\n\n return instance\n }\n}\n\nexport function providerFactory<TInput>(\n factory: (name: string) => TInput,\n): (name: string) => TInput {\n const instances = new Map<string, TInput>()\n return name => {\n if (!instances.has(name)) {\n instances.set(name, factory(name))\n }\n\n return instances.get(name)!\n }\n}\n\nexport function mergeInputObjects<\n T1 extends Record<string, unknown>,\n T2 extends Record<string, unknown>,\n>(obj1: Input<T1 | undefined> | undefined, obj2: Input<T2 | undefined> | undefined): Output<T1 & T2>\n\nexport function mergeInputObjects<\n T1 extends Record<string, unknown>,\n T2 extends Record<string, unknown>,\n T3 extends Record<string, unknown>,\n>(\n obj1: Input<T1 | undefined> | undefined,\n obj2: Input<T2 | undefined> | undefined,\n obj3: Input<T3 | undefined> | undefined,\n): Output<T1 & T2 & T3>\n\n/**\n * Merges the given input objects into a single output object.\n *\n * @param objects The input objects.\n * @returns The output object.\n */\nexport function mergeInputObjects(\n ...objects: Input<Record<string, unknown>>[]\n): Output<Record<string, unknown>> {\n return output(objects).apply(array => {\n return Object.assign({}, ...array) as Record<string, unknown>\n })\n}\n\nexport function normalize<T>(item: T | undefined, collection: T[] | undefined): T[] {\n if (item && collection) {\n return [item, ...collection]\n }\n\n if (item) {\n return [item]\n }\n\n return collection ?? []\n}\n\nexport function apply<T, U>(fn: (value: Unwrap<T>) => U): (input: Input<T>) => Output<U> {\n return input => output(input).apply(fn)\n}\n\nexport function applyMap<T, U>(fn: (value: Unwrap<T>) => U): (input: Input<T[]>) => Output<U[]> {\n return input => output(input).apply(array => array.map(fn))\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@highstate/pulumi",
3
- "version": "0.9.14",
3
+ "version": "0.9.16",
4
4
  "type": "module",
5
5
  "files": [
6
6
  "dist",
@@ -19,15 +19,15 @@
19
19
  "build": "highstate build"
20
20
  },
21
21
  "dependencies": {
22
- "@highstate/contract": "^0.9.14",
23
- "@pulumi/pulumi": "^3.165.0",
22
+ "@highstate/contract": "^0.9.16",
23
+ "@pulumi/pulumi": "^3.181.0",
24
24
  "@sinclair/typebox": "^0.34.11",
25
25
  "ajv": "^8.17.1",
26
26
  "import-meta-resolve": "^4.1.0",
27
27
  "remeda": "^2.21.0"
28
28
  },
29
29
  "devDependencies": {
30
- "@highstate/cli": "^0.9.14"
30
+ "@highstate/cli": "^0.9.16"
31
31
  },
32
- "gitHead": "8b5d1079961cc5bf9cf8ea3c10f7313384e3a2ff"
32
+ "gitHead": "458d6f1f9f6d4aec0ba75a2b2c4c01408cb9c8df"
33
33
  }
package/src/unit.ts CHANGED
@@ -17,6 +17,8 @@ import {
17
17
  getInstanceId,
18
18
  type ComponentArgumentSpec,
19
19
  type ComponentArgumentSpecToStatic,
20
+ HighstateSignature,
21
+ camelCaseToHumanReadable,
20
22
  } from "@highstate/contract"
21
23
  import { Type, type Static } from "@sinclair/typebox"
22
24
  import { mapValues, pickBy, pipe } from "remeda"
@@ -35,54 +37,67 @@ import { createdSecrets } from "./secret"
35
37
 
36
38
  const ajv = new Ajv({ strict: false })
37
39
 
38
- export type InstanceTerminalFile = {
39
- content: Input<string | undefined>
40
- mode?: Input<number | undefined>
41
- isBinary?: Input<boolean>
40
+ export type ObjectMeta = {
41
+ title?: Input<string | undefined>
42
+ description?: Input<string | undefined>
43
+ icon?: Input<string | undefined>
44
+ iconColor?: Input<string | undefined>
42
45
  }
43
46
 
44
- export type InstanceTerminal = {
47
+ export type InstanceFileMeta = {
45
48
  name: Input<string>
46
- title: Input<string>
47
- description?: Input<string>
49
+ contentType?: Input<string>
50
+ size?: Input<number>
51
+ isBinary?: Input<boolean>
52
+ mode?: Input<number>
53
+ }
54
+
55
+ export type UnitArtifact = {
56
+ hash: Input<string>
57
+ meta?: Input<ObjectMeta>
58
+ }
59
+
60
+ export type InstanceFile = {
61
+ meta: Input<InstanceFileMeta>
62
+ content:
63
+ | { type: "embedded"; value: Input<string> }
64
+ | {
65
+ type: "artifact"
66
+ [HighstateSignature.Artifact]: UnitArtifact
67
+ }
68
+ }
69
+
70
+ export type InstanceTerminalSpec = {
48
71
  image: Input<string>
49
72
  command: InputArray<string>
50
73
  cwd?: Input<string | undefined>
51
74
  env?: InputMap<string | undefined>
52
- files?: InputMap<InstanceTerminalFile | string | undefined>
75
+ files?: InputMap<InstanceFile | string | undefined>
76
+ }
77
+
78
+ export type InstanceTerminal = {
79
+ name: Input<string>
80
+ meta: Input<ObjectMeta>
81
+ spec: Input<InstanceTerminalSpec>
53
82
  }
54
83
 
55
84
  export type StatusFieldValue = string | number | boolean | string[]
56
85
 
57
86
  export type StatusField<TArgName extends string = string> = {
58
87
  name: Input<string>
59
- value?: Input<StatusFieldValue | undefined>
60
- displayName?: Input<string | undefined>
61
- sensitive?: Input<boolean | undefined>
62
- url?: Input<string | undefined>
88
+ meta?: Input<ObjectMeta>
63
89
  complementaryTo?: Input<TArgName | undefined>
64
- }
65
-
66
- export type InstanceFileMeta = {
67
- name: Input<string>
68
- contentType: Input<string>
69
- isBinary?: Input<boolean>
70
- size: Input<number>
71
- }
72
-
73
- export type InstanceFile = {
74
- meta: Input<InstanceFileMeta>
75
- content: Input<string>
90
+ value?: Input<StatusFieldValue | undefined>
76
91
  }
77
92
 
78
93
  export type InstancePageBlock =
79
94
  | { type: "markdown"; content: Input<string> }
80
95
  | { type: "qr"; content: Input<string>; showContent?: boolean; language?: string }
81
- | { type: "file"; fileMeta: Input<InstanceFileMeta> }
96
+ | ({ type: "file" } & InstanceFile)
82
97
 
83
98
  export type InstancePage = {
84
99
  name: Input<string>
85
- title: Input<string>
100
+ meta: Input<ObjectMeta>
86
101
  content: InputArray<InstancePageBlock>
87
102
  }
88
103
 
@@ -103,7 +118,7 @@ export type InstanceTrigger = {
103
118
  }
104
119
 
105
120
  export type ExtraOutputs<TArgName extends string = string> = {
106
- $status?:
121
+ $statusFields?:
107
122
  | InputMap<Omit<StatusField<TArgName>, "name"> | StatusFieldValue | undefined>
108
123
  | InputArray<StatusField<TArgName> | undefined>
109
124
 
@@ -112,7 +127,6 @@ export type ExtraOutputs<TArgName extends string = string> = {
112
127
  | InputArray<InstanceTerminal | undefined>
113
128
 
114
129
  $pages?: InputMap<Omit<InstancePage, "name"> | undefined> | InputArray<InstancePage | undefined>
115
- $files?: InputArray<InstanceFile | undefined>
116
130
 
117
131
  $triggers?:
118
132
  | InputMap<Omit<InstanceTrigger, "name"> | undefined>
@@ -209,18 +223,20 @@ function getOutput(unit: Unit, input: ComponentInput, refs: InstanceInput[]) {
209
223
  const value = getStackRef(ref).requireOutput(ref.output)
210
224
 
211
225
  return value.apply(value => {
212
- let schema = entity.schema
213
-
214
- if (input.multiple) {
215
- schema = Type.Union([schema, Type.Array(schema)])
216
- }
217
-
218
- if (!ajv.validate(schema, value)) {
219
- throw new Error(`Invalid output for '${input.type}': ${ajv.errorsText()}`)
226
+ if (Array.isArray(value)) {
227
+ for (const [index, item] of value.entries()) {
228
+ if (!ajv.validate(entity.schema, item)) {
229
+ throw new Error(`Invalid output for '${input.type}[${index}]': ${ajv.errorsText()}`)
230
+ }
231
+ }
232
+ } else {
233
+ if (!ajv.validate(entity.schema, value)) {
234
+ throw new Error(`Invalid output for '${input.type}': ${ajv.errorsText()}`)
235
+ }
220
236
  }
221
237
 
222
238
  if (Array.isArray(value)) {
223
- return value as unknown
239
+ return value
224
240
  }
225
241
 
226
242
  return input.multiple ? [value] : value
@@ -301,19 +317,48 @@ export function forUnit<
301
317
  const args = mapValues(unit.model.args, (arg, argName) => {
302
318
  switch (true) {
303
319
  case isStringSchema(arg.schema): {
304
- return arg.required ? config.require(argName) : (config.get(argName) ?? arg.schema.default)
320
+ if (arg.required) {
321
+ return config.require(argName)
322
+ }
323
+
324
+ // handle empty strings as undefined
325
+ return config.get(argName) || arg.schema.default
305
326
  }
306
327
  case isNumberSchema(arg.schema): {
307
- return arg.required
308
- ? config.requireNumber(argName)
309
- : (config.getNumber(argName) ?? arg.schema.default)
328
+ if (arg.required) {
329
+ return config.requireNumber(argName)
330
+ }
331
+
332
+ // handle empty strings as undefined
333
+ const value = config.get(argName)
334
+ if (!value) {
335
+ return arg.schema.default
336
+ }
337
+
338
+ return config.getNumber(argName) ?? arg.schema.default
310
339
  }
311
340
  case isBooleanSchema(arg.schema): {
312
- return arg.required
313
- ? config.requireBoolean(argName)
314
- : (config.getBoolean(argName) ?? arg.schema.default)
341
+ if (arg.required) {
342
+ return config.requireBoolean(argName)
343
+ }
344
+
345
+ // handle empty strings as undefined
346
+ const value = config.get(argName)
347
+ if (!value) {
348
+ return arg.schema.default
349
+ }
350
+
351
+ return config.getBoolean(argName) ?? arg.schema.default
315
352
  }
316
353
  default: {
354
+ if (!arg.required) {
355
+ const value = config.get(argName)
356
+ // handle empty strings as undefined
357
+ if (!value) {
358
+ return arg.schema.default
359
+ }
360
+ }
361
+
317
362
  const value = arg.required ? config.requireObject(argName) : config.getObject(argName)
318
363
  if (value === undefined) return arg.schema.default
319
364
 
@@ -387,18 +432,14 @@ export function forUnit<
387
432
 
388
433
  outputs: async (outputs: any = {}) => {
389
434
  const result: any = mapValues(outputs, (outputValue, outputName) => {
390
- if (outputName === "$status") {
391
- return output(outputValue).apply(mapStatus)
435
+ if (outputName === "$statusFields") {
436
+ return output(outputValue).apply(mapStatusFields)
392
437
  }
393
438
 
394
439
  if (outputName === "$pages") {
395
440
  return output(outputValue).apply(mapPages)
396
441
  }
397
442
 
398
- if (outputName === "$files") {
399
- return output(outputValue).apply(mapFiles)
400
- }
401
-
402
443
  if (outputName === "$terminals") {
403
444
  return output(outputValue).apply(mapTerminals)
404
445
  }
@@ -448,6 +489,22 @@ export function forUnit<
448
489
  result.$secrets = createdSecrets
449
490
  }
450
491
 
492
+ // collect artifacts from all outputs
493
+ const artifactsMap: Record<string, UnitArtifact[]> = {}
494
+ for (const [outputName, outputValue] of Object.entries(outputs)) {
495
+ if (!outputName.startsWith("$")) {
496
+ const resolvedValue = await outputToPromise(outputValue)
497
+ const artifacts = extractArtifactsFromValue(resolvedValue)
498
+ if (artifacts.length > 0) {
499
+ artifactsMap[outputName] = artifacts
500
+ }
501
+ }
502
+ }
503
+
504
+ if (Object.keys(artifactsMap).length > 0) {
505
+ result.$artifacts = artifactsMap
506
+ }
507
+
451
508
  return result
452
509
  },
453
510
  }
@@ -460,13 +517,23 @@ function outputToPromise(o: unknown): Promise<unknown> {
460
517
  return new Promise(resolve => (output(o) as Output<unknown>).apply(resolve))
461
518
  }
462
519
 
463
- function mapStatus(status: Unwrap<ExtraOutputs["$status"]>): StatusField[] {
520
+ function mapStatusFields(status: Unwrap<ExtraOutputs["$statusFields"]>): StatusField[] {
464
521
  if (!status) {
465
522
  return []
466
523
  }
467
524
 
468
525
  if (Array.isArray(status)) {
469
- return status.filter(field => !!field?.value) as StatusField[]
526
+ return status
527
+ .filter(field => !!field?.value)
528
+ .map(field => {
529
+ return {
530
+ name: field!.name,
531
+ meta: {
532
+ title: field!.meta?.title ?? camelCaseToHumanReadable(field!.name),
533
+ },
534
+ value: field!.value,
535
+ } as StatusField
536
+ })
470
537
  }
471
538
 
472
539
  return Object.entries(status)
@@ -481,10 +548,23 @@ function mapStatus(status: Unwrap<ExtraOutputs["$status"]>): StatusField[] {
481
548
  typeof field === "boolean" ||
482
549
  Array.isArray(field)
483
550
  ) {
484
- return { name, value: field }
551
+ return {
552
+ name,
553
+ meta: {
554
+ title: camelCaseToHumanReadable(name),
555
+ },
556
+ value: field,
557
+ }
485
558
  }
486
559
 
487
- return { ...(field as StatusField), name }
560
+ return {
561
+ ...(field as StatusField),
562
+ meta: {
563
+ ...field.meta,
564
+ title: field.meta?.title ?? camelCaseToHumanReadable(name),
565
+ },
566
+ name,
567
+ }
488
568
  })
489
569
  .filter(field => !!field?.value) as StatusField[]
490
570
  }
@@ -515,7 +595,10 @@ export function fileFromString(
515
595
  contentType,
516
596
  size: Buffer.byteLength(content, "utf8"),
517
597
  },
518
- content: isSecret ? secret(content) : content,
598
+ content: {
599
+ type: "embedded",
600
+ value: isSecret ? secret(content) : content,
601
+ },
519
602
  }
520
603
  }
521
604
 
@@ -532,14 +615,13 @@ export function fileFromBuffer(
532
615
  size: content.byteLength,
533
616
  isBinary: true,
534
617
  },
535
- content: isSecret ? secret(content.toString("base64")) : content.toString("base64"),
618
+ content: {
619
+ type: "embedded",
620
+ value: isSecret ? secret(content.toString("base64")) : content.toString("base64"),
621
+ },
536
622
  }
537
623
  }
538
624
 
539
- function mapFiles(files: Unwrap<ExtraOutputs["$files"]>): InstanceFile[] {
540
- return files?.filter(file => !!file) ?? []
541
- }
542
-
543
625
  function mapTerminals(terminals: Unwrap<ExtraOutputs["$terminals"]>): InstanceTerminal[] {
544
626
  if (!terminals) {
545
627
  return []
@@ -558,24 +640,38 @@ function mapTerminals(terminals: Unwrap<ExtraOutputs["$terminals"]>): InstanceTe
558
640
  return terminals
559
641
  .filter(terminal => !!terminal)
560
642
  .map(terminal => {
561
- if (!terminal.files) {
643
+ if (!terminal.spec.files) {
562
644
  return terminal
563
645
  }
564
646
 
565
647
  return {
566
648
  ...terminal,
567
649
 
568
- files: pipe(
569
- terminal.files,
570
- mapValues(file => {
571
- if (typeof file === "string") {
572
- return { content: file }
573
- }
574
-
575
- return file
576
- }),
577
- pickBy(value => !!value?.content),
578
- ),
650
+ spec: {
651
+ ...terminal.spec,
652
+
653
+ files: pipe(
654
+ terminal.spec.files,
655
+ mapValues(file => {
656
+ if (typeof file === "string") {
657
+ return {
658
+ meta: {
659
+ name: "content",
660
+ contentType: "text/plain",
661
+ size: Buffer.byteLength(file, "utf8"),
662
+ },
663
+ content: {
664
+ type: "embedded" as const,
665
+ value: file,
666
+ },
667
+ }
668
+ }
669
+
670
+ return file
671
+ }),
672
+ pickBy(value => !!value),
673
+ ),
674
+ },
579
675
  }
580
676
  })
581
677
  }
@@ -593,3 +689,44 @@ function mapTriggers(triggers: Unwrap<ExtraOutputs["$triggers"]>): InstanceTrigg
593
689
  .filter(([, trigger]) => !!trigger)
594
690
  .map(([name, trigger]) => ({ ...(trigger as InstanceTrigger), name }))
595
691
  }
692
+
693
+ /**
694
+ * Extracts artifact objects from a value by traversing the object tree
695
+ * looking for properties with HighstateSignature.Artifact.
696
+ */
697
+ function extractArtifactsFromValue(data: unknown): UnitArtifact[] {
698
+ const artifacts: UnitArtifact[] = []
699
+
700
+ function traverse(obj: unknown): void {
701
+ if (obj === null || obj === undefined || typeof obj !== "object") {
702
+ return
703
+ }
704
+
705
+ if (Array.isArray(obj)) {
706
+ for (const item of obj) {
707
+ traverse(item)
708
+ }
709
+ return
710
+ }
711
+
712
+ const record = obj as Record<string, unknown>
713
+
714
+ // check if this object has an artifact signature
715
+ if (HighstateSignature.Artifact in record) {
716
+ const artifactData = record[HighstateSignature.Artifact] as UnitArtifact
717
+ artifacts.push(artifactData)
718
+
719
+ // strip all other properties except the artifact hash
720
+ record[HighstateSignature.Artifact] = { hash: artifactData.hash }
721
+ return
722
+ }
723
+
724
+ // recursively traverse all properties
725
+ for (const value of Object.values(record)) {
726
+ traverse(value)
727
+ }
728
+ }
729
+
730
+ traverse(data)
731
+ return artifacts
732
+ }