@homeflare/alchemy 0.34.0 → 0.36.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (65) hide show
  1. package/dist/grafana/alert-rule-group-drop-warning.d.ts +25 -0
  2. package/dist/grafana/alert-rule-group-drop-warning.d.ts.map +1 -0
  3. package/dist/grafana/alert-rule-group-fixtures.d.ts +73 -0
  4. package/dist/grafana/alert-rule-group-fixtures.d.ts.map +1 -0
  5. package/dist/grafana/alert-rule-group-model.d.ts +28 -0
  6. package/dist/grafana/alert-rule-group-model.d.ts.map +1 -0
  7. package/dist/grafana/alert-rule-group.d.ts +60 -0
  8. package/dist/grafana/alert-rule-group.d.ts.map +1 -0
  9. package/dist/grafana/index.d.ts +6 -4
  10. package/dist/grafana/index.d.ts.map +1 -1
  11. package/dist/grafana/index.js +355 -139
  12. package/dist/grafana/index.js.map +14 -8
  13. package/dist/grafana/notification-policy-drop-warning.d.ts +27 -0
  14. package/dist/grafana/notification-policy-drop-warning.d.ts.map +1 -0
  15. package/dist/grafana/notification-policy-fixtures.d.ts +34 -0
  16. package/dist/grafana/notification-policy-fixtures.d.ts.map +1 -0
  17. package/dist/grafana/notification-policy-model.d.ts +53 -0
  18. package/dist/grafana/notification-policy-model.d.ts.map +1 -0
  19. package/dist/grafana/notification-policy.d.ts +57 -0
  20. package/dist/grafana/notification-policy.d.ts.map +1 -0
  21. package/dist/grafana/providers.d.ts +1 -1
  22. package/dist/grafana/providers.d.ts.map +1 -1
  23. package/dist/proxmox/index.js +349 -287
  24. package/dist/proxmox/index.js.map +8 -7
  25. package/dist/proxmox/network-apply-read.d.ts +12 -0
  26. package/dist/proxmox/network-apply-read.d.ts.map +1 -1
  27. package/dist/proxmox/network-apply.d.ts +2 -0
  28. package/dist/proxmox/network-apply.d.ts.map +1 -1
  29. package/dist/proxmox/node-network-form.d.ts +86 -54
  30. package/dist/proxmox/node-network-form.d.ts.map +1 -1
  31. package/dist/proxmox/node-network-wire.d.ts +100 -0
  32. package/dist/proxmox/node-network-wire.d.ts.map +1 -0
  33. package/dist/proxmox/node-network.d.ts +21 -106
  34. package/dist/proxmox/node-network.d.ts.map +1 -1
  35. package/docs/grafana-alerting-rules.md +143 -0
  36. package/docs/grafana-alerting.md +7 -4
  37. package/docs/grafana-notification-policy.md +127 -0
  38. package/docs/grafana.md +12 -6
  39. package/docs/upstream-conformance.md +30 -4
  40. package/package.json +1 -1
  41. package/src/grafana/alert-rule-group-drop-warning.test.ts +107 -0
  42. package/src/grafana/alert-rule-group-drop-warning.ts +41 -0
  43. package/src/grafana/alert-rule-group-fixtures.ts +46 -0
  44. package/src/grafana/alert-rule-group-model.test.ts +75 -0
  45. package/src/grafana/alert-rule-group-model.ts +66 -0
  46. package/src/grafana/alert-rule-group-provenance.test.ts +116 -0
  47. package/src/grafana/alert-rule-group.test.ts +164 -0
  48. package/src/grafana/alert-rule-group.ts +231 -0
  49. package/src/grafana/index.ts +18 -4
  50. package/src/grafana/notification-policy-drop-warning.test.ts +163 -0
  51. package/src/grafana/notification-policy-drop-warning.ts +60 -0
  52. package/src/grafana/notification-policy-fixtures.ts +27 -0
  53. package/src/grafana/notification-policy-model.test.ts +104 -0
  54. package/src/grafana/notification-policy-model.ts +100 -0
  55. package/src/grafana/notification-policy-refusals.test.ts +119 -0
  56. package/src/grafana/notification-policy.test.ts +86 -0
  57. package/src/grafana/notification-policy.ts +191 -0
  58. package/src/grafana/providers.ts +4 -0
  59. package/src/proxmox/constraints-host-forms.test.ts +2 -2
  60. package/src/proxmox/network-apply-read.ts +12 -0
  61. package/src/proxmox/network-apply.ts +2 -0
  62. package/src/proxmox/node-network-form.ts +93 -99
  63. package/src/proxmox/node-network-read-failure.test.ts +206 -0
  64. package/src/proxmox/node-network-wire.ts +239 -0
  65. package/src/proxmox/node-network.ts +155 -167
@@ -3372,10 +3372,14 @@ var handlers10 = {
3372
3372
  var ProxmoxNetworkApplyProvider = () => Provider15.effect(ProxmoxNetworkApply, Effect38.succeed(ProxmoxNetworkApply.Provider.of(handlers10)));
3373
3373
  // src/proxmox/node-network.ts
3374
3374
  import { Resource as Resource16 } from "alchemy";
3375
+ import { isResolved as isResolved10 } from "alchemy/Diff";
3375
3376
  import * as Provider16 from "alchemy/Provider";
3376
- import * as Effect39 from "effect/Effect";
3377
+ import * as nodes2 from "@distilled.cloud/proxmox/nodes";
3378
+ import * as Effect40 from "effect/Effect";
3377
3379
 
3378
3380
  // src/proxmox/node-network-form.ts
3381
+ var NODE_NETWORK_CREATE = "pve:POST /nodes/{node}/network";
3382
+ var NODE_NETWORK_UPDATE = "pve:PUT /nodes/{node}/network/{iface}";
3379
3383
  var UNSET3 = -1;
3380
3384
  var ifaceList = (value) => text(value).split(/[\s,;]+/).filter((part) => part !== "").sort().join(" ");
3381
3385
  var comment2 = (value) => text(value).replace(/\s+$/, "");
@@ -3400,72 +3404,130 @@ var body4 = (props) => ({
3400
3404
  ...field3("vlan-raw-device", props["vlan-raw-device"]),
3401
3405
  type: props.type
3402
3406
  });
3403
- var createBody3 = (props) => ({
3407
+ var createForm5 = (props) => ({
3404
3408
  ...body4(props),
3405
3409
  iface: props.iface
3406
3410
  });
3407
- var updateBody2 = (props) => {
3411
+ var updateForm2 = (props) => {
3408
3412
  const clear = [
3409
3413
  ...props.cidr === undefined ? ["cidr"] : [],
3410
3414
  ...props.bridge_vlan_aware === false ? ["bridge_vlan_aware"] : []
3411
3415
  ];
3412
- const fields = body4(props);
3413
- return withClears(fields, clear);
3416
+ return withClears(body4(props), clear);
3414
3417
  };
3415
- var readAttributes2 = (live, props) => {
3416
- const liveType = text(live["type"]);
3418
+
3419
+ // src/proxmox/node-network-wire.ts
3420
+ import * as nodes from "@distilled.cloud/proxmox/nodes";
3421
+ import * as Effect39 from "effect/Effect";
3422
+ var attributesOf5 = (live, props) => {
3423
+ const data = live;
3424
+ const liveType = text(data["type"]);
3417
3425
  if (liveType !== "" && liveType !== props.type)
3418
3426
  return;
3419
3427
  return {
3420
- active: bool(live["active"]),
3421
- autostart: bool(live["autostart"]),
3422
- "bond-primary": text(live["bond-primary"]),
3423
- bond_miimon: text(live["bond_miimon"]),
3424
- bond_mode: text(live["bond_mode"]),
3425
- bond_xmit_hash_policy: text(live["bond_xmit_hash_policy"]),
3426
- bridge_fd: text(live["bridge_fd"]),
3427
- bridge_ports: ifaceList(live["bridge_ports"]),
3428
- bridge_stp: text(live["bridge_stp"]),
3429
- bridge_vids: ifaceList(live["bridge_vids"]),
3430
- bridge_vlan_aware: bool(live["bridge_vlan_aware"]),
3431
- cidr: text(live["cidr"]),
3432
- comments: comment2(live["comments"]),
3433
- exists: bool(live["exists"]),
3434
- families: Array.isArray(live["families"]) ? live["families"].join(",") : "",
3435
- gateway: text(live["gateway"]),
3428
+ active: bool(data["active"]),
3429
+ autostart: bool(data["autostart"]),
3430
+ "bond-primary": text(data["bond-primary"]),
3431
+ bond_miimon: text(data["bond_miimon"]),
3432
+ bond_mode: text(data["bond_mode"]),
3433
+ bond_xmit_hash_policy: text(data["bond_xmit_hash_policy"]),
3434
+ bridge_fd: text(data["bridge_fd"]),
3435
+ bridge_ports: ifaceList(data["bridge_ports"]),
3436
+ bridge_stp: text(data["bridge_stp"]),
3437
+ bridge_vids: ifaceList(data["bridge_vids"]),
3438
+ bridge_vlan_aware: bool(data["bridge_vlan_aware"]),
3439
+ cidr: text(data["cidr"]),
3440
+ comments: comment2(data["comments"]),
3441
+ exists: bool(data["exists"]),
3442
+ families: Array.isArray(data["families"]) ? data["families"].join(",") : "",
3443
+ gateway: text(data["gateway"]),
3436
3444
  iface: props.iface,
3437
- method: text(live["method"]),
3438
- mtu: int(live["mtu"], UNSET3),
3445
+ method: text(data["method"]),
3446
+ mtu: int(data["mtu"], UNSET3),
3439
3447
  node: props.node,
3440
- priority: int(live["priority"], UNSET3),
3441
- slaves: ifaceList(live["slaves"]),
3448
+ priority: int(data["priority"], UNSET3),
3449
+ slaves: ifaceList(data["slaves"]),
3442
3450
  type: liveType === "" ? props.type : liveType,
3443
- "vlan-id": int(live["vlan-id"], UNSET3),
3444
- "vlan-raw-device": text(live["vlan-raw-device"])
3451
+ "vlan-id": int(data["vlan-id"], UNSET3),
3452
+ "vlan-raw-device": text(data["vlan-raw-device"])
3445
3453
  };
3446
3454
  };
3455
+ var readInterfaceOrFail = (props) => readOrUnreadable(runPve(props.target, "read", false, nodes.getNodeNetwork({ iface: props.iface, node: props.node })).pipe(Effect39.catchTag("ParameterVerificationFailed", (error) => error.errors["iface"] === "interface does not exist" ? Effect39.succeed(undefined) : Effect39.fail(error)))).pipe(Effect39.map((live) => {
3456
+ if (live === UNREADABLE)
3457
+ return UNREADABLE;
3458
+ return live === undefined ? undefined : attributesOf5(live, props);
3459
+ }));
3460
+ var readInterface = (props) => readInterfaceOrFail(props).pipe(Effect39.orElseSucceed(() => {
3461
+ return;
3462
+ }));
3463
+ var dropUnreadable4 = (live) => live === UNREADABLE ? undefined : live;
3464
+ var matches4 = (attributes, props) => attributes.cidr === (props.cidr ?? "") && same2(props.gateway, attributes.gateway) && same2(props.autostart, attributes.autostart) && same2(props.mtu, attributes.mtu) && sameComment(props.comments, attributes.comments) && sameList(props.bridge_ports, attributes.bridge_ports) && sameList(props.bridge_vids, attributes.bridge_vids) && same2(props.bridge_vlan_aware, attributes.bridge_vlan_aware) && sameList(props.slaves, attributes.slaves) && same2(props.bond_mode, attributes.bond_mode) && same2(props.bond_xmit_hash_policy, attributes.bond_xmit_hash_policy) && same2(props["bond-primary"], attributes["bond-primary"]) && same2(props["vlan-id"], attributes["vlan-id"]) && same2(props["vlan-raw-device"], attributes["vlan-raw-device"]);
3447
3465
 
3448
3466
  // src/proxmox/node-network.ts
3449
3467
  var ProxmoxNodeNetwork = Resource16("Proxmox.NodeNetwork", {
3450
3468
  defaultRemovalPolicy: "retain"
3451
3469
  });
3452
- var handlers11 = pveHandlers({
3453
- attributes: readAttributes2,
3454
- collection: (props) => `nodes/${props.node}/network`,
3455
- createForm: createBody3,
3456
- endpoint: {
3457
- create: "pve:POST /nodes/{node}/network",
3458
- update: "pve:PUT /nodes/{node}/network/{iface}"
3459
- },
3460
- matches: (attributes, props) => attributes.cidr === (props.cidr ?? "") && same2(props.gateway, attributes.gateway) && same2(props.autostart, attributes.autostart) && same2(props.mtu, attributes.mtu) && sameComment(props.comments, attributes.comments) && sameList(props.bridge_ports, attributes.bridge_ports) && sameList(props.bridge_vids, attributes.bridge_vids) && same2(props.bridge_vlan_aware, attributes.bridge_vlan_aware) && sameList(props.slaves, attributes.slaves) && same2(props.bond_mode, attributes.bond_mode) && same2(props.bond_xmit_hash_policy, attributes.bond_xmit_hash_policy) && same2(props["bond-primary"], attributes["bond-primary"]) && same2(props["vlan-id"], attributes["vlan-id"]) && same2(props["vlan-raw-device"], attributes["vlan-raw-device"]),
3461
- path: (props) => `nodes/${props.node}/network/${props.iface}`,
3462
- updateForm: updateBody2
3463
- });
3464
- var ProxmoxNodeNetworkProvider = () => Provider16.effect(ProxmoxNodeNetwork, Effect39.succeed(ProxmoxNodeNetwork.Provider.of(handlers11)));
3470
+ var RENAMED = {
3471
+ "bond-primary": "bond_primary",
3472
+ "vlan-id": "vlan_id",
3473
+ "vlan-raw-device": "vlan_raw_device"
3474
+ };
3475
+ var toDistilled = (form) => Object.fromEntries(Object.entries(form).map(([key, value]) => [RENAMED[key] ?? key, value]));
3476
+ var toDistilledCreate = (props) => ({
3477
+ ...toDistilled(createForm5(props)),
3478
+ node: props.node
3479
+ });
3480
+ var toDistilledUpdate = (props) => ({
3481
+ ...toDistilled(updateForm2(props)),
3482
+ iface: props.iface,
3483
+ node: props.node
3484
+ });
3485
+ var ProxmoxNodeNetworkProvider = () => Provider16.effect(ProxmoxNodeNetwork, Effect40.succeed(ProxmoxNodeNetwork.Provider.of({
3486
+ list: () => Effect40.succeed([]),
3487
+ read: Effect40.fn(function* ({ olds, output }) {
3488
+ return dropUnreadable4(yield* output === undefined ? readInterface(olds) : readInterfaceOrFail(olds));
3489
+ }),
3490
+ diff: Effect40.fn(function* ({ news, output }) {
3491
+ if (!isResolved10(news))
3492
+ return;
3493
+ yield* guardWrite2(NODE_NETWORK_CREATE, createForm5(news), output === undefined);
3494
+ yield* guardWrite2(NODE_NETWORK_UPDATE, updateForm2(news), false);
3495
+ if (output === undefined)
3496
+ return;
3497
+ const live = yield* readInterfaceOrFail(news);
3498
+ if (live === UNREADABLE) {
3499
+ yield* unreadableWarning("Proxmox.NodeNetwork", `${news.node}/${news.iface}`);
3500
+ return { action: "noop" };
3501
+ }
3502
+ if (live === undefined) {
3503
+ yield* guardWrite2(NODE_NETWORK_CREATE, createForm5(news), true);
3504
+ return { action: "update" };
3505
+ }
3506
+ return matches4(live, news) ? { action: "noop" } : { action: "update" };
3507
+ }),
3508
+ reconcile: Effect40.fn(function* ({ news }) {
3509
+ const before = dropUnreadable4(yield* readInterface(news));
3510
+ yield* guardWrite2(NODE_NETWORK_CREATE, createForm5(news), before === undefined);
3511
+ yield* guardWrite2(NODE_NETWORK_UPDATE, updateForm2(news), false);
3512
+ if (before === undefined) {
3513
+ yield* runPve(news.target, "provision", true, nodes2.createNodeNetwork(toDistilledCreate(news)));
3514
+ } else if (!matches4(before, news)) {
3515
+ yield* runPve(news.target, "provision", true, nodes2.putNodeNetwork2(toDistilledUpdate(news)));
3516
+ }
3517
+ const after = dropUnreadable4(yield* readInterface(news));
3518
+ if (after === undefined) {
3519
+ return yield* Effect40.die(new Error(`nodes/${news.node}/network/${news.iface}: wrote with no error, but the ` + 'interface is still absent -- PVE wraps every answer in {"data":...} and can ' + "report success on a call that did nothing, so read back rather than trust it."));
3520
+ }
3521
+ return after;
3522
+ }),
3523
+ delete: Effect40.fn(function* ({ olds }) {
3524
+ yield* runPve(olds.target, "provision", true, nodes2.deleteNodeNetwork2({ iface: olds.iface, node: olds.node }));
3525
+ })
3526
+ })));
3465
3527
  // src/proxmox/notification-matcher.ts
3466
3528
  import { Resource as Resource17 } from "alchemy";
3467
3529
  import * as Provider17 from "alchemy/Provider";
3468
- import * as Effect40 from "effect/Effect";
3530
+ import * as Effect41 from "effect/Effect";
3469
3531
 
3470
3532
  // src/proxmox/notification-matcher-form.ts
3471
3533
  var list = (value) => Array.isArray(value) ? value.map((item) => String(item)) : [];
@@ -3543,7 +3605,7 @@ var matcherUpdateForm = (fields) => {
3543
3605
 
3544
3606
  // src/proxmox/notification-matcher.ts
3545
3607
  var ProxmoxNotificationMatcher = Resource17("Proxmox.NotificationMatcher");
3546
- var handlers12 = pveHandlers({
3608
+ var handlers11 = pveHandlers({
3547
3609
  attributes: (live, props) => matcherAttributes(live, props.name),
3548
3610
  collection: () => "cluster/notifications/matchers",
3549
3611
  createForm: matcherCreateForm,
@@ -3555,11 +3617,11 @@ var handlers12 = pveHandlers({
3555
3617
  path: (props) => `cluster/notifications/matchers/${props.name}`,
3556
3618
  updateForm: matcherUpdateForm
3557
3619
  });
3558
- var ProxmoxNotificationMatcherProvider = () => Provider17.effect(ProxmoxNotificationMatcher, Effect40.succeed(ProxmoxNotificationMatcher.Provider.of(handlers12)));
3620
+ var ProxmoxNotificationMatcherProvider = () => Provider17.effect(ProxmoxNotificationMatcher, Effect41.succeed(ProxmoxNotificationMatcher.Provider.of(handlers11)));
3559
3621
  // src/proxmox/notification-target.ts
3560
3622
  import { Resource as Resource18 } from "alchemy";
3561
3623
  import * as Provider18 from "alchemy/Provider";
3562
- import * as Effect41 from "effect/Effect";
3624
+ import * as Effect42 from "effect/Effect";
3563
3625
 
3564
3626
  // src/proxmox/notification-target-endpoint.ts
3565
3627
  var ENDPOINTS = {
@@ -3615,7 +3677,7 @@ var createShape = (props) => ({
3615
3677
 
3616
3678
  // src/proxmox/notification-target.ts
3617
3679
  var ProxmoxNotificationTarget = Resource18("Proxmox.NotificationTarget");
3618
- var handlers13 = pveHandlers({
3680
+ var handlers12 = pveHandlers({
3619
3681
  attributes: (live, props) => ({
3620
3682
  author: text(live["author"]),
3621
3683
  body: text(live["body"]),
@@ -3641,15 +3703,15 @@ var handlers13 = pveHandlers({
3641
3703
  path: (props) => `cluster/notifications/endpoints/${props.type}/${props.name}`,
3642
3704
  updateForm: shape4
3643
3705
  });
3644
- var ProxmoxNotificationTargetProvider = () => Provider18.effect(ProxmoxNotificationTarget, Effect41.succeed(ProxmoxNotificationTarget.Provider.of(handlers13)));
3706
+ var ProxmoxNotificationTargetProvider = () => Provider18.effect(ProxmoxNotificationTarget, Effect42.succeed(ProxmoxNotificationTarget.Provider.of(handlers12)));
3645
3707
  // src/proxmox/pbs-datastore.ts
3646
3708
  import { Resource as Resource19 } from "alchemy";
3647
- import { isResolved as isResolved10 } from "alchemy/Diff";
3709
+ import { isResolved as isResolved11 } from "alchemy/Diff";
3648
3710
  import * as Provider19 from "alchemy/Provider";
3649
- import * as Effect45 from "effect/Effect";
3711
+ import * as Effect46 from "effect/Effect";
3650
3712
 
3651
3713
  // src/proxmox/pbs-datastore-form.ts
3652
- import * as Effect42 from "effect/Effect";
3714
+ import * as Effect43 from "effect/Effect";
3653
3715
  var attributes = (live, props) => ({
3654
3716
  backend: propertyString(live["backend"]),
3655
3717
  comment: text(live["comment"]),
@@ -3672,7 +3734,7 @@ var attributes = (live, props) => ({
3672
3734
  "verify-new": bool(live["verify-new"])
3673
3735
  });
3674
3736
  var same4 = (declared, live) => declared === undefined || declared === live;
3675
- var matches4 = (live, props) => same4(props.comment, live.comment) && same4(props["gc-schedule"]?.trim(), live["gc-schedule"]) && same4(props["prune-schedule"]?.trim(), live["prune-schedule"]) && same4(props["keep-last"], live["keep-last"]) && same4(props["keep-hourly"], live["keep-hourly"]) && same4(props["keep-daily"], live["keep-daily"]) && same4(props["keep-weekly"], live["keep-weekly"]) && same4(props["keep-monthly"], live["keep-monthly"]) && same4(props["keep-yearly"], live["keep-yearly"]) && same4(props["notify-user"], live["notify-user"]) && same4(props["counter-reset-schedule"]?.trim(), live["counter-reset-schedule"]) && (props["notification-thresholds"] === undefined || propertyString(props["notification-thresholds"]) === live["notification-thresholds"]) && same4(props["verify-new"], live["verify-new"]) && (props.notify === undefined || propertyString(props.notify) === live.notify) && (props.tuning === undefined || propertyString(props.tuning) === live.tuning) && (props["maintenance-mode"] === undefined || propertyString(props["maintenance-mode"], "type") === live["maintenance-mode"]);
3737
+ var matches5 = (live, props) => same4(props.comment, live.comment) && same4(props["gc-schedule"]?.trim(), live["gc-schedule"]) && same4(props["prune-schedule"]?.trim(), live["prune-schedule"]) && same4(props["keep-last"], live["keep-last"]) && same4(props["keep-hourly"], live["keep-hourly"]) && same4(props["keep-daily"], live["keep-daily"]) && same4(props["keep-weekly"], live["keep-weekly"]) && same4(props["keep-monthly"], live["keep-monthly"]) && same4(props["keep-yearly"], live["keep-yearly"]) && same4(props["notify-user"], live["notify-user"]) && same4(props["counter-reset-schedule"]?.trim(), live["counter-reset-schedule"]) && (props["notification-thresholds"] === undefined || propertyString(props["notification-thresholds"]) === live["notification-thresholds"]) && same4(props["verify-new"], live["verify-new"]) && (props.notify === undefined || propertyString(props.notify) === live.notify) && (props.tuning === undefined || propertyString(props.tuning) === live.tuning) && (props["maintenance-mode"] === undefined || propertyString(props["maintenance-mode"], "type") === live["maintenance-mode"]);
3676
3738
  var set2 = (key, value) => value === undefined ? {} : { [key]: value };
3677
3739
  var count = (value) => value === undefined ? undefined : String(value);
3678
3740
  var mutable = (props) => ({
@@ -3693,56 +3755,56 @@ var mutable = (props) => ({
3693
3755
  ...set2("tuning", props.tuning),
3694
3756
  ...set2("verify-new", flag(props["verify-new"]))
3695
3757
  });
3696
- var createForm5 = (props) => ({
3758
+ var createForm6 = (props) => ({
3697
3759
  ...mutable(props),
3698
3760
  name: props.name,
3699
3761
  path: props.path,
3700
3762
  ...props.backend === undefined ? {} : { backend: props.backend }
3701
3763
  });
3702
- var updateForm2 = (props) => mutable(props);
3764
+ var updateForm3 = (props) => mutable(props);
3703
3765
  var object2 = (props) => `config/datastore/${props.name}`;
3704
- var readOne = (props) => pve(props.target, "read", "GET", object2(props)).pipe(Effect42.map((live) => live === undefined || typeof live["name"] !== "string" ? undefined : attributes(live, props)), Effect42.orElseSucceed(() => {
3766
+ var readOne = (props) => pve(props.target, "read", "GET", object2(props)).pipe(Effect43.map((live) => live === undefined || typeof live["name"] !== "string" ? undefined : attributes(live, props)), Effect43.orElseSucceed(() => {
3705
3767
  return;
3706
3768
  }));
3707
3769
 
3708
3770
  // src/proxmox/pbs-datastore-guard.ts
3709
- import * as Effect43 from "effect/Effect";
3771
+ import * as Effect44 from "effect/Effect";
3710
3772
  var samePath = (left, right) => {
3711
3773
  const trim = (value) => value.length > 1 ? value.replace(/\/+$/, "") : value;
3712
3774
  return trim(left) === trim(right);
3713
3775
  };
3714
- var guardPath = (live, props) => live.path === "" || samePath(live.path, props.path) ? Effect43.void : Effect43.die(new Error(`${object2(props)}: declared path ${props.path} but PBS holds ${live.path}. \`path\` ` + "is create-only, so this cannot be reconciled and will NOT be planned as a silent " + "noop: backups would keep landing in the old directory behind a green plan. Correct " + "the declaration, or remove the datastore and declare a new one -- the contents live, " + "because `destroy-data` is never sent."));
3715
- var guardBackend = (live, props) => props.backend === undefined || propertyString(props.backend) === live.backend ? Effect43.void : Effect43.die(new Error(`${object2(props)}: declared backend ${props.backend} but PBS holds ` + `${live.backend === "" ? "(none — a local datastore)" : live.backend}. \`backend\` ` + "is create-only: PBS has no update for it, so this cannot be reconciled and will NOT " + "be planned as a silent noop. Correct the declaration to match what is really there, " + "or remove the datastore and declare a new one -- the contents live, because " + "`destroy-data` is never sent."));
3716
- var settle3 = (read3, done) => Effect43.gen(function* () {
3776
+ var guardPath = (live, props) => live.path === "" || samePath(live.path, props.path) ? Effect44.void : Effect44.die(new Error(`${object2(props)}: declared path ${props.path} but PBS holds ${live.path}. \`path\` ` + "is create-only, so this cannot be reconciled and will NOT be planned as a silent " + "noop: backups would keep landing in the old directory behind a green plan. Correct " + "the declaration, or remove the datastore and declare a new one -- the contents live, " + "because `destroy-data` is never sent."));
3777
+ var guardBackend = (live, props) => props.backend === undefined || propertyString(props.backend) === live.backend ? Effect44.void : Effect44.die(new Error(`${object2(props)}: declared backend ${props.backend} but PBS holds ` + `${live.backend === "" ? "(none — a local datastore)" : live.backend}. \`backend\` ` + "is create-only: PBS has no update for it, so this cannot be reconciled and will NOT " + "be planned as a silent noop. Correct the declaration to match what is really there, " + "or remove the datastore and declare a new one -- the contents live, because " + "`destroy-data` is never sent."));
3778
+ var settle3 = (read3, done) => Effect44.gen(function* () {
3717
3779
  for (let attempt = 0;attempt < 60; attempt += 1) {
3718
3780
  const live = yield* read3;
3719
3781
  if (done(live))
3720
3782
  return live;
3721
- yield* Effect43.sleep("2 seconds");
3783
+ yield* Effect44.sleep("2 seconds");
3722
3784
  }
3723
3785
  return yield* read3;
3724
3786
  });
3725
3787
 
3726
3788
  // src/proxmox/pbs-datastore-endpoint.ts
3727
- import * as Effect44 from "effect/Effect";
3789
+ import * as Effect45 from "effect/Effect";
3728
3790
  var DATASTORE_ENDPOINT = {
3729
3791
  create: "pbs:POST /config/datastore",
3730
3792
  update: "pbs:PUT /config/datastore/{name}"
3731
3793
  };
3732
- var guardDatastoreForms = (props) => Effect44.gen(function* () {
3733
- yield* guardForm(DATASTORE_ENDPOINT.create, createForm5(props), true);
3734
- yield* guardForm(DATASTORE_ENDPOINT.update, updateForm2(props), false);
3794
+ var guardDatastoreForms = (props) => Effect45.gen(function* () {
3795
+ yield* guardForm(DATASTORE_ENDPOINT.create, createForm6(props), true);
3796
+ yield* guardForm(DATASTORE_ENDPOINT.update, updateForm3(props), false);
3735
3797
  });
3736
3798
 
3737
3799
  // src/proxmox/pbs-datastore.ts
3738
3800
  var PbsDatastore = Resource19("Pbs.Datastore", {
3739
3801
  defaultRemovalPolicy: "retain"
3740
3802
  });
3741
- var PbsDatastoreProvider = () => Provider19.effect(PbsDatastore, Effect45.succeed(PbsDatastore.Provider.of({
3742
- list: () => Effect45.succeed([]),
3803
+ var PbsDatastoreProvider = () => Provider19.effect(PbsDatastore, Effect46.succeed(PbsDatastore.Provider.of({
3804
+ list: () => Effect46.succeed([]),
3743
3805
  read: ({ olds }) => readOne(olds),
3744
- diff: ({ news, output }) => Effect45.gen(function* () {
3745
- if (!isResolved10(news))
3806
+ diff: ({ news, output }) => Effect46.gen(function* () {
3807
+ if (!isResolved11(news))
3746
3808
  return;
3747
3809
  yield* guardDatastoreForms(news);
3748
3810
  if (output === undefined)
@@ -3752,42 +3814,42 @@ var PbsDatastoreProvider = () => Provider19.effect(PbsDatastore, Effect45.succee
3752
3814
  return { action: "update" };
3753
3815
  yield* guardPath(live, news);
3754
3816
  yield* guardBackend(live, news);
3755
- return matches4(live, news) ? { action: "noop" } : { action: "update" };
3817
+ return matches5(live, news) ? { action: "noop" } : { action: "update" };
3756
3818
  }),
3757
- reconcile: Effect45.fn(function* ({ news }) {
3819
+ reconcile: Effect46.fn(function* ({ news }) {
3758
3820
  yield* guardDatastoreForms(news);
3759
3821
  const live = yield* readOne(news);
3760
3822
  let upid;
3761
3823
  if (live === undefined) {
3762
- upid = yield* pve(news.target, "provision", "POST", "config/datastore", createForm5(news));
3824
+ upid = yield* pve(news.target, "provision", "POST", "config/datastore", createForm6(news));
3763
3825
  } else {
3764
3826
  yield* guardPath(live, news);
3765
3827
  yield* guardBackend(live, news);
3766
- const form = formToSend(matches4, live, news, updateForm2(news));
3828
+ const form = formToSend(matches5, live, news, updateForm3(news));
3767
3829
  if (form !== undefined) {
3768
3830
  yield* pve(news.target, "provision", "PUT", object2(news), form);
3769
3831
  }
3770
3832
  }
3771
- const after = yield* settle3(readOne(news), (row) => row !== undefined && matches4(row, news));
3772
- if (after === undefined || !matches4(after, news)) {
3773
- return yield* Effect45.die(new Error(`${object2(news)}: the write returned no error but the datastore still does not ` + `match the declaration after 120s. PBS answered with task ${upid ?? "(none)"} ` + "-- read it with `proxmox-backup-manager task log <upid>`. A slow disk is a " + "plausible cause (see `settle`); a create over an existing chunk store is not, " + "because PBS refuses that outright rather than timing out."));
3833
+ const after = yield* settle3(readOne(news), (row) => row !== undefined && matches5(row, news));
3834
+ if (after === undefined || !matches5(after, news)) {
3835
+ return yield* Effect46.die(new Error(`${object2(news)}: the write returned no error but the datastore still does not ` + `match the declaration after 120s. PBS answered with task ${upid ?? "(none)"} ` + "-- read it with `proxmox-backup-manager task log <upid>`. A slow disk is a " + "plausible cause (see `settle`); a create over an existing chunk store is not, " + "because PBS refuses that outright rather than timing out."));
3774
3836
  }
3775
3837
  return after;
3776
3838
  }),
3777
- delete: Effect45.fn(function* ({ olds }) {
3839
+ delete: Effect46.fn(function* ({ olds }) {
3778
3840
  yield* pve(olds.target, "provision", "DELETE", object2(olds));
3779
3841
  const left = yield* settle3(readOne(olds), (row) => row === undefined);
3780
3842
  if (left !== undefined) {
3781
- return yield* Effect45.die(new Error(`${object2(olds)}: the DELETE returned no error but the datastore is still in ` + "datastore.cfg after 120s. Either a backup, verify or GC task still holds it, " + "or the provision role lacks Datastore.Allocate on /datastore/" + `${olds.name}. Read the task log with \`proxmox-backup-manager task log <upid>\`.`));
3843
+ return yield* Effect46.die(new Error(`${object2(olds)}: the DELETE returned no error but the datastore is still in ` + "datastore.cfg after 120s. Either a backup, verify or GC task still holds it, " + "or the provision role lacks Datastore.Allocate on /datastore/" + `${olds.name}. Read the task log with \`proxmox-backup-manager task log <upid>\`.`));
3782
3844
  }
3783
3845
  })
3784
3846
  })));
3785
3847
  // src/proxmox/pbs-notification-matcher.ts
3786
3848
  import { Resource as Resource20 } from "alchemy";
3787
3849
  import * as Provider20 from "alchemy/Provider";
3788
- import * as Effect46 from "effect/Effect";
3850
+ import * as Effect47 from "effect/Effect";
3789
3851
  var PbsNotificationMatcher = Resource20("Pbs.NotificationMatcher");
3790
- var handlers14 = pveHandlers({
3852
+ var handlers13 = pveHandlers({
3791
3853
  attributes: (live, props) => matcherAttributes(live, props.name),
3792
3854
  collection: () => "config/notifications/matchers",
3793
3855
  createForm: matcherCreateForm,
@@ -3799,15 +3861,15 @@ var handlers14 = pveHandlers({
3799
3861
  path: (props) => `config/notifications/matchers/${props.name}`,
3800
3862
  updateForm: matcherUpdateForm
3801
3863
  });
3802
- var PbsNotificationMatcherProvider = () => Provider20.effect(PbsNotificationMatcher, Effect46.succeed(PbsNotificationMatcher.Provider.of(handlers14)));
3864
+ var PbsNotificationMatcherProvider = () => Provider20.effect(PbsNotificationMatcher, Effect47.succeed(PbsNotificationMatcher.Provider.of(handlers13)));
3803
3865
  // src/proxmox/pbs-notification-target.ts
3804
3866
  import { Resource as Resource21 } from "alchemy";
3805
3867
  import * as Provider21 from "alchemy/Provider";
3806
- import * as Effect48 from "effect/Effect";
3868
+ import * as Effect49 from "effect/Effect";
3807
3869
 
3808
3870
  // src/proxmox/pbs-notification-target-lifecycle.ts
3809
- import { isResolved as isResolved11 } from "alchemy/Diff";
3810
- import * as Effect47 from "effect/Effect";
3871
+ import { isResolved as isResolved12 } from "alchemy/Diff";
3872
+ import * as Effect48 from "effect/Effect";
3811
3873
 
3812
3874
  // src/proxmox/pbs-notification-target-endpoint.ts
3813
3875
  var ENDPOINTS2 = {
@@ -4084,12 +4146,12 @@ var targetForm = (props, groups, carry, mode) => {
4084
4146
 
4085
4147
  // src/proxmox/pbs-notification-target-lifecycle.ts
4086
4148
  var path = (props) => `config/notifications/endpoints/${props.type}/${props.name}`;
4087
- var readLive2 = (props) => pve(props.target, "read", "GET", path(props)).pipe(Effect47.map((data) => data == null ? undefined : targetAttributes(data, props)), Effect47.orElseSucceed(() => {
4149
+ var readLive2 = (props) => pve(props.target, "read", "GET", path(props)).pipe(Effect48.map((data) => data == null ? undefined : targetAttributes(data, props)), Effect48.orElseSucceed(() => {
4088
4150
  return;
4089
4151
  }));
4090
4152
  var refuse2 = (props) => {
4091
4153
  const reasons = refusals(props);
4092
- return reasons.length === 0 ? Effect47.void : Effect47.die(new Error(`${path(props)}: ${reasons.join("; ")}.`));
4154
+ return reasons.length === 0 ? Effect48.void : Effect48.die(new Error(`${path(props)}: ${reasons.join("; ")}.`));
4093
4155
  };
4094
4156
  var toCarry = (live, props, groups, sealed) => {
4095
4157
  const header = headerState(live, props, groups) === "stale";
@@ -4101,17 +4163,17 @@ var requireValues = (props, groups, carry) => {
4101
4163
  ...carry.header ? groups.header.missing : [],
4102
4164
  ...carry.sealed ? groups.sealed.missing : []
4103
4165
  ];
4104
- return missing.length === 0 ? Effect47.void : Effect47.die(new Error(`${path(props)}: this write must send write-only values, and ${missing.join(", ")} ` + "is unset or empty in the deploying environment. Export it and deploy again."));
4166
+ return missing.length === 0 ? Effect48.void : Effect48.die(new Error(`${path(props)}: this write must send write-only values, and ${missing.join(", ")} ` + "is unset or empty in the deploying environment. Export it and deploy again."));
4105
4167
  };
4106
- var handlers15 = {
4107
- list: () => Effect47.succeed([]),
4108
- read: ({ olds, output }) => (output === undefined ? refuse2(olds) : Effect47.void).pipe(Effect47.andThen(readLive2(olds)), Effect47.map((live) => live === undefined ? undefined : { ...live, sealed: output?.sealed ?? "" })),
4168
+ var handlers14 = {
4169
+ list: () => Effect48.succeed([]),
4170
+ read: ({ olds, output }) => (output === undefined ? refuse2(olds) : Effect48.void).pipe(Effect48.andThen(readLive2(olds)), Effect48.map((live) => live === undefined ? undefined : { ...live, sealed: output?.sealed ?? "" })),
4109
4171
  diff: ({
4110
4172
  news,
4111
4173
  olds,
4112
4174
  output
4113
- }) => Effect47.gen(function* () {
4114
- if (output === undefined || !isResolved11(news))
4175
+ }) => Effect48.gen(function* () {
4176
+ if (output === undefined || !isResolved12(news))
4115
4177
  return;
4116
4178
  if (olds !== undefined && (olds.type !== news.type || olds.name !== news.name)) {
4117
4179
  return { action: "replace", deleteFirst: olds.name === news.name };
@@ -4122,7 +4184,7 @@ var handlers15 = {
4122
4184
  return { action: "update" };
4123
4185
  return toCarry(live, news, resolveGroups(news), output.sealed) === undefined ? { action: "noop" } : { action: "update" };
4124
4186
  }),
4125
- reconcile: ({ news, output }) => Effect47.gen(function* () {
4187
+ reconcile: ({ news, output }) => Effect48.gen(function* () {
4126
4188
  yield* refuse2(news);
4127
4189
  const groups = resolveGroups(news);
4128
4190
  const live = yield* readLive2(news);
@@ -4148,7 +4210,7 @@ var handlers15 = {
4148
4210
  }
4149
4211
  const after = yield* readLive2(news);
4150
4212
  if (after === undefined) {
4151
- return yield* Effect47.die(new Error(`${path(news)}: the write returned no error but the target is still absent.`));
4213
+ return yield* Effect48.die(new Error(`${path(news)}: the write returned no error but the target is still absent.`));
4152
4214
  }
4153
4215
  return { ...after, sealed };
4154
4216
  }),
@@ -4157,11 +4219,11 @@ var handlers15 = {
4157
4219
 
4158
4220
  // src/proxmox/pbs-notification-target.ts
4159
4221
  var PbsNotificationTarget = Resource21("Pbs.NotificationTarget");
4160
- var PbsNotificationTargetProvider = () => Provider21.effect(PbsNotificationTarget, Effect48.succeed(PbsNotificationTarget.Provider.of(handlers15)));
4222
+ var PbsNotificationTargetProvider = () => Provider21.effect(PbsNotificationTarget, Effect49.succeed(PbsNotificationTarget.Provider.of(handlers14)));
4161
4223
  // src/proxmox/pbs-prune-job.ts
4162
4224
  import { Resource as Resource22 } from "alchemy";
4163
4225
  import * as Provider22 from "alchemy/Provider";
4164
- import * as Effect49 from "effect/Effect";
4226
+ import * as Effect50 from "effect/Effect";
4165
4227
 
4166
4228
  // src/proxmox/pbs-prune-job-form.ts
4167
4229
  var KEEP_KEYS = [
@@ -4207,11 +4269,11 @@ var shape5 = (props) => ({
4207
4269
  schedule: props.schedule,
4208
4270
  store: props.store
4209
4271
  });
4210
- var createBody4 = (props) => {
4272
+ var createBody3 = (props) => {
4211
4273
  requireKeeps(props);
4212
4274
  return { ...shape5(props), id: props.id };
4213
4275
  };
4214
- var updateBody3 = (props) => {
4276
+ var updateBody2 = (props) => {
4215
4277
  requireKeeps(props);
4216
4278
  return shape5(props);
4217
4279
  };
@@ -4219,7 +4281,7 @@ var updateBody3 = (props) => {
4219
4281
  // src/proxmox/pbs-prune-job.ts
4220
4282
  var PbsPruneJob = Resource22("Pbs.PruneJob");
4221
4283
  var same6 = (declared2, live) => declared2 === undefined || declared2 === live;
4222
- var handlers16 = pveHandlers({
4284
+ var handlers15 = pveHandlers({
4223
4285
  attributes: (live, props) => ({
4224
4286
  comment: text(live["comment"], ""),
4225
4287
  disable: bool(live["disable"], false),
@@ -4231,17 +4293,17 @@ var handlers16 = pveHandlers({
4231
4293
  store: text(live["store"], props.store)
4232
4294
  }),
4233
4295
  collection: () => "config/prune",
4234
- createForm: createBody4,
4296
+ createForm: createBody3,
4235
4297
  endpoint: { create: "pbs:POST /config/prune", update: "pbs:PUT /config/prune/{id}" },
4236
4298
  matches: (attributes2, props) => attributes2.schedule === props.schedule && attributes2.store === props.store && same6(props.ns, attributes2.ns) && same6(props["max-depth"], attributes2["max-depth"]) && same6(props.disable, attributes2.disable) && same6(props.comment, attributes2.comment) && keepsMatch(attributes2, props),
4237
4299
  path: (props) => `config/prune/${props.id}`,
4238
- updateForm: updateBody3
4300
+ updateForm: updateBody2
4239
4301
  });
4240
- var PbsPruneJobProvider = () => Provider22.effect(PbsPruneJob, Effect49.succeed(PbsPruneJob.Provider.of(handlers16)));
4302
+ var PbsPruneJobProvider = () => Provider22.effect(PbsPruneJob, Effect50.succeed(PbsPruneJob.Provider.of(handlers15)));
4241
4303
  // src/proxmox/pbs-sync-job.ts
4242
4304
  import { Resource as Resource23 } from "alchemy";
4243
4305
  import * as Provider23 from "alchemy/Provider";
4244
- import * as Effect50 from "effect/Effect";
4306
+ import * as Effect51 from "effect/Effect";
4245
4307
 
4246
4308
  // src/proxmox/pbs-sync-job-form.ts
4247
4309
  var UNSET4 = -1;
@@ -4283,13 +4345,13 @@ var shape6 = (props) => ({
4283
4345
  ...props["verified-only"] === undefined ? {} : { "verified-only": props["verified-only"] ? "1" : "0" },
4284
4346
  ...props["transfer-last"] === undefined ? {} : { "transfer-last": String(props["transfer-last"]) }
4285
4347
  });
4286
- var createBody5 = (props) => ({
4348
+ var createBody4 = (props) => ({
4287
4349
  ...shape6(props),
4288
4350
  id: props.id,
4289
4351
  ...props["sync-direction"] === undefined ? {} : { "sync-direction": props["sync-direction"] }
4290
4352
  });
4291
- var updateBody4 = (props) => shape6(props);
4292
- var handlers17 = pveHandlers({
4353
+ var updateBody3 = (props) => shape6(props);
4354
+ var handlers16 = pveHandlers({
4293
4355
  attributes: (live, props) => ({
4294
4356
  comment: text(live["comment"], ""),
4295
4357
  "group-filter": filters(live["group-filter"]),
@@ -4309,20 +4371,20 @@ var handlers17 = pveHandlers({
4309
4371
  "transfer-last": int(live["transfer-last"], UNSET4)
4310
4372
  }),
4311
4373
  collection: () => "config/sync",
4312
- createForm: createBody5,
4374
+ createForm: createBody4,
4313
4375
  endpoint: { create: "pbs:POST /config/sync", update: "pbs:PUT /config/sync/{id}" },
4314
4376
  matches: (attributes2, props) => attributes2["remove-vanished"] === (props["remove-vanished"] === true) && attributes2.store === props.store && attributes2["remote-store"] === props["remote-store"] && (props.remote === undefined || attributes2.remote === props.remote) && (props.ns === undefined || attributes2.ns === props.ns) && (props["remote-ns"] === undefined || attributes2["remote-ns"] === props["remote-ns"]) && (props.schedule === undefined || attributes2.schedule === props.schedule) && (props.comment === undefined || attributes2.comment === props.comment) && (props.owner === undefined || attributes2.owner === props.owner) && (props["verified-only"] === undefined || attributes2["verified-only"] === props["verified-only"]) && (props["rate-in"] === undefined || attributes2["rate-in"] === props["rate-in"]) && (props["max-depth"] === undefined || attributes2["max-depth"] === props["max-depth"]) && (props["transfer-last"] === undefined || attributes2["transfer-last"] === props["transfer-last"]),
4315
4377
  path: (props) => `config/sync/${props.id}`,
4316
- updateForm: updateBody4
4378
+ updateForm: updateBody3
4317
4379
  });
4318
4380
 
4319
4381
  // src/proxmox/pbs-sync-job.ts
4320
4382
  var PbsSyncJob = Resource23("Pbs.SyncJob");
4321
- var PbsSyncJobProvider = () => Provider23.effect(PbsSyncJob, Effect50.succeed(PbsSyncJob.Provider.of(handlers17)));
4383
+ var PbsSyncJobProvider = () => Provider23.effect(PbsSyncJob, Effect51.succeed(PbsSyncJob.Provider.of(handlers16)));
4322
4384
  // src/proxmox/pbs-verify-job.ts
4323
4385
  import { Resource as Resource24 } from "alchemy";
4324
4386
  import * as Provider24 from "alchemy/Provider";
4325
- import * as Effect51 from "effect/Effect";
4387
+ import * as Effect52 from "effect/Effect";
4326
4388
 
4327
4389
  // src/proxmox/pbs-verify-job-form.ts
4328
4390
  var rechecks = (ignoreVerified, outdatedAfter) => {
@@ -4344,7 +4406,7 @@ var shape7 = (props) => ({
4344
4406
 
4345
4407
  // src/proxmox/pbs-verify-job.ts
4346
4408
  var PbsVerifyJob = Resource24("Pbs.VerifyJob");
4347
- var handlers18 = pveHandlers({
4409
+ var handlers17 = pveHandlers({
4348
4410
  attributes: (live, props) => {
4349
4411
  const ignoreVerified = bool(live["ignore-verified"], true);
4350
4412
  const outdatedAfter = int(live["outdated-after"], -1);
@@ -4367,11 +4429,11 @@ var handlers18 = pveHandlers({
4367
4429
  path: (props) => `config/verify/${props.id}`,
4368
4430
  updateForm: shape7
4369
4431
  });
4370
- var PbsVerifyJobProvider = () => Provider24.effect(PbsVerifyJob, Effect51.succeed(PbsVerifyJob.Provider.of(handlers18)));
4432
+ var PbsVerifyJobProvider = () => Provider24.effect(PbsVerifyJob, Effect52.succeed(PbsVerifyJob.Provider.of(handlers17)));
4371
4433
  // src/proxmox/pool.ts
4372
4434
  import { Resource as Resource25 } from "alchemy";
4373
4435
  import * as Provider25 from "alchemy/Provider";
4374
- import * as Effect52 from "effect/Effect";
4436
+ import * as Effect53 from "effect/Effect";
4375
4437
  var ProxmoxPool = Resource25("Proxmox.Pool");
4376
4438
  var poolCreateForm = (props) => ({
4377
4439
  comment: props.comment ?? "",
@@ -4380,7 +4442,7 @@ var poolCreateForm = (props) => ({
4380
4442
  var poolUpdateForm = (props) => ({
4381
4443
  comment: props.comment ?? ""
4382
4444
  });
4383
- var handlers19 = pveHandlers({
4445
+ var handlers18 = pveHandlers({
4384
4446
  attributes: (live, props) => {
4385
4447
  const row = live;
4386
4448
  return {
@@ -4396,7 +4458,7 @@ var handlers19 = pveHandlers({
4396
4458
  path: (props) => `pools/${props.poolid}`,
4397
4459
  updateForm: poolUpdateForm
4398
4460
  });
4399
- var ProxmoxPoolProvider = () => Provider25.effect(ProxmoxPool, Effect52.succeed(ProxmoxPool.Provider.of(handlers19)));
4461
+ var ProxmoxPoolProvider = () => Provider25.effect(ProxmoxPool, Effect53.succeed(ProxmoxPool.Provider.of(handlers18)));
4400
4462
  // src/proxmox/provision-baseline.ts
4401
4463
  var PROVISION_PRIVILEGES = Object.freeze([
4402
4464
  "Datastore.Allocate",
@@ -4589,53 +4651,53 @@ echo 'provision baseline: done. Next: point the OpenBao proxmox mount at these u
4589
4651
  // src/proxmox/provision-declare.ts
4590
4652
  import { adopt } from "alchemy/AdoptPolicy";
4591
4653
  import * as RemovalPolicy from "alchemy/RemovalPolicy";
4592
- import * as Effect56 from "effect/Effect";
4654
+ import * as Effect57 from "effect/Effect";
4593
4655
 
4594
4656
  // src/proxmox/role.ts
4595
4657
  import { Resource as Resource26 } from "alchemy";
4596
- import { isResolved as isResolved12 } from "alchemy/Diff";
4658
+ import { isResolved as isResolved13 } from "alchemy/Diff";
4597
4659
  import * as Provider26 from "alchemy/Provider";
4598
4660
  import * as access5 from "@distilled.cloud/proxmox/access";
4599
- import * as Effect53 from "effect/Effect";
4661
+ import * as Effect54 from "effect/Effect";
4600
4662
 
4601
4663
  // src/proxmox/role-wire.ts
4602
4664
  var ROLE_CREATE = "pve:POST /access/roles";
4603
4665
  var ROLE_UPDATE = "pve:PUT /access/roles/{roleid}";
4604
4666
  var canonical2 = (privs) => [...new Set(privs.map((priv) => priv.trim()).filter((priv) => priv.length > 0))].sort();
4605
- var createForm6 = (props) => ({
4667
+ var createForm7 = (props) => ({
4606
4668
  privs: canonical2(props.privs).join(","),
4607
4669
  roleid: props.roleid
4608
4670
  });
4609
- var updateForm3 = (props) => ({
4671
+ var updateForm4 = (props) => ({
4610
4672
  privs: canonical2(props.privs).join(","),
4611
4673
  roleid: props.roleid
4612
4674
  });
4613
4675
  var find2 = (rows, roleid) => rows.find((row) => row.roleid === roleid);
4614
- var attributesOf5 = (row, props) => ({
4676
+ var attributesOf6 = (row, props) => ({
4615
4677
  privs: canonical2(row.privs === undefined ? [] : row.privs.split(",")),
4616
4678
  roleid: props.roleid
4617
4679
  });
4618
- var matches5 = (attributes2, props) => canonical2(attributes2.privs).join(",") === canonical2(props.privs).join(",");
4680
+ var matches6 = (attributes2, props) => canonical2(attributes2.privs).join(",") === canonical2(props.privs).join(",");
4619
4681
 
4620
4682
  // src/proxmox/role.ts
4621
4683
  var ProxmoxRole = Resource26("Proxmox.Role");
4622
- var readRole = (props) => readOrUnreadable(runPve(props.target, "read", false, access5.listAccessRoles({}))).pipe(Effect53.map((rows) => {
4684
+ var readRole = (props) => readOrUnreadable(runPve(props.target, "read", false, access5.listAccessRoles({}))).pipe(Effect54.map((rows) => {
4623
4685
  if (rows === UNREADABLE)
4624
4686
  return UNREADABLE;
4625
4687
  const row = find2(rows, props.roleid);
4626
- return row === undefined ? undefined : attributesOf5(row, props);
4688
+ return row === undefined ? undefined : attributesOf6(row, props);
4627
4689
  }));
4628
- var dropUnreadable4 = (live) => live === UNREADABLE ? undefined : live;
4629
- var ProxmoxRoleProvider = () => Provider26.effect(ProxmoxRole, Effect53.succeed(ProxmoxRole.Provider.of({
4630
- list: () => Effect53.succeed([]),
4631
- read: Effect53.fn(function* ({ olds }) {
4632
- return dropUnreadable4(yield* readRole(olds));
4690
+ var dropUnreadable5 = (live) => live === UNREADABLE ? undefined : live;
4691
+ var ProxmoxRoleProvider = () => Provider26.effect(ProxmoxRole, Effect54.succeed(ProxmoxRole.Provider.of({
4692
+ list: () => Effect54.succeed([]),
4693
+ read: Effect54.fn(function* ({ olds }) {
4694
+ return dropUnreadable5(yield* readRole(olds));
4633
4695
  }),
4634
- diff: Effect53.fn(function* ({ news, output }) {
4635
- if (!isResolved12(news))
4696
+ diff: Effect54.fn(function* ({ news, output }) {
4697
+ if (!isResolved13(news))
4636
4698
  return;
4637
- yield* guardWrite2(ROLE_CREATE, createForm6(news), output === undefined);
4638
- yield* guardWrite2(ROLE_UPDATE, updateForm3(news), false);
4699
+ yield* guardWrite2(ROLE_CREATE, createForm7(news), output === undefined);
4700
+ yield* guardWrite2(ROLE_UPDATE, updateForm4(news), false);
4639
4701
  if (output === undefined)
4640
4702
  return;
4641
4703
  const live = yield* readRole(news);
@@ -4644,41 +4706,41 @@ var ProxmoxRoleProvider = () => Provider26.effect(ProxmoxRole, Effect53.succeed(
4644
4706
  return { action: "noop" };
4645
4707
  }
4646
4708
  if (live === undefined) {
4647
- yield* guardWrite2(ROLE_CREATE, createForm6(news), true);
4709
+ yield* guardWrite2(ROLE_CREATE, createForm7(news), true);
4648
4710
  return { action: "update" };
4649
4711
  }
4650
- return matches5(live, news) ? { action: "noop" } : { action: "update" };
4712
+ return matches6(live, news) ? { action: "noop" } : { action: "update" };
4651
4713
  }),
4652
- reconcile: Effect53.fn(function* ({ news }) {
4653
- const before = dropUnreadable4(yield* readRole(news));
4654
- yield* guardWrite2(ROLE_CREATE, createForm6(news), before === undefined);
4655
- yield* guardWrite2(ROLE_UPDATE, updateForm3(news), false);
4714
+ reconcile: Effect54.fn(function* ({ news }) {
4715
+ const before = dropUnreadable5(yield* readRole(news));
4716
+ yield* guardWrite2(ROLE_CREATE, createForm7(news), before === undefined);
4717
+ yield* guardWrite2(ROLE_UPDATE, updateForm4(news), false);
4656
4718
  if (before === undefined) {
4657
- yield* runPve(news.target, "provision", true, access5.createAccessRole(createForm6(news)));
4658
- } else if (!matches5(before, news)) {
4659
- yield* runPve(news.target, "provision", true, access5.putAccessRole(updateForm3(news)));
4719
+ yield* runPve(news.target, "provision", true, access5.createAccessRole(createForm7(news)));
4720
+ } else if (!matches6(before, news)) {
4721
+ yield* runPve(news.target, "provision", true, access5.putAccessRole(updateForm4(news)));
4660
4722
  }
4661
- const after = dropUnreadable4(yield* readRole(news));
4723
+ const after = dropUnreadable5(yield* readRole(news));
4662
4724
  if (after === undefined) {
4663
- return yield* Effect53.die(new Error(`access/roles/${news.roleid}: the write returned no error but the role is ` + 'still absent. PVE wraps every answer in {"data":...} and can report success ' + "on a call that did nothing -- read back rather than trusting the status code."));
4725
+ return yield* Effect54.die(new Error(`access/roles/${news.roleid}: the write returned no error but the role is ` + 'still absent. PVE wraps every answer in {"data":...} and can report success ' + "on a call that did nothing -- read back rather than trusting the status code."));
4664
4726
  }
4665
4727
  return after;
4666
4728
  }),
4667
- delete: Effect53.fn(function* ({ olds }) {
4729
+ delete: Effect54.fn(function* ({ olds }) {
4668
4730
  yield* runPve(olds.target, "provision", true, access5.deleteAccessRole({ roleid: olds.roleid }));
4669
4731
  })
4670
4732
  })));
4671
4733
 
4672
4734
  // src/proxmox/user.ts
4673
4735
  import { Resource as Resource27 } from "alchemy";
4674
- import { isResolved as isResolved13 } from "alchemy/Diff";
4736
+ import { isResolved as isResolved14 } from "alchemy/Diff";
4675
4737
  import * as Provider27 from "alchemy/Provider";
4676
4738
  import * as access7 from "@distilled.cloud/proxmox/access";
4677
- import * as Effect55 from "effect/Effect";
4739
+ import * as Effect56 from "effect/Effect";
4678
4740
 
4679
4741
  // src/proxmox/user-wire.ts
4680
4742
  import * as access6 from "@distilled.cloud/proxmox/access";
4681
- import * as Effect54 from "effect/Effect";
4743
+ import * as Effect55 from "effect/Effect";
4682
4744
  var USER_CREATE = "pve:POST /access/users";
4683
4745
  var USER_UPDATE = "pve:PUT /access/users/{userid}";
4684
4746
  var int2 = (value) => {
@@ -4700,15 +4762,15 @@ var shape8 = (props) => ({
4700
4762
  groups: groupSet(props.groups).join(","),
4701
4763
  lastname: props.lastname ?? ""
4702
4764
  });
4703
- var createForm7 = (props) => ({
4765
+ var createForm8 = (props) => ({
4704
4766
  ...shape8(props),
4705
4767
  userid: props.userid
4706
4768
  });
4707
- var updateForm4 = (props) => ({
4769
+ var updateForm5 = (props) => ({
4708
4770
  ...shape8(props),
4709
4771
  userid: props.userid
4710
4772
  });
4711
- var attributesOf6 = (live, props) => ({
4773
+ var attributesOf7 = (live, props) => ({
4712
4774
  comment: text(live.comment),
4713
4775
  email: text(live.email),
4714
4776
  enable: bool(live.enable, true),
@@ -4719,25 +4781,25 @@ var attributesOf6 = (live, props) => ({
4719
4781
  tokens: tokenNames(live.tokens),
4720
4782
  userid: props.userid
4721
4783
  });
4722
- var matches6 = (attributes2, props) => attributes2.comment === (props.comment ?? "") && attributes2.email === (props.email ?? "") && attributes2.enable === (props.enable !== false) && attributes2.expire === (props.expire ?? 0) && attributes2.firstname === (props.firstname ?? "") && attributes2.lastname === (props.lastname ?? "") && attributes2.groups.join(",") === groupSet(props.groups).join(",");
4723
- var readUserOrFail = (props) => readOrUnreadable(runPve(props.target, "read", false, access6.getAccessUser({ userid: props.userid }))).pipe(Effect54.map((live) => live === UNREADABLE ? UNREADABLE : attributesOf6(live, props)));
4724
- var readUser = (props) => readUserOrFail(props).pipe(Effect54.orElseSucceed(() => {
4784
+ var matches7 = (attributes2, props) => attributes2.comment === (props.comment ?? "") && attributes2.email === (props.email ?? "") && attributes2.enable === (props.enable !== false) && attributes2.expire === (props.expire ?? 0) && attributes2.firstname === (props.firstname ?? "") && attributes2.lastname === (props.lastname ?? "") && attributes2.groups.join(",") === groupSet(props.groups).join(",");
4785
+ var readUserOrFail = (props) => readOrUnreadable(runPve(props.target, "read", false, access6.getAccessUser({ userid: props.userid }))).pipe(Effect55.map((live) => live === UNREADABLE ? UNREADABLE : attributesOf7(live, props)));
4786
+ var readUser = (props) => readUserOrFail(props).pipe(Effect55.orElseSucceed(() => {
4725
4787
  return;
4726
4788
  }));
4727
- var dropUnreadable5 = (live) => live === UNREADABLE ? undefined : live;
4789
+ var dropUnreadable6 = (live) => live === UNREADABLE ? undefined : live;
4728
4790
 
4729
4791
  // src/proxmox/user.ts
4730
4792
  var ProxmoxUser = Resource27("Proxmox.User");
4731
- var ProxmoxUserProvider = () => Provider27.effect(ProxmoxUser, Effect55.succeed(ProxmoxUser.Provider.of({
4732
- list: () => Effect55.succeed([]),
4733
- read: Effect55.fn(function* ({ olds, output }) {
4734
- return dropUnreadable5(yield* output === undefined ? readUser(olds) : readUserOrFail(olds));
4793
+ var ProxmoxUserProvider = () => Provider27.effect(ProxmoxUser, Effect56.succeed(ProxmoxUser.Provider.of({
4794
+ list: () => Effect56.succeed([]),
4795
+ read: Effect56.fn(function* ({ olds, output }) {
4796
+ return dropUnreadable6(yield* output === undefined ? readUser(olds) : readUserOrFail(olds));
4735
4797
  }),
4736
- diff: Effect55.fn(function* ({ news, output }) {
4737
- if (!isResolved13(news))
4798
+ diff: Effect56.fn(function* ({ news, output }) {
4799
+ if (!isResolved14(news))
4738
4800
  return;
4739
- yield* guardWrite2(USER_CREATE, createForm7(news), output === undefined);
4740
- yield* guardWrite2(USER_UPDATE, updateForm4(news), false);
4801
+ yield* guardWrite2(USER_CREATE, createForm8(news), output === undefined);
4802
+ yield* guardWrite2(USER_UPDATE, updateForm5(news), false);
4741
4803
  if (output === undefined)
4742
4804
  return;
4743
4805
  const live = yield* readUserOrFail(news);
@@ -4746,34 +4808,34 @@ var ProxmoxUserProvider = () => Provider27.effect(ProxmoxUser, Effect55.succeed(
4746
4808
  return { action: "noop" };
4747
4809
  }
4748
4810
  if (live === undefined) {
4749
- yield* guardWrite2(USER_CREATE, createForm7(news), true);
4811
+ yield* guardWrite2(USER_CREATE, createForm8(news), true);
4750
4812
  return { action: "update" };
4751
4813
  }
4752
- return matches6(live, news) ? { action: "noop" } : { action: "update" };
4814
+ return matches7(live, news) ? { action: "noop" } : { action: "update" };
4753
4815
  }),
4754
- reconcile: Effect55.fn(function* ({ news }) {
4755
- const before = dropUnreadable5(yield* readUser(news));
4756
- yield* guardWrite2(USER_CREATE, createForm7(news), before === undefined);
4757
- yield* guardWrite2(USER_UPDATE, updateForm4(news), false);
4816
+ reconcile: Effect56.fn(function* ({ news }) {
4817
+ const before = dropUnreadable6(yield* readUser(news));
4818
+ yield* guardWrite2(USER_CREATE, createForm8(news), before === undefined);
4819
+ yield* guardWrite2(USER_UPDATE, updateForm5(news), false);
4758
4820
  if (before === undefined) {
4759
- yield* runPve(news.target, "provision", true, access7.createAccessUser(createForm7(news)));
4760
- } else if (!matches6(before, news)) {
4761
- yield* runPve(news.target, "provision", true, access7.putAccessUser(updateForm4(news)));
4821
+ yield* runPve(news.target, "provision", true, access7.createAccessUser(createForm8(news)));
4822
+ } else if (!matches7(before, news)) {
4823
+ yield* runPve(news.target, "provision", true, access7.putAccessUser(updateForm5(news)));
4762
4824
  }
4763
- const after = dropUnreadable5(yield* readUser(news));
4825
+ const after = dropUnreadable6(yield* readUser(news));
4764
4826
  if (after === undefined) {
4765
- return yield* Effect55.die(new Error(`access/users/${news.userid}: the write returned no error but the account is ` + 'still absent. PVE wraps every answer in {"data":...} and can report success ' + "on a call that did nothing -- read back rather than trusting the status code."));
4827
+ return yield* Effect56.die(new Error(`access/users/${news.userid}: the write returned no error but the account is ` + 'still absent. PVE wraps every answer in {"data":...} and can report success ' + "on a call that did nothing -- read back rather than trusting the status code."));
4766
4828
  }
4767
4829
  return after;
4768
4830
  }),
4769
- delete: Effect55.fn(function* ({ olds }) {
4831
+ delete: Effect56.fn(function* ({ olds }) {
4770
4832
  yield* runPve(olds.target, "provision", true, access7.deleteAccessUser({ userid: olds.userid }));
4771
4833
  })
4772
4834
  })));
4773
4835
 
4774
4836
  // src/proxmox/provision-declare.ts
4775
- var declareProvisionBaseline = (id, target, names2 = {}, options = {}) => Effect56.gen(function* () {
4776
- const baseline = yield* Effect56.try({
4837
+ var declareProvisionBaseline = (id, target, names2 = {}, options = {}) => Effect57.gen(function* () {
4838
+ const baseline = yield* Effect57.try({
4777
4839
  catch: (cause) => cause instanceof Error ? cause : new Error(String(cause)),
4778
4840
  try: () => provisionBaseline(names2)
4779
4841
  });
@@ -4787,13 +4849,13 @@ var declareProvisionBaseline = (id, target, names2 = {}, options = {}) => Effect
4787
4849
  target
4788
4850
  }));
4789
4851
  const group = yield* owned(ProxmoxGroup(`${id}-mint-group`, { ...baseline.group, target }));
4790
- const users = yield* Effect56.all(baseline.users.map((user) => owned(ProxmoxUser(`${id}-${user.lane}-user`, {
4852
+ const users = yield* Effect57.all(baseline.users.map((user) => owned(ProxmoxUser(`${id}-${user.lane}-user`, {
4791
4853
  comment: user.comment,
4792
4854
  groups: [...user.groups],
4793
4855
  target,
4794
4856
  userid: user.userid
4795
4857
  }))));
4796
- const grants = yield* Effect56.all(baseline.grants.map((grant) => owned(ProxmoxAcl(`${id}-${grant.lane}-grant`, {
4858
+ const grants = yield* Effect57.all(baseline.grants.map((grant) => owned(ProxmoxAcl(`${id}-${grant.lane}-grant`, {
4797
4859
  path: "/",
4798
4860
  propagate: true,
4799
4861
  roleid: grant.roleid,
@@ -4806,9 +4868,9 @@ var declareProvisionBaseline = (id, target, names2 = {}, options = {}) => Effect
4806
4868
  // src/proxmox/qemu.ts
4807
4869
  import { Resource as Resource28 } from "alchemy";
4808
4870
  import * as Provider28 from "alchemy/Provider";
4809
- import * as Effect57 from "effect/Effect";
4871
+ import * as Effect58 from "effect/Effect";
4810
4872
  var ProxmoxVm = Resource28("Proxmox.Vm");
4811
- var createForm8 = (props) => ({ ...shape9(props), vmid: String(props.vmid) });
4873
+ var createForm9 = (props) => ({ ...shape9(props), vmid: String(props.vmid) });
4812
4874
  var shape9 = (props) => ({
4813
4875
  cores: String(props.cores ?? 1),
4814
4876
  memory: String(props.memory ?? 512),
@@ -4817,7 +4879,7 @@ var shape9 = (props) => ({
4817
4879
  sockets: String(props.sockets ?? 1),
4818
4880
  ...props.net0 === undefined ? {} : { net0: props.net0 }
4819
4881
  });
4820
- var handlers20 = pveHandlers({
4882
+ var handlers19 = pveHandlers({
4821
4883
  attributes: (live, props) => ({
4822
4884
  cores: num(live["cores"], 1),
4823
4885
  memory: num(live["memory"], 512),
@@ -4828,7 +4890,7 @@ var handlers20 = pveHandlers({
4828
4890
  vmid: props.vmid
4829
4891
  }),
4830
4892
  collection: (props) => `nodes/${props.node}/qemu`,
4831
- createForm: createForm8,
4893
+ createForm: createForm9,
4832
4894
  endpoint: {
4833
4895
  create: "pve:POST /nodes/{node}/qemu",
4834
4896
  update: "pve:PUT /nodes/{node}/qemu/{vmid}/config"
@@ -4837,11 +4899,11 @@ var handlers20 = pveHandlers({
4837
4899
  path: (props) => `nodes/${props.node}/qemu/${String(props.vmid)}/config`,
4838
4900
  updateForm: shape9
4839
4901
  });
4840
- var ProxmoxVmProvider = () => Provider28.effect(ProxmoxVm, Effect57.succeed(ProxmoxVm.Provider.of(handlers20)));
4902
+ var ProxmoxVmProvider = () => Provider28.effect(ProxmoxVm, Effect58.succeed(ProxmoxVm.Provider.of(handlers19)));
4841
4903
  // src/proxmox/replication-job.ts
4842
4904
  import { Resource as Resource29 } from "alchemy";
4843
4905
  import * as Provider29 from "alchemy/Provider";
4844
- import * as Effect58 from "effect/Effect";
4906
+ import * as Effect59 from "effect/Effect";
4845
4907
 
4846
4908
  // src/proxmox/replication-job-form.ts
4847
4909
  var DEFAULT_SCHEDULE = "*/15";
@@ -4852,13 +4914,13 @@ var shape10 = (props) => ({
4852
4914
  schedule: props.schedule ?? DEFAULT_SCHEDULE,
4853
4915
  ...props.rate === undefined ? {} : { rate: String(props.rate) }
4854
4916
  });
4855
- var createBody6 = (props) => ({
4917
+ var createBody5 = (props) => ({
4856
4918
  ...shape10(props),
4857
4919
  id: jobId(props),
4858
4920
  target: props.targetNode,
4859
4921
  type: "local"
4860
4922
  });
4861
- var updateBody5 = (props) => ({
4923
+ var updateBody4 = (props) => ({
4862
4924
  ...shape10(props),
4863
4925
  delete: "remove_job"
4864
4926
  });
@@ -4871,7 +4933,7 @@ var rateOf = (value) => {
4871
4933
  const parsed = Number.parseFloat(text(value));
4872
4934
  return Number.isFinite(parsed) ? parsed : 0;
4873
4935
  };
4874
- var handlers21 = pveHandlers({
4936
+ var handlers20 = pveHandlers({
4875
4937
  attributes: (live, props) => ({
4876
4938
  comment: text(live["comment"], ""),
4877
4939
  disable: bool(live["disable"], false),
@@ -4886,24 +4948,24 @@ var handlers21 = pveHandlers({
4886
4948
  type: text(live["type"], "local")
4887
4949
  }),
4888
4950
  collection: () => "cluster/replication",
4889
- createForm: createBody6,
4951
+ createForm: createBody5,
4890
4952
  endpoint: {
4891
4953
  create: "pve:POST /cluster/replication",
4892
4954
  update: "pve:PUT /cluster/replication/{id}"
4893
4955
  },
4894
4956
  matches: (attributes2, props) => attributes2.remove_job === "" && attributes2.schedule === (props.schedule ?? DEFAULT_SCHEDULE) && attributes2.disable === (props.disable === true) && attributes2.comment === (props.comment ?? "") && (props.rate === undefined || attributes2.rate === props.rate),
4895
4957
  path: (props) => `cluster/replication/${jobId(props)}`,
4896
- updateForm: updateBody5
4958
+ updateForm: updateBody4
4897
4959
  });
4898
- var ProxmoxReplicationJobProvider = () => Provider29.effect(ProxmoxReplicationJob, Effect58.succeed(ProxmoxReplicationJob.Provider.of(handlers21)));
4960
+ var ProxmoxReplicationJobProvider = () => Provider29.effect(ProxmoxReplicationJob, Effect59.succeed(ProxmoxReplicationJob.Provider.of(handlers20)));
4899
4961
  // src/proxmox/sdn-apply.ts
4900
4962
  import { Resource as Resource30 } from "alchemy";
4901
- import { isResolved as isResolved14 } from "alchemy/Diff";
4963
+ import { isResolved as isResolved15 } from "alchemy/Diff";
4902
4964
  import * as Provider30 from "alchemy/Provider";
4903
- import * as Effect60 from "effect/Effect";
4965
+ import * as Effect61 from "effect/Effect";
4904
4966
 
4905
4967
  // src/proxmox/sdn-apply-read.ts
4906
- import * as Effect59 from "effect/Effect";
4968
+ import * as Effect60 from "effect/Effect";
4907
4969
  var MARKED = [
4908
4970
  "cluster/sdn/zones",
4909
4971
  "cluster/sdn/vnets",
@@ -4912,7 +4974,7 @@ var MARKED = [
4912
4974
  "cluster/sdn/route-maps"
4913
4975
  ];
4914
4976
  var subsystemAbsent = (error) => error instanceof PveError && error.status === 501;
4915
- var markedPending = (target) => Effect59.all(MARKED.map((collection2) => pve(target, "read", "GET", `${collection2}?pending=1`).pipe(Effect59.map((rows) => (rows ?? []).filter((row) => row.state !== undefined).length), Effect59.catchIf(subsystemAbsent, () => Effect59.succeed(0)))), { concurrency: "unbounded" }).pipe(Effect59.map((counts) => counts.reduce((total, count2) => total + count2, 0)));
4977
+ var markedPending = (target) => Effect60.all(MARKED.map((collection2) => pve(target, "read", "GET", `${collection2}?pending=1`).pipe(Effect60.map((rows) => (rows ?? []).filter((row) => row.state !== undefined).length), Effect60.catchIf(subsystemAbsent, () => Effect60.succeed(0)))), { concurrency: "unbounded" }).pipe(Effect60.map((counts) => counts.reduce((total, count2) => total + count2, 0)));
4916
4978
  var fabricStaged = (staged, running) => {
4917
4979
  if (staged === undefined && running === undefined)
4918
4980
  return 0;
@@ -4920,9 +4982,9 @@ var fabricStaged = (staged, running) => {
4920
4982
  return "inconsistent";
4921
4983
  return staged === running ? 0 : 1;
4922
4984
  };
4923
- var fabricPending = (target) => Effect59.all(["pending", "running"].map((view) => pve(target, "read", "GET", `cluster/sdn/fabrics/all?${view}=1`).pipe(Effect59.map(canonical3), Effect59.catchIf(subsystemAbsent, () => Effect59.succeed(undefined)))), { concurrency: "unbounded" }).pipe(Effect59.flatMap(([staged, running]) => {
4985
+ var fabricPending = (target) => Effect60.all(["pending", "running"].map((view) => pve(target, "read", "GET", `cluster/sdn/fabrics/all?${view}=1`).pipe(Effect60.map(canonical3), Effect60.catchIf(subsystemAbsent, () => Effect60.succeed(undefined)))), { concurrency: "unbounded" }).pipe(Effect60.flatMap(([staged, running]) => {
4924
4986
  const verdict = fabricStaged(staged, running);
4925
- return verdict === "inconsistent" ? Effect59.die(new Error("cluster/sdn/fabrics/all answered 501 for one of ?pending=1 and ?running=1 and not " + "the other. Refusing to read that as a staged fabric change.")) : Effect59.succeed(verdict);
4987
+ return verdict === "inconsistent" ? Effect60.die(new Error("cluster/sdn/fabrics/all answered 501 for one of ?pending=1 and ?running=1 and not " + "the other. Refusing to read that as a staged fabric change.")) : Effect60.succeed(verdict);
4926
4988
  }));
4927
4989
  var canonical3 = (value) => JSON.stringify(sortDeep(value));
4928
4990
  var sortDeep = (value) => {
@@ -4935,23 +4997,23 @@ var sortDeep = (value) => {
4935
4997
  }
4936
4998
  return value;
4937
4999
  };
4938
- var sdnPendingCount = (target) => Effect59.all([markedPending(target), fabricPending(target)], { concurrency: "unbounded" }).pipe(Effect59.map(([marked, fabric]) => marked + fabric));
5000
+ var sdnPendingCount = (target) => Effect60.all([markedPending(target), fabricPending(target)], { concurrency: "unbounded" }).pipe(Effect60.map(([marked, fabric]) => marked + fabric));
4939
5001
 
4940
5002
  // src/proxmox/sdn-apply.ts
4941
5003
  var ProxmoxSdnApply = Resource30("Proxmox.SdnApply");
4942
- var read3 = (props) => sdnPendingCount(props.target).pipe(Effect60.map((pending) => ({ pending })));
4943
- var ProxmoxSdnApplyProvider = () => Provider30.effect(ProxmoxSdnApply, Effect60.succeed(ProxmoxSdnApply.Provider.of({
4944
- list: () => Effect60.succeed([]),
4945
- read: Effect60.fn(function* ({ olds }) {
5004
+ var read3 = (props) => sdnPendingCount(props.target).pipe(Effect61.map((pending) => ({ pending })));
5005
+ var ProxmoxSdnApplyProvider = () => Provider30.effect(ProxmoxSdnApply, Effect61.succeed(ProxmoxSdnApply.Provider.of({
5006
+ list: () => Effect61.succeed([]),
5007
+ read: Effect61.fn(function* ({ olds }) {
4946
5008
  return yield* read3(olds);
4947
5009
  }),
4948
- diff: Effect60.fn(function* ({ news }) {
4949
- if (!isResolved14(news))
5010
+ diff: Effect61.fn(function* ({ news }) {
5011
+ if (!isResolved15(news))
4950
5012
  return;
4951
5013
  const { pending } = yield* read3(news);
4952
5014
  return pending === 0 ? { action: "noop" } : { action: "update" };
4953
5015
  }),
4954
- reconcile: Effect60.fn(function* ({ news }) {
5016
+ reconcile: Effect61.fn(function* ({ news }) {
4955
5017
  const staged = yield* read3(news);
4956
5018
  if (staged.pending === 0)
4957
5019
  return staged;
@@ -4959,16 +5021,16 @@ var ProxmoxSdnApplyProvider = () => Provider30.effect(ProxmoxSdnApply, Effect60.
4959
5021
  yield* pve(news.target, "provision", "PUT", "cluster/sdn");
4960
5022
  const after = yield* read3(news);
4961
5023
  if (after.pending !== 0) {
4962
- return yield* Effect60.die(new Error(`PUT /cluster/sdn returned no error but ${String(after.pending)} SDN object(s) ` + "are still staged. The running config does not match the declared one -- check " + "`pvesh get /cluster/sdn/zones --pending 1` for the objects PVE refused."));
5024
+ return yield* Effect61.die(new Error(`PUT /cluster/sdn returned no error but ${String(after.pending)} SDN object(s) ` + "are still staged. The running config does not match the declared one -- check " + "`pvesh get /cluster/sdn/zones --pending 1` for the objects PVE refused."));
4963
5025
  }
4964
5026
  return after;
4965
5027
  }),
4966
- delete: () => Effect60.void
5028
+ delete: () => Effect61.void
4967
5029
  })));
4968
5030
  // src/proxmox/sdn-subnet.ts
4969
5031
  import { Resource as Resource31 } from "alchemy";
4970
5032
  import * as Provider31 from "alchemy/Provider";
4971
- import * as Effect61 from "effect/Effect";
5033
+ import * as Effect62 from "effect/Effect";
4972
5034
 
4973
5035
  // src/proxmox/sdn-subnet-form.ts
4974
5036
  var subnetId = (props) => `${props.zone}-${props.cidr.replace("/", "-")}`;
@@ -4987,19 +5049,19 @@ var body5 = (props) => ({
4987
5049
  vnet: props.vnet,
4988
5050
  ...Object.fromEntries(Object.entries(optional3(props)).filter((entry) => entry[1] !== undefined))
4989
5051
  });
4990
- var createForm9 = (props) => ({
5052
+ var createForm10 = (props) => ({
4991
5053
  ...body5(props),
4992
5054
  subnet: props.cidr,
4993
5055
  type: "subnet"
4994
5056
  });
4995
- var updateForm5 = (props) => {
5057
+ var updateForm6 = (props) => {
4996
5058
  const clear = Object.entries(optional3(props)).filter(([, value]) => value === undefined).map(([key]) => key);
4997
5059
  return withClears(body5(props), clear);
4998
5060
  };
4999
5061
 
5000
5062
  // src/proxmox/sdn-subnet.ts
5001
5063
  var ProxmoxSdnSubnet = Resource31("Proxmox.SdnSubnet");
5002
- var handlers22 = pveHandlers({
5064
+ var handlers21 = pveHandlers({
5003
5065
  attributes: (live, props) => {
5004
5066
  const liveVnet = text(live["vnet"]);
5005
5067
  if (liveVnet !== "" && liveVnet !== props.vnet)
@@ -5019,20 +5081,20 @@ var handlers22 = pveHandlers({
5019
5081
  };
5020
5082
  },
5021
5083
  collection: (props) => `cluster/sdn/vnets/${props.vnet}/subnets`,
5022
- createForm: createForm9,
5084
+ createForm: createForm10,
5023
5085
  endpoint: {
5024
5086
  create: "pve:POST /cluster/sdn/vnets/{vnet}/subnets",
5025
5087
  update: "pve:PUT /cluster/sdn/vnets/{vnet}/subnets/{subnet}"
5026
5088
  },
5027
5089
  matches: (attributes2, props) => attributes2.gateway === (props.gateway ?? "") && attributes2.snat === (props.snat === true) && attributes2.dnszoneprefix === (props.dnszoneprefix ?? "") && attributes2.dhcpDnsServer === (props.dhcpDnsServer ?? "") && attributes2.dhcpRange === declaredRanges(props.dhcpRange),
5028
5090
  path: (props) => `cluster/sdn/vnets/${props.vnet}/subnets/${subnetId(props)}`,
5029
- updateForm: updateForm5
5091
+ updateForm: updateForm6
5030
5092
  });
5031
- var ProxmoxSdnSubnetProvider = () => Provider31.effect(ProxmoxSdnSubnet, Effect61.succeed(ProxmoxSdnSubnet.Provider.of(handlers22)));
5093
+ var ProxmoxSdnSubnetProvider = () => Provider31.effect(ProxmoxSdnSubnet, Effect62.succeed(ProxmoxSdnSubnet.Provider.of(handlers21)));
5032
5094
  // src/proxmox/sdn-vnet.ts
5033
5095
  import { Resource as Resource32 } from "alchemy";
5034
5096
  import * as Provider32 from "alchemy/Provider";
5035
- import * as Effect62 from "effect/Effect";
5097
+ import * as Effect63 from "effect/Effect";
5036
5098
  var ProxmoxSdnVnet = Resource32("Proxmox.SdnVnet");
5037
5099
  var tagOf = (value) => typeof value === "number" ? value : undefined;
5038
5100
  var shape11 = (props) => {
@@ -5045,14 +5107,14 @@ var shape11 = (props) => {
5045
5107
  ...props.tag === undefined ? {} : { tag: String(props.tag) }
5046
5108
  };
5047
5109
  };
5048
- var updateForm6 = (props) => {
5110
+ var updateForm7 = (props) => {
5049
5111
  const unset2 = [
5050
5112
  ...(props.alias ?? "") === "" ? ["alias"] : [],
5051
5113
  ...props.tag === undefined ? ["tag"] : []
5052
5114
  ];
5053
5115
  return withClears(shape11(props), unset2);
5054
5116
  };
5055
- var handlers23 = pveHandlers({
5117
+ var handlers22 = pveHandlers({
5056
5118
  readRole: "provision",
5057
5119
  attributes: (live, props) => ({
5058
5120
  alias: typeof live["alias"] === "string" ? live["alias"] : "",
@@ -5068,13 +5130,13 @@ var handlers23 = pveHandlers({
5068
5130
  endpoint: { create: "pve:POST /cluster/sdn/vnets", update: "pve:PUT /cluster/sdn/vnets/{vnet}" },
5069
5131
  matches: (attributes2, props) => attributes2.zone === props.zone && attributes2.alias === (props.alias ?? "") && attributes2.tag === props.tag && attributes2.vlanaware === (props.vlanaware === true) && attributes2.isolatePorts === (props.isolatePorts === true),
5070
5132
  path: (props) => `cluster/sdn/vnets/${props.vnet}`,
5071
- updateForm: updateForm6
5133
+ updateForm: updateForm7
5072
5134
  });
5073
- var ProxmoxSdnVnetProvider = () => Provider32.effect(ProxmoxSdnVnet, Effect62.succeed(ProxmoxSdnVnet.Provider.of(handlers23)));
5135
+ var ProxmoxSdnVnetProvider = () => Provider32.effect(ProxmoxSdnVnet, Effect63.succeed(ProxmoxSdnVnet.Provider.of(handlers22)));
5074
5136
  // src/proxmox/sdn-zone.ts
5075
5137
  import { Resource as Resource33 } from "alchemy";
5076
5138
  import * as Provider33 from "alchemy/Provider";
5077
- import * as Effect63 from "effect/Effect";
5139
+ import * as Effect64 from "effect/Effect";
5078
5140
  var ProxmoxSdnZone = Resource33("Proxmox.SdnZone");
5079
5141
  var sameIpam = (live, declared2) => (live === "" ? "pve" : live) === (declared2 === undefined || declared2 === "" ? "pve" : declared2);
5080
5142
  var body6 = (props) => ({
@@ -5095,7 +5157,7 @@ var clearable = {
5095
5157
  vlan: ["dns", "dnszone", "ipam", "mtu", "nodes"],
5096
5158
  vxlan: ["dns", "dnszone", "ipam", "mtu", "nodes"]
5097
5159
  };
5098
- var handlers24 = pveHandlers({
5160
+ var handlers23 = pveHandlers({
5099
5161
  readRole: "provision",
5100
5162
  attributes: (live, props) => {
5101
5163
  const liveType = text(live["type"]);
@@ -5127,13 +5189,13 @@ var handlers24 = pveHandlers({
5127
5189
  return withClears(fields, clear);
5128
5190
  }
5129
5191
  });
5130
- var ProxmoxSdnZoneProvider = () => Provider33.effect(ProxmoxSdnZone, Effect63.succeed(ProxmoxSdnZone.Provider.of(handlers24)));
5192
+ var ProxmoxSdnZoneProvider = () => Provider33.effect(ProxmoxSdnZone, Effect64.succeed(ProxmoxSdnZone.Provider.of(handlers23)));
5131
5193
  // src/proxmox/storage.ts
5132
5194
  import { Resource as Resource34 } from "alchemy";
5133
- import { isResolved as isResolved15 } from "alchemy/Diff";
5195
+ import { isResolved as isResolved16 } from "alchemy/Diff";
5134
5196
  import * as Provider34 from "alchemy/Provider";
5135
5197
  import * as storage2 from "@distilled.cloud/proxmox/storage";
5136
- import * as Effect65 from "effect/Effect";
5198
+ import * as Effect66 from "effect/Effect";
5137
5199
 
5138
5200
  // src/proxmox/storage-form.ts
5139
5201
  var STORAGE_CREATE = "pve:POST /storage";
@@ -5150,27 +5212,27 @@ var mutable2 = (props) => ({
5150
5212
  ...field6("prune-backups", props["prune-backups"]),
5151
5213
  ...field6("shared", flag(props.shared))
5152
5214
  });
5153
- var createForm10 = (props) => ({
5215
+ var createForm11 = (props) => ({
5154
5216
  ...locatorForm(props.locator),
5155
5217
  ...mutable2(props),
5156
5218
  storage: props.storage,
5157
5219
  type: props.type
5158
5220
  });
5159
- var updateForm7 = (props) => ({
5221
+ var updateForm8 = (props) => ({
5160
5222
  ...mutable2(props),
5161
5223
  storage: props.storage
5162
5224
  });
5163
- var toDistilledCreate = (props) => underscored(createForm10(props));
5164
- var toDistilledUpdate = (props) => underscored(updateForm7(props));
5225
+ var toDistilledCreate2 = (props) => underscored(createForm11(props));
5226
+ var toDistilledUpdate2 = (props) => underscored(updateForm8(props));
5165
5227
 
5166
5228
  // src/proxmox/storage-wire.ts
5167
5229
  import * as storage from "@distilled.cloud/proxmox/storage";
5168
- import * as Effect64 from "effect/Effect";
5230
+ import * as Effect65 from "effect/Effect";
5169
5231
  var str2 = (value, fallback = "") => typeof value === "string" ? value : fallback;
5170
5232
  var tokens = (value) => value.split(",").map((part) => part.trim()).filter((part) => part !== "").sort().join(",");
5171
5233
  var sameList2 = (declared2, live) => declared2 === undefined || tokens(declared2) === tokens(live);
5172
5234
  var same7 = (declared2, live) => declared2 === undefined || declared2 === live;
5173
- var attributesOf7 = (live, props) => {
5235
+ var attributesOf8 = (live, props) => {
5174
5236
  const data = live;
5175
5237
  return {
5176
5238
  comment: str2(data["comment"]),
@@ -5184,27 +5246,27 @@ var attributesOf7 = (live, props) => {
5184
5246
  type: str2(data["type"], props.type)
5185
5247
  };
5186
5248
  };
5187
- var readStorageOrFail = (props) => readOrUnreadable(runPve(props.target, "provision", false, storage.getStorage({ storage: props.storage }))).pipe(Effect64.map((live) => live === UNREADABLE ? UNREADABLE : attributesOf7(live, props)));
5188
- var readStorage = (props) => readStorageOrFail(props).pipe(Effect64.orElseSucceed(() => {
5249
+ var readStorageOrFail = (props) => readOrUnreadable(runPve(props.target, "provision", false, storage.getStorage({ storage: props.storage }))).pipe(Effect65.map((live) => live === UNREADABLE ? UNREADABLE : attributesOf8(live, props)));
5250
+ var readStorage = (props) => readStorageOrFail(props).pipe(Effect65.orElseSucceed(() => {
5189
5251
  return;
5190
5252
  }));
5191
- var dropUnreadable6 = (live) => live === UNREADABLE ? undefined : live;
5192
- var matches7 = (attributes2, props) => sameList2(props.content, attributes2.content) && sameList2(props.nodes, attributes2.nodes) && sameList2(props["prune-backups"], attributes2["prune-backups"]) && same7(props.disable, attributes2.disable) && same7(props.shared, attributes2.shared) && same7(props.preallocation, attributes2.preallocation) && same7(props.comment, attributes2.comment);
5253
+ var dropUnreadable7 = (live) => live === UNREADABLE ? undefined : live;
5254
+ var matches8 = (attributes2, props) => sameList2(props.content, attributes2.content) && sameList2(props.nodes, attributes2.nodes) && sameList2(props["prune-backups"], attributes2["prune-backups"]) && same7(props.disable, attributes2.disable) && same7(props.shared, attributes2.shared) && same7(props.preallocation, attributes2.preallocation) && same7(props.comment, attributes2.comment);
5193
5255
 
5194
5256
  // src/proxmox/storage.ts
5195
5257
  var ProxmoxStorage = Resource34("Proxmox.Storage", {
5196
5258
  defaultRemovalPolicy: "retain"
5197
5259
  });
5198
- var ProxmoxStorageProvider = () => Provider34.effect(ProxmoxStorage, Effect65.succeed(ProxmoxStorage.Provider.of({
5199
- list: () => Effect65.succeed([]),
5200
- read: Effect65.fn(function* ({ olds, output }) {
5201
- return dropUnreadable6(yield* output === undefined ? readStorage(olds) : readStorageOrFail(olds));
5260
+ var ProxmoxStorageProvider = () => Provider34.effect(ProxmoxStorage, Effect66.succeed(ProxmoxStorage.Provider.of({
5261
+ list: () => Effect66.succeed([]),
5262
+ read: Effect66.fn(function* ({ olds, output }) {
5263
+ return dropUnreadable7(yield* output === undefined ? readStorage(olds) : readStorageOrFail(olds));
5202
5264
  }),
5203
- diff: Effect65.fn(function* ({ news, output }) {
5204
- if (!isResolved15(news))
5265
+ diff: Effect66.fn(function* ({ news, output }) {
5266
+ if (!isResolved16(news))
5205
5267
  return;
5206
- yield* guardWrite2(STORAGE_CREATE, createForm10(news), output === undefined);
5207
- yield* guardWrite2(STORAGE_UPDATE, updateForm7(news), false);
5268
+ yield* guardWrite2(STORAGE_CREATE, createForm11(news), output === undefined);
5269
+ yield* guardWrite2(STORAGE_UPDATE, updateForm8(news), false);
5208
5270
  if (output === undefined)
5209
5271
  return;
5210
5272
  const live = yield* readStorageOrFail(news);
@@ -5213,67 +5275,67 @@ var ProxmoxStorageProvider = () => Provider34.effect(ProxmoxStorage, Effect65.su
5213
5275
  return { action: "noop" };
5214
5276
  }
5215
5277
  if (live === undefined) {
5216
- yield* guardWrite2(STORAGE_CREATE, createForm10(news), true);
5278
+ yield* guardWrite2(STORAGE_CREATE, createForm11(news), true);
5217
5279
  return { action: "update" };
5218
5280
  }
5219
- return matches7(live, news) ? { action: "noop" } : { action: "update" };
5281
+ return matches8(live, news) ? { action: "noop" } : { action: "update" };
5220
5282
  }),
5221
- reconcile: Effect65.fn(function* ({ news }) {
5222
- const before = dropUnreadable6(yield* readStorage(news));
5223
- yield* guardWrite2(STORAGE_CREATE, createForm10(news), before === undefined);
5224
- yield* guardWrite2(STORAGE_UPDATE, updateForm7(news), false);
5283
+ reconcile: Effect66.fn(function* ({ news }) {
5284
+ const before = dropUnreadable7(yield* readStorage(news));
5285
+ yield* guardWrite2(STORAGE_CREATE, createForm11(news), before === undefined);
5286
+ yield* guardWrite2(STORAGE_UPDATE, updateForm8(news), false);
5225
5287
  if (before === undefined) {
5226
- yield* runPve(news.target, "provision", true, storage2.createStorage(toDistilledCreate(news)));
5227
- } else if (!matches7(before, news)) {
5228
- yield* runPve(news.target, "provision", true, storage2.putStorage(toDistilledUpdate(news)));
5288
+ yield* runPve(news.target, "provision", true, storage2.createStorage(toDistilledCreate2(news)));
5289
+ } else if (!matches8(before, news)) {
5290
+ yield* runPve(news.target, "provision", true, storage2.putStorage(toDistilledUpdate2(news)));
5229
5291
  }
5230
- const after = dropUnreadable6(yield* readStorage(news));
5292
+ const after = dropUnreadable7(yield* readStorage(news));
5231
5293
  if (after === undefined) {
5232
- return yield* Effect65.die(new Error(`storage/${news.storage}: the write returned no error but the storage is still ` + 'absent. PVE wraps every answer in {"data":...} and can report success on a ' + "call that did nothing -- read back rather than trusting the status code."));
5294
+ return yield* Effect66.die(new Error(`storage/${news.storage}: the write returned no error but the storage is still ` + 'absent. PVE wraps every answer in {"data":...} and can report success on a ' + "call that did nothing -- read back rather than trusting the status code."));
5233
5295
  }
5234
5296
  return after;
5235
5297
  }),
5236
- delete: Effect65.fn(function* ({ olds }) {
5298
+ delete: Effect66.fn(function* ({ olds }) {
5237
5299
  yield* runPve(olds.target, "provision", true, storage2.deleteStorage({ storage: olds.storage }));
5238
5300
  })
5239
5301
  })));
5240
5302
  // src/proxmox/zfs-pool.ts
5241
5303
  import { Resource as Resource35 } from "alchemy";
5242
- import { isResolved as isResolved16 } from "alchemy/Diff";
5304
+ import { isResolved as isResolved17 } from "alchemy/Diff";
5243
5305
  import * as Provider35 from "alchemy/Provider";
5244
- import * as Effect68 from "effect/Effect";
5306
+ import * as Effect69 from "effect/Effect";
5245
5307
 
5246
5308
  // src/proxmox/zfs-pool-wire.ts
5247
- import * as nodes from "@distilled.cloud/proxmox/nodes";
5248
- import * as Effect66 from "effect/Effect";
5309
+ import * as nodes3 from "@distilled.cloud/proxmox/nodes";
5310
+ import * as Effect67 from "effect/Effect";
5249
5311
  var leafDevices = (children) => Array.isArray(children) ? children.flatMap((entry) => {
5250
5312
  const vdev = entry;
5251
5313
  const nested = leafDevices(vdev.children);
5252
5314
  return nested.length > 0 ? nested : [text(vdev.name)].filter((name) => name !== "");
5253
5315
  }) : [];
5254
- var attributesOf8 = (live, props) => ({
5316
+ var attributesOf9 = (live, props) => ({
5255
5317
  devices: leafDevices(live.children).join(","),
5256
5318
  errors: text(live.errors, "unknown"),
5257
5319
  name: props.name,
5258
5320
  node: props.node,
5259
5321
  state: text(live.state, "unknown")
5260
5322
  });
5261
- var readPoolOrFail = (props) => readOrUnreadable(runPve(props.target, "read", false, nodes.getNodeDiskZfs({ name: props.name, node: props.node }))).pipe(Effect66.map((live) => {
5323
+ var readPoolOrFail = (props) => readOrUnreadable(runPve(props.target, "read", false, nodes3.getNodeDiskZfs({ name: props.name, node: props.node }))).pipe(Effect67.map((live) => {
5262
5324
  if (live === UNREADABLE)
5263
5325
  return UNREADABLE;
5264
- return text(live.name) === "" ? undefined : attributesOf8(live, props);
5326
+ return text(live.name) === "" ? undefined : attributesOf9(live, props);
5265
5327
  }));
5266
- var readPool = (props) => readPoolOrFail(props).pipe(Effect66.orElseSucceed(() => {
5328
+ var readPool = (props) => readPoolOrFail(props).pipe(Effect67.orElseSucceed(() => {
5267
5329
  return;
5268
5330
  }));
5269
- var dropUnreadable7 = (live) => live === UNREADABLE ? undefined : live;
5331
+ var dropUnreadable8 = (live) => live === UNREADABLE ? undefined : live;
5270
5332
 
5271
5333
  // src/proxmox/zfs-pool-form.ts
5272
- import * as Effect67 from "effect/Effect";
5273
- import * as nodes2 from "@distilled.cloud/proxmox/nodes";
5334
+ import * as Effect68 from "effect/Effect";
5335
+ import * as nodes4 from "@distilled.cloud/proxmox/nodes";
5274
5336
  var ZFS_POOL_CREATE = "pve:POST /nodes/{node}/disks/zfs";
5275
5337
  var zfsPoolCreateEndpoint = (props) => props.devices === undefined || props.raidlevel === undefined ? undefined : ZFS_POOL_CREATE;
5276
- var createForm11 = (props) => ({
5338
+ var createForm12 = (props) => ({
5277
5339
  ...props.devices === undefined ? {} : { devices: props.devices.join(",") },
5278
5340
  name: props.name,
5279
5341
  ...props.raidlevel === undefined ? {} : { raidlevel: props.raidlevel },
@@ -5281,8 +5343,8 @@ var createForm11 = (props) => ({
5281
5343
  ...props.compression === undefined ? {} : { compression: props.compression },
5282
5344
  ...props["draid-config"] === undefined ? {} : { "draid-config": props["draid-config"] }
5283
5345
  });
5284
- var toDistilledCreate2 = (props) => {
5285
- const form = createForm11(props);
5346
+ var toDistilledCreate3 = (props) => {
5347
+ const form = createForm12(props);
5286
5348
  return {
5287
5349
  ...form,
5288
5350
  draid_config: form["draid-config"],
@@ -5290,43 +5352,43 @@ var toDistilledCreate2 = (props) => {
5290
5352
  };
5291
5353
  };
5292
5354
  var SETTLE_ATTEMPTS = 30;
5293
- var createPool = (props, read4) => Effect67.gen(function* () {
5355
+ var createPool = (props, read4) => Effect68.gen(function* () {
5294
5356
  const existing = yield* read4(props);
5295
5357
  if (existing !== undefined)
5296
5358
  return existing;
5297
5359
  if (props.devices === undefined || props.raidlevel === undefined) {
5298
- return yield* Effect67.die(new Error(`${props.node}/${props.name}: this is an adopt-only declaration (no \`devices\` or ` + "`raidlevel`) and the pool is not there to adopt. An adopt-only Proxmox.ZfsPool never " + "creates -- declare both fields for a pool this resource should build, or point this " + "declaration at a pool that already exists on this node."));
5360
+ return yield* Effect68.die(new Error(`${props.node}/${props.name}: this is an adopt-only declaration (no \`devices\` or ` + "`raidlevel`) and the pool is not there to adopt. An adopt-only Proxmox.ZfsPool never " + "creates -- declare both fields for a pool this resource should build, or point this " + "declaration at a pool that already exists on this node."));
5299
5361
  }
5300
- yield* guardForm(zfsPoolCreateEndpoint(props), asForm2(createForm11(props)), true);
5301
- const upid = yield* runPve(props.target, "provision", true, nodes2.createNodeDiskZfs(toDistilledCreate2(props)));
5302
- const settle4 = (attempts) => Effect67.gen(function* () {
5362
+ yield* guardForm(zfsPoolCreateEndpoint(props), asForm2(createForm12(props)), true);
5363
+ const upid = yield* runPve(props.target, "provision", true, nodes4.createNodeDiskZfs(toDistilledCreate3(props)));
5364
+ const settle4 = (attempts) => Effect68.gen(function* () {
5303
5365
  const live = yield* read4(props);
5304
5366
  if (live !== undefined || attempts <= 0)
5305
5367
  return live;
5306
- yield* Effect67.sleep("2 seconds");
5368
+ yield* Effect68.sleep("2 seconds");
5307
5369
  return yield* settle4(attempts - 1);
5308
5370
  });
5309
5371
  const after = yield* settle4(SETTLE_ATTEMPTS);
5310
5372
  if (after === undefined) {
5311
- return yield* Effect67.die(new Error(`nodes/${props.node}/disks/zfs/${props.name}: POST returned ${text(upid, "(no UPID)")} ` + "but the pool has not appeared. That POST only forks a `zfscreate` worker, so the task " + `holds the real error -- read it with \`pvesh get /nodes/${props.node}/tasks/<upid>/log\`. ` + "NOTHING WAS RETRIED AND NOTHING WAS CLEANED UP: if the worker reached `zpool create`, " + "the declared devices have already been written to. DO NOT RE-RUN THIS DEPLOY BEFORE " + 'READING THAT LOG: `read` cannot tell "the worker is still running" from "the pool is ' + 'genuinely gone", so a re-run this soon can POST a SECOND `zpool create` at the SAME ' + "devices while the first one is still mid-write -- confirm the task finished (one way " + "or the other) before trying again."));
5373
+ return yield* Effect68.die(new Error(`nodes/${props.node}/disks/zfs/${props.name}: POST returned ${text(upid, "(no UPID)")} ` + "but the pool has not appeared. That POST only forks a `zfscreate` worker, so the task " + `holds the real error -- read it with \`pvesh get /nodes/${props.node}/tasks/<upid>/log\`. ` + "NOTHING WAS RETRIED AND NOTHING WAS CLEANED UP: if the worker reached `zpool create`, " + "the declared devices have already been written to. DO NOT RE-RUN THIS DEPLOY BEFORE " + 'READING THAT LOG: `read` cannot tell "the worker is still running" from "the pool is ' + 'genuinely gone", so a re-run this soon can POST a SECOND `zpool create` at the SAME ' + "devices while the first one is still mid-write -- confirm the task finished (one way " + "or the other) before trying again."));
5312
5374
  }
5313
5375
  return after;
5314
5376
  });
5315
- var destroyPool = (props) => runPve(props.target, "provision", true, nodes2.deleteNodeDiskZfs({ name: props.name, node: props.node }));
5377
+ var destroyPool = (props) => runPve(props.target, "provision", true, nodes4.deleteNodeDiskZfs({ name: props.name, node: props.node }));
5316
5378
 
5317
5379
  // src/proxmox/zfs-pool.ts
5318
5380
  var ProxmoxZfsPool = Resource35("Proxmox.ZfsPool", {
5319
5381
  defaultRemovalPolicy: "retain"
5320
5382
  });
5321
- var ProxmoxZfsPoolProvider = () => Provider35.effect(ProxmoxZfsPool, Effect68.succeed(ProxmoxZfsPool.Provider.of({
5322
- list: () => Effect68.succeed([]),
5323
- read: Effect68.fn(function* ({ olds, output }) {
5324
- return dropUnreadable7(yield* output === undefined ? readPool(olds) : readPoolOrFail(olds));
5383
+ var ProxmoxZfsPoolProvider = () => Provider35.effect(ProxmoxZfsPool, Effect69.succeed(ProxmoxZfsPool.Provider.of({
5384
+ list: () => Effect69.succeed([]),
5385
+ read: Effect69.fn(function* ({ olds, output }) {
5386
+ return dropUnreadable8(yield* output === undefined ? readPool(olds) : readPoolOrFail(olds));
5325
5387
  }),
5326
- diff: Effect68.fn(function* ({ news, output }) {
5327
- if (!isResolved16(news))
5388
+ diff: Effect69.fn(function* ({ news, output }) {
5389
+ if (!isResolved17(news))
5328
5390
  return;
5329
- yield* guardForm(zfsPoolCreateEndpoint(news), asForm2(createForm11(news)), output === undefined);
5391
+ yield* guardForm(zfsPoolCreateEndpoint(news), asForm2(createForm12(news)), output === undefined);
5330
5392
  if (output === undefined)
5331
5393
  return;
5332
5394
  const live = yield* readPoolOrFail(news);
@@ -5335,15 +5397,15 @@ var ProxmoxZfsPoolProvider = () => Provider35.effect(ProxmoxZfsPool, Effect68.su
5335
5397
  return { action: "noop" };
5336
5398
  }
5337
5399
  if (live === undefined) {
5338
- yield* guardForm(zfsPoolCreateEndpoint(news), asForm2(createForm11(news)), true);
5400
+ yield* guardForm(zfsPoolCreateEndpoint(news), asForm2(createForm12(news)), true);
5339
5401
  return { action: "update" };
5340
5402
  }
5341
5403
  return { action: "noop" };
5342
5404
  }),
5343
- reconcile: Effect68.fn(function* ({ news }) {
5344
- return yield* createPool(news, (props) => readPool(props).pipe(Effect68.map(dropUnreadable7)));
5405
+ reconcile: Effect69.fn(function* ({ news }) {
5406
+ return yield* createPool(news, (props) => readPool(props).pipe(Effect69.map(dropUnreadable8)));
5345
5407
  }),
5346
- delete: Effect68.fn(function* ({ olds }) {
5408
+ delete: Effect69.fn(function* ({ olds }) {
5347
5409
  yield* destroyPool(olds);
5348
5410
  })
5349
5411
  })));
@@ -5423,5 +5485,5 @@ export {
5423
5485
  violations
5424
5486
  };
5425
5487
 
5426
- //# debugId=D100179D867AAA0364756E2164756E21
5488
+ //# debugId=AF866CF2F0A2718F64756E2164756E21
5427
5489
  //# sourceMappingURL=index.js.map