@layr-labs/ecloud-sdk 1.0.0-dev.6 → 1.0.0-dev.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.cjs CHANGED
@@ -171,8 +171,10 @@ __export(index_exports, {
171
171
  BuildError: () => BuildError,
172
172
  BuildFailedError: () => BuildFailedError,
173
173
  ConflictError: () => ConflictError,
174
+ EMPTY_CONTAINER_POLICY: () => EMPTY_CONTAINER_POLICY,
174
175
  ERC20ABI: () => ERC20_default,
175
176
  ForbiddenError: () => ForbiddenError,
177
+ InsufficientGasError: () => InsufficientGasError,
176
178
  JwtProvider: () => JwtProvider,
177
179
  NoopClient: () => NoopClient,
178
180
  NotFoundError: () => NotFoundError,
@@ -182,9 +184,12 @@ __export(index_exports, {
182
184
  TimeoutError: () => TimeoutError,
183
185
  USDCCreditsABI: () => USDCCredits_default,
184
186
  UserApiClient: () => UserApiClient,
187
+ WATCH_DEFAULT_TIMEOUT_SECONDS: () => WATCH_DEFAULT_TIMEOUT_SECONDS,
188
+ WatchTimeoutError: () => WatchTimeoutError,
185
189
  addHexPrefix: () => addHexPrefix,
186
190
  addMetric: () => addMetric,
187
191
  addMetricWithDimensions: () => addMetricWithDimensions,
192
+ assertSufficientGas: () => assertSufficientGas,
188
193
  assertValidFilePath: () => assertValidFilePath,
189
194
  assertValidImageReference: () => assertValidImageReference,
190
195
  assertValidPrivateKey: () => assertValidPrivateKey,
@@ -286,7 +291,7 @@ __export(index_exports, {
286
291
  module.exports = __toCommonJS(index_exports);
287
292
 
288
293
  // src/client/modules/compute/app/index.ts
289
- var import_viem6 = require("viem");
294
+ var import_viem7 = require("viem");
290
295
 
291
296
  // src/client/common/docker/build.ts
292
297
  var child_process = __toESM(require("child_process"), 1);
@@ -575,7 +580,74 @@ var PushPermissionError = class extends Error {
575
580
  var import_handlebars = __toESM(require("handlebars"), 1);
576
581
 
577
582
  // src/client/common/templates/Dockerfile.layered.tmpl
578
- var Dockerfile_layered_default = '{{#if includeTLS}}\n# Get Caddy from official image\nFROM caddy:2.10.2-alpine AS caddy\n{{/if}}\n\nFROM {{baseImage}}\n\n{{#if originalUser}}\n# Switch to root to perform setup (base image has non-root USER: {{originalUser}})\nUSER root\n{{/if}}\n\n# Copy core TEE components\nCOPY compute-source-env.sh /usr/local/bin/\nCOPY kms-client /usr/local/bin/\nCOPY kms-signing-public-key.pem /usr/local/bin/\n\n{{#if includeTLS}}\n# Copy Caddy from official image\nCOPY --from=caddy /usr/bin/caddy /usr/local/bin/caddy\n\n# Copy TLS components\nCOPY tls-keygen /usr/local/bin/\nCOPY Caddyfile /etc/caddy/\n{{/if}}\n\n{{#if originalUser}}\n# Make binaries executable (755 for executables, 644 for keys)\nRUN chmod 755 /usr/local/bin/compute-source-env.sh \\\n && chmod 755 /usr/local/bin/kms-client{{#if includeTLS}} \\\n && chmod 755 /usr/local/bin/tls-keygen \\\n && chmod 755 /usr/local/bin/caddy{{/if}} \\\n && chmod 644 /usr/local/bin/kms-signing-public-key.pem\n\n# Store original user - entrypoint will drop privileges to this user after TEE setup\nENV __ECLOUD_ORIGINAL_USER={{originalUser}}\n{{else}}\n# Make binaries executable (preserve existing permissions, just add execute)\nRUN chmod +x /usr/local/bin/compute-source-env.sh \\\n && chmod +x /usr/local/bin/kms-client{{#if includeTLS}} \\\n && chmod +x /usr/local/bin/tls-keygen{{/if}}\n{{/if}}\n\n{{#if logRedirect}}\n\nLABEL tee.launch_policy.log_redirect={{logRedirect}}\n{{/if}}\n{{#if resourceUsageAllow}}\n\nLABEL tee.launch_policy.monitoring_memory_allow={{resourceUsageAllow}}\n{{/if}}\n\nLABEL eigenx_cli_version={{ecloudCLIVersion}}\nLABEL eigenx_vm_image=eigen\n\n{{#if includeTLS}}\n# Expose both HTTP and HTTPS ports for Caddy\nEXPOSE 80 443\n{{/if}}\n\nENTRYPOINT ["/usr/local/bin/compute-source-env.sh"]\nCMD {{{originalCmd}}}\n';
583
+ var Dockerfile_layered_default = `{{#if includeTLS}}
584
+ # Get Caddy from official image
585
+ FROM caddy:2.10.2-alpine AS caddy
586
+ {{/if}}
587
+
588
+ FROM {{baseImage}}
589
+
590
+ {{#if originalUser}}
591
+ # Switch to root to perform setup (base image has non-root USER: {{originalUser}})
592
+ USER root
593
+ {{/if}}
594
+
595
+ # Copy core TEE components
596
+ # CA bundle for kms-client / tls-keygen to validate HTTPS calls to
597
+ # eigencloud.xyz endpoints. Bundled at a non-standard path and consumed
598
+ # only via SSL_CERT_FILE in compute-source-env.sh, so the user's
599
+ # /etc/ssl/ is never touched.
600
+ COPY --from=alpine:3.20.10 /etc/ssl/certs/ca-certificates.crt /usr/local/share/eigenx-ca-certs.crt
601
+ COPY compute-source-env.sh /usr/local/bin/
602
+ COPY kms-client /usr/local/bin/
603
+ COPY kms-signing-public-key.pem /usr/local/bin/
604
+
605
+ {{#if includeTLS}}
606
+ # Copy Caddy from official image
607
+ COPY --from=caddy /usr/bin/caddy /usr/local/bin/caddy
608
+
609
+ # Copy TLS components
610
+ COPY tls-keygen /usr/local/bin/
611
+ COPY Caddyfile /etc/caddy/
612
+ {{/if}}
613
+
614
+ {{#if originalUser}}
615
+ # Make binaries executable (755 for executables, 644 for keys)
616
+ RUN chmod 755 /usr/local/bin/compute-source-env.sh \\
617
+ && chmod 755 /usr/local/bin/kms-client{{#if includeTLS}} \\
618
+ && chmod 755 /usr/local/bin/tls-keygen \\
619
+ && chmod 755 /usr/local/bin/caddy{{/if}} \\
620
+ && chmod 644 /usr/local/bin/kms-signing-public-key.pem
621
+
622
+ # Store original user - entrypoint will drop privileges to this user after TEE setup
623
+ ENV __ECLOUD_ORIGINAL_USER={{originalUser}}
624
+ {{else}}
625
+ # Make binaries executable (preserve existing permissions, just add execute)
626
+ RUN chmod +x /usr/local/bin/compute-source-env.sh \\
627
+ && chmod +x /usr/local/bin/kms-client{{#if includeTLS}} \\
628
+ && chmod +x /usr/local/bin/tls-keygen{{/if}}
629
+ {{/if}}
630
+
631
+ {{#if logRedirect}}
632
+
633
+ LABEL tee.launch_policy.log_redirect={{logRedirect}}
634
+ {{/if}}
635
+ {{#if resourceUsageAllow}}
636
+
637
+ LABEL tee.launch_policy.monitoring_memory_allow={{resourceUsageAllow}}
638
+ {{/if}}
639
+
640
+ LABEL eigenx_cli_version={{ecloudCLIVersion}}
641
+ LABEL eigenx_vm_image=eigen
642
+
643
+ {{#if includeTLS}}
644
+ # Expose both HTTP and HTTPS ports for Caddy
645
+ EXPOSE 80 443
646
+ {{/if}}
647
+
648
+ ENTRYPOINT ["/usr/local/bin/compute-source-env.sh"]
649
+ CMD {{{originalCmd}}}
650
+ `;
579
651
 
580
652
  // src/client/common/templates/dockerfileTemplate.ts
581
653
  function processDockerfileTemplate(data) {
@@ -592,7 +664,7 @@ echo "compute-source-env.sh: Running setup script..."
592
664
 
593
665
  # Fetch and source environment variables from KMS
594
666
  echo "Fetching secrets from KMS..."
595
- if /usr/local/bin/kms-client \\
667
+ if SSL_CERT_FILE=/usr/local/share/eigenx-ca-certs.crt /usr/local/bin/kms-client \\
596
668
  --kms-server-url "{{kmsServerURL}}" \\
597
669
  --kms-signing-key-file /usr/local/bin/kms-signing-public-key.pem \\
598
670
  --userapi-url "{{userAPIURL}}" \\
@@ -650,7 +722,8 @@ setup_tls() {
650
722
 
651
723
  echo "compute-source-env.sh: Obtaining TLS certificate using $challenge challenge..."
652
724
  # Pass the API URL for certificate persistence
653
- if ! MNEMONIC="$mnemonic" DOMAIN="$domain" API_URL="{{userAPIURL}}" /usr/local/bin/tls-keygen \\
725
+ if ! SSL_CERT_FILE=/usr/local/share/eigenx-ca-certs.crt \\
726
+ MNEMONIC="$mnemonic" DOMAIN="$domain" API_URL="{{userAPIURL}}" /usr/local/bin/tls-keygen \\
654
727
  -challenge "$challenge" \\
655
728
  $staging_flag; then
656
729
  echo "compute-source-env.sh: ERROR - Failed to obtain TLS certificate"
@@ -1043,16 +1116,7 @@ async function extractDigestFromSinglePlatform(manifest, imageRef) {
1043
1116
  architecture: inspectData[0].Architecture
1044
1117
  } : null;
1045
1118
  if (!config) {
1046
- if (manifest.config?.digest) {
1047
- const digest = hexStringToBytes32(manifest.config.digest);
1048
- const registry = extractRegistryName(imageRef);
1049
- return {
1050
- digest,
1051
- registry,
1052
- platform: DOCKER_PLATFORM
1053
- };
1054
- }
1055
- throw new Error(`Could not determine platform for ${imageRef}`);
1119
+ throw createPlatformErrorMessage(imageRef, ["unknown (could not determine architecture)"]);
1056
1120
  }
1057
1121
  const platform2 = `${config.os}/${config.architecture}`;
1058
1122
  if (platform2 === DOCKER_PLATFORM) {
@@ -1124,14 +1188,11 @@ Image: ${imageRef}
1124
1188
  Found platform(s): ${platforms.join(", ")}
1125
1189
  Required platform: ${DOCKER_PLATFORM}
1126
1190
 
1127
- To fix this issue:
1128
- 1. Manual fix:
1129
- a. Rebuild your image with the correct platform:
1130
- docker build --platform ${DOCKER_PLATFORM} -t ${imageRef} .
1131
- b. Push the rebuilt image to your remote registry:
1132
- docker push ${imageRef}
1133
-
1134
- 2. Or use the SDK to build with the correct platform automatically.`;
1191
+ To fix, either:
1192
+ 1. Rebuild the image for ${DOCKER_PLATFORM} and push it:
1193
+ docker buildx build --platform ${DOCKER_PLATFORM} -t ${imageRef} --push .
1194
+ 2. Or use a verifiable build (--verifiable --repo <repo> --commit <sha>), which
1195
+ builds server-side and needs no local Docker.`;
1135
1196
  return new Error(errorMsg);
1136
1197
  }
1137
1198
 
@@ -1236,6 +1297,8 @@ async function prepareRelease(options, logger) {
1236
1297
  logger.info(`Waiting ${REGISTRY_PROPAGATION_WAIT_SECONDS} seconds for registry propagation...`);
1237
1298
  await new Promise((resolve2) => setTimeout(resolve2, REGISTRY_PROPAGATION_WAIT_SECONDS * 1e3));
1238
1299
  } else {
1300
+ logger.info("Verifying image platform (linux/amd64)...");
1301
+ await getImageDigestAndName(imageRef);
1239
1302
  logger.info("Checking if image needs layering...");
1240
1303
  finalImageRef = await layerRemoteImageIfNeeded(
1241
1304
  {
@@ -1394,6 +1457,13 @@ function extractRegistryNameNoDocker(imageRef) {
1394
1457
  var import_viem = require("viem");
1395
1458
 
1396
1459
  // src/client/common/types/index.ts
1460
+ var EMPTY_CONTAINER_POLICY = {
1461
+ args: [],
1462
+ cmdOverride: [],
1463
+ env: [],
1464
+ envOverride: [],
1465
+ restartPolicy: ""
1466
+ };
1397
1467
  var noopLogger = {
1398
1468
  debug: () => {
1399
1469
  },
@@ -2634,49 +2704,1594 @@ async function executeBatch(options, logger = noopLogger) {
2634
2704
  } else {
2635
2705
  revertReason = callError.message || "Unknown reason";
2636
2706
  }
2637
- }
2638
- throw new Error(`Transaction reverted: ${hash}. Reason: ${revertReason}`);
2707
+ }
2708
+ throw new Error(`Transaction reverted: ${hash}. Reason: ${revertReason}`);
2709
+ }
2710
+ return hash;
2711
+ }
2712
+
2713
+ // src/client/common/contract/caller.ts
2714
+ var import_viem3 = require("viem");
2715
+
2716
+ // src/client/common/utils/helpers.ts
2717
+ var import_viem2 = require("viem");
2718
+ var import_chains2 = require("viem/chains");
2719
+ var import_accounts = require("viem/accounts");
2720
+ function getChainFromID(chainID, fallback2 = import_chains2.sepolia) {
2721
+ const id = Number(chainID);
2722
+ return (0, import_viem2.extractChain)({ chains: SUPPORTED_CHAINS, id }) || fallback2;
2723
+ }
2724
+ function createClients(options) {
2725
+ const { privateKey, rpcUrl, chainId } = options;
2726
+ const privateKeyHex = addHexPrefix(privateKey);
2727
+ const account = (0, import_accounts.privateKeyToAccount)(privateKeyHex);
2728
+ const chain = getChainFromID(chainId);
2729
+ const transport = typeof rpcUrl === "string" ? (0, import_viem2.http)(rpcUrl) : (0, import_viem2.fallback)(rpcUrl.map((url) => (0, import_viem2.http)(url)));
2730
+ const publicClient = (0, import_viem2.createPublicClient)({
2731
+ chain,
2732
+ transport
2733
+ });
2734
+ const walletClient = (0, import_viem2.createWalletClient)({
2735
+ account,
2736
+ chain,
2737
+ transport
2738
+ });
2739
+ return { walletClient, publicClient };
2740
+ }
2741
+ function addHexPrefix(value) {
2742
+ return value.startsWith("0x") ? value : `0x${value}`;
2743
+ }
2744
+ function stripHexPrefix(value) {
2745
+ return value.startsWith("0x") ? value.slice(2) : value;
2746
+ }
2747
+
2748
+ // src/client/common/abis/AppController.json
2749
+ var AppController_default = [
2750
+ {
2751
+ type: "constructor",
2752
+ inputs: [
2753
+ {
2754
+ name: "_version",
2755
+ type: "string",
2756
+ internalType: "string"
2757
+ },
2758
+ {
2759
+ name: "_permissionController",
2760
+ type: "address",
2761
+ internalType: "contractIPermissionController"
2762
+ },
2763
+ {
2764
+ name: "_releaseManager",
2765
+ type: "address",
2766
+ internalType: "contractIReleaseManager"
2767
+ },
2768
+ {
2769
+ name: "_computeAVSRegistrar",
2770
+ type: "address",
2771
+ internalType: "contractIComputeAVSRegistrar"
2772
+ },
2773
+ {
2774
+ name: "_computeOperator",
2775
+ type: "address",
2776
+ internalType: "contractIComputeOperator"
2777
+ },
2778
+ {
2779
+ name: "_appBeacon",
2780
+ type: "address",
2781
+ internalType: "contractIBeacon"
2782
+ }
2783
+ ],
2784
+ stateMutability: "nonpayable"
2785
+ },
2786
+ {
2787
+ type: "function",
2788
+ name: "API_PERMISSION_TYPEHASH",
2789
+ inputs: [],
2790
+ outputs: [
2791
+ {
2792
+ name: "",
2793
+ type: "bytes32",
2794
+ internalType: "bytes32"
2795
+ }
2796
+ ],
2797
+ stateMutability: "view"
2798
+ },
2799
+ {
2800
+ type: "function",
2801
+ name: "appBeacon",
2802
+ inputs: [],
2803
+ outputs: [
2804
+ {
2805
+ name: "",
2806
+ type: "address",
2807
+ internalType: "contractIBeacon"
2808
+ }
2809
+ ],
2810
+ stateMutability: "view"
2811
+ },
2812
+ {
2813
+ type: "function",
2814
+ name: "calculateApiPermissionDigestHash",
2815
+ inputs: [
2816
+ {
2817
+ name: "permission",
2818
+ type: "bytes4",
2819
+ internalType: "bytes4"
2820
+ },
2821
+ {
2822
+ name: "expiry",
2823
+ type: "uint256",
2824
+ internalType: "uint256"
2825
+ }
2826
+ ],
2827
+ outputs: [
2828
+ {
2829
+ name: "",
2830
+ type: "bytes32",
2831
+ internalType: "bytes32"
2832
+ }
2833
+ ],
2834
+ stateMutability: "view"
2835
+ },
2836
+ {
2837
+ type: "function",
2838
+ name: "calculateAppId",
2839
+ inputs: [
2840
+ {
2841
+ name: "deployer",
2842
+ type: "address",
2843
+ internalType: "address"
2844
+ },
2845
+ {
2846
+ name: "salt",
2847
+ type: "bytes32",
2848
+ internalType: "bytes32"
2849
+ }
2850
+ ],
2851
+ outputs: [
2852
+ {
2853
+ name: "",
2854
+ type: "address",
2855
+ internalType: "contractIApp"
2856
+ }
2857
+ ],
2858
+ stateMutability: "view"
2859
+ },
2860
+ {
2861
+ type: "function",
2862
+ name: "computeAVSRegistrar",
2863
+ inputs: [],
2864
+ outputs: [
2865
+ {
2866
+ name: "",
2867
+ type: "address",
2868
+ internalType: "contractIComputeAVSRegistrar"
2869
+ }
2870
+ ],
2871
+ stateMutability: "view"
2872
+ },
2873
+ {
2874
+ type: "function",
2875
+ name: "computeOperator",
2876
+ inputs: [],
2877
+ outputs: [
2878
+ {
2879
+ name: "",
2880
+ type: "address",
2881
+ internalType: "contractIComputeOperator"
2882
+ }
2883
+ ],
2884
+ stateMutability: "view"
2885
+ },
2886
+ {
2887
+ type: "function",
2888
+ name: "confirmUpgrade",
2889
+ inputs: [
2890
+ {
2891
+ name: "app",
2892
+ type: "address",
2893
+ internalType: "contractIApp"
2894
+ }
2895
+ ],
2896
+ outputs: [],
2897
+ stateMutability: "nonpayable"
2898
+ },
2899
+ {
2900
+ type: "function",
2901
+ name: "createApp",
2902
+ inputs: [
2903
+ {
2904
+ name: "salt",
2905
+ type: "bytes32",
2906
+ internalType: "bytes32"
2907
+ },
2908
+ {
2909
+ name: "release",
2910
+ type: "tuple",
2911
+ internalType: "structIAppController.Release",
2912
+ components: [
2913
+ {
2914
+ name: "rmsRelease",
2915
+ type: "tuple",
2916
+ internalType: "structIReleaseManagerTypes.Release",
2917
+ components: [
2918
+ {
2919
+ name: "artifacts",
2920
+ type: "tuple[]",
2921
+ internalType: "structIReleaseManagerTypes.Artifact[]",
2922
+ components: [
2923
+ {
2924
+ name: "digest",
2925
+ type: "bytes32",
2926
+ internalType: "bytes32"
2927
+ },
2928
+ {
2929
+ name: "registry",
2930
+ type: "string",
2931
+ internalType: "string"
2932
+ }
2933
+ ]
2934
+ },
2935
+ {
2936
+ name: "upgradeByTime",
2937
+ type: "uint32",
2938
+ internalType: "uint32"
2939
+ }
2940
+ ]
2941
+ },
2942
+ {
2943
+ name: "publicEnv",
2944
+ type: "bytes",
2945
+ internalType: "bytes"
2946
+ },
2947
+ {
2948
+ name: "encryptedEnv",
2949
+ type: "bytes",
2950
+ internalType: "bytes"
2951
+ },
2952
+ {
2953
+ name: "containerPolicy",
2954
+ type: "tuple",
2955
+ internalType: "structIAppController.ContainerPolicy",
2956
+ components: [
2957
+ {
2958
+ name: "args",
2959
+ type: "string[]",
2960
+ internalType: "string[]"
2961
+ },
2962
+ {
2963
+ name: "cmdOverride",
2964
+ type: "string[]",
2965
+ internalType: "string[]"
2966
+ },
2967
+ {
2968
+ name: "env",
2969
+ type: "tuple[]",
2970
+ internalType: "structIAppController.EnvVar[]",
2971
+ components: [
2972
+ {
2973
+ name: "key",
2974
+ type: "string",
2975
+ internalType: "string"
2976
+ },
2977
+ {
2978
+ name: "value",
2979
+ type: "string",
2980
+ internalType: "string"
2981
+ }
2982
+ ]
2983
+ },
2984
+ {
2985
+ name: "envOverride",
2986
+ type: "tuple[]",
2987
+ internalType: "structIAppController.EnvVar[]",
2988
+ components: [
2989
+ {
2990
+ name: "key",
2991
+ type: "string",
2992
+ internalType: "string"
2993
+ },
2994
+ {
2995
+ name: "value",
2996
+ type: "string",
2997
+ internalType: "string"
2998
+ }
2999
+ ]
3000
+ },
3001
+ {
3002
+ name: "restartPolicy",
3003
+ type: "string",
3004
+ internalType: "string"
3005
+ }
3006
+ ]
3007
+ }
3008
+ ]
3009
+ }
3010
+ ],
3011
+ outputs: [
3012
+ {
3013
+ name: "app",
3014
+ type: "address",
3015
+ internalType: "contractIApp"
3016
+ }
3017
+ ],
3018
+ stateMutability: "nonpayable"
3019
+ },
3020
+ {
3021
+ type: "function",
3022
+ name: "createAppWithIsolatedBilling",
3023
+ inputs: [
3024
+ {
3025
+ name: "salt",
3026
+ type: "bytes32",
3027
+ internalType: "bytes32"
3028
+ },
3029
+ {
3030
+ name: "release",
3031
+ type: "tuple",
3032
+ internalType: "structIAppController.Release",
3033
+ components: [
3034
+ {
3035
+ name: "rmsRelease",
3036
+ type: "tuple",
3037
+ internalType: "structIReleaseManagerTypes.Release",
3038
+ components: [
3039
+ {
3040
+ name: "artifacts",
3041
+ type: "tuple[]",
3042
+ internalType: "structIReleaseManagerTypes.Artifact[]",
3043
+ components: [
3044
+ {
3045
+ name: "digest",
3046
+ type: "bytes32",
3047
+ internalType: "bytes32"
3048
+ },
3049
+ {
3050
+ name: "registry",
3051
+ type: "string",
3052
+ internalType: "string"
3053
+ }
3054
+ ]
3055
+ },
3056
+ {
3057
+ name: "upgradeByTime",
3058
+ type: "uint32",
3059
+ internalType: "uint32"
3060
+ }
3061
+ ]
3062
+ },
3063
+ {
3064
+ name: "publicEnv",
3065
+ type: "bytes",
3066
+ internalType: "bytes"
3067
+ },
3068
+ {
3069
+ name: "encryptedEnv",
3070
+ type: "bytes",
3071
+ internalType: "bytes"
3072
+ },
3073
+ {
3074
+ name: "containerPolicy",
3075
+ type: "tuple",
3076
+ internalType: "structIAppController.ContainerPolicy",
3077
+ components: [
3078
+ {
3079
+ name: "args",
3080
+ type: "string[]",
3081
+ internalType: "string[]"
3082
+ },
3083
+ {
3084
+ name: "cmdOverride",
3085
+ type: "string[]",
3086
+ internalType: "string[]"
3087
+ },
3088
+ {
3089
+ name: "env",
3090
+ type: "tuple[]",
3091
+ internalType: "structIAppController.EnvVar[]",
3092
+ components: [
3093
+ {
3094
+ name: "key",
3095
+ type: "string",
3096
+ internalType: "string"
3097
+ },
3098
+ {
3099
+ name: "value",
3100
+ type: "string",
3101
+ internalType: "string"
3102
+ }
3103
+ ]
3104
+ },
3105
+ {
3106
+ name: "envOverride",
3107
+ type: "tuple[]",
3108
+ internalType: "structIAppController.EnvVar[]",
3109
+ components: [
3110
+ {
3111
+ name: "key",
3112
+ type: "string",
3113
+ internalType: "string"
3114
+ },
3115
+ {
3116
+ name: "value",
3117
+ type: "string",
3118
+ internalType: "string"
3119
+ }
3120
+ ]
3121
+ },
3122
+ {
3123
+ name: "restartPolicy",
3124
+ type: "string",
3125
+ internalType: "string"
3126
+ }
3127
+ ]
3128
+ }
3129
+ ]
3130
+ }
3131
+ ],
3132
+ outputs: [
3133
+ {
3134
+ name: "app",
3135
+ type: "address",
3136
+ internalType: "contractIApp"
3137
+ }
3138
+ ],
3139
+ stateMutability: "nonpayable"
3140
+ },
3141
+ {
3142
+ type: "function",
3143
+ name: "createEmptyApp",
3144
+ inputs: [
3145
+ {
3146
+ name: "salt",
3147
+ type: "bytes32",
3148
+ internalType: "bytes32"
3149
+ }
3150
+ ],
3151
+ outputs: [
3152
+ {
3153
+ name: "app",
3154
+ type: "address",
3155
+ internalType: "contractIApp"
3156
+ }
3157
+ ],
3158
+ stateMutability: "nonpayable"
3159
+ },
3160
+ {
3161
+ type: "function",
3162
+ name: "createEmptyAppWithIsolatedBilling",
3163
+ inputs: [
3164
+ {
3165
+ name: "salt",
3166
+ type: "bytes32",
3167
+ internalType: "bytes32"
3168
+ }
3169
+ ],
3170
+ outputs: [
3171
+ {
3172
+ name: "app",
3173
+ type: "address",
3174
+ internalType: "contractIApp"
3175
+ }
3176
+ ],
3177
+ stateMutability: "nonpayable"
3178
+ },
3179
+ {
3180
+ type: "function",
3181
+ name: "domainSeparator",
3182
+ inputs: [],
3183
+ outputs: [
3184
+ {
3185
+ name: "",
3186
+ type: "bytes32",
3187
+ internalType: "bytes32"
3188
+ }
3189
+ ],
3190
+ stateMutability: "view"
3191
+ },
3192
+ {
3193
+ type: "function",
3194
+ name: "getActiveAppCount",
3195
+ inputs: [
3196
+ {
3197
+ name: "user",
3198
+ type: "address",
3199
+ internalType: "address"
3200
+ }
3201
+ ],
3202
+ outputs: [
3203
+ {
3204
+ name: "",
3205
+ type: "uint32",
3206
+ internalType: "uint32"
3207
+ }
3208
+ ],
3209
+ stateMutability: "view"
3210
+ },
3211
+ {
3212
+ type: "function",
3213
+ name: "getAppCreator",
3214
+ inputs: [
3215
+ {
3216
+ name: "app",
3217
+ type: "address",
3218
+ internalType: "contractIApp"
3219
+ }
3220
+ ],
3221
+ outputs: [
3222
+ {
3223
+ name: "",
3224
+ type: "address",
3225
+ internalType: "address"
3226
+ }
3227
+ ],
3228
+ stateMutability: "view"
3229
+ },
3230
+ {
3231
+ type: "function",
3232
+ name: "getAppLatestReleaseBlockNumber",
3233
+ inputs: [
3234
+ {
3235
+ name: "app",
3236
+ type: "address",
3237
+ internalType: "contractIApp"
3238
+ }
3239
+ ],
3240
+ outputs: [
3241
+ {
3242
+ name: "",
3243
+ type: "uint32",
3244
+ internalType: "uint32"
3245
+ }
3246
+ ],
3247
+ stateMutability: "view"
3248
+ },
3249
+ {
3250
+ type: "function",
3251
+ name: "getAppOperatorSetId",
3252
+ inputs: [
3253
+ {
3254
+ name: "app",
3255
+ type: "address",
3256
+ internalType: "contractIApp"
3257
+ }
3258
+ ],
3259
+ outputs: [
3260
+ {
3261
+ name: "",
3262
+ type: "uint32",
3263
+ internalType: "uint32"
3264
+ }
3265
+ ],
3266
+ stateMutability: "view"
3267
+ },
3268
+ {
3269
+ type: "function",
3270
+ name: "getAppPendingReleaseBlockNumber",
3271
+ inputs: [
3272
+ {
3273
+ name: "app",
3274
+ type: "address",
3275
+ internalType: "contractIApp"
3276
+ }
3277
+ ],
3278
+ outputs: [
3279
+ {
3280
+ name: "",
3281
+ type: "uint32",
3282
+ internalType: "uint32"
3283
+ }
3284
+ ],
3285
+ stateMutability: "view"
3286
+ },
3287
+ {
3288
+ type: "function",
3289
+ name: "getAppStatus",
3290
+ inputs: [
3291
+ {
3292
+ name: "app",
3293
+ type: "address",
3294
+ internalType: "contractIApp"
3295
+ }
3296
+ ],
3297
+ outputs: [
3298
+ {
3299
+ name: "",
3300
+ type: "uint8",
3301
+ internalType: "enumIAppController.AppStatus"
3302
+ }
3303
+ ],
3304
+ stateMutability: "view"
3305
+ },
3306
+ {
3307
+ type: "function",
3308
+ name: "getApps",
3309
+ inputs: [
3310
+ {
3311
+ name: "offset",
3312
+ type: "uint256",
3313
+ internalType: "uint256"
3314
+ },
3315
+ {
3316
+ name: "limit",
3317
+ type: "uint256",
3318
+ internalType: "uint256"
3319
+ }
3320
+ ],
3321
+ outputs: [
3322
+ {
3323
+ name: "apps",
3324
+ type: "address[]",
3325
+ internalType: "contractIApp[]"
3326
+ },
3327
+ {
3328
+ name: "appConfigsMem",
3329
+ type: "tuple[]",
3330
+ internalType: "structIAppController.AppConfig[]",
3331
+ components: [
3332
+ {
3333
+ name: "creator",
3334
+ type: "address",
3335
+ internalType: "address"
3336
+ },
3337
+ {
3338
+ name: "operatorSetId",
3339
+ type: "uint32",
3340
+ internalType: "uint32"
3341
+ },
3342
+ {
3343
+ name: "latestReleaseBlockNumber",
3344
+ type: "uint32",
3345
+ internalType: "uint32"
3346
+ },
3347
+ {
3348
+ name: "pendingReleaseBlockNumber",
3349
+ type: "uint32",
3350
+ internalType: "uint32"
3351
+ },
3352
+ {
3353
+ name: "status",
3354
+ type: "uint8",
3355
+ internalType: "enumIAppController.AppStatus"
3356
+ }
3357
+ ]
3358
+ }
3359
+ ],
3360
+ stateMutability: "view"
3361
+ },
3362
+ {
3363
+ type: "function",
3364
+ name: "getAppsByBillingAccount",
3365
+ inputs: [
3366
+ {
3367
+ name: "account",
3368
+ type: "address",
3369
+ internalType: "address"
3370
+ },
3371
+ {
3372
+ name: "offset",
3373
+ type: "uint256",
3374
+ internalType: "uint256"
3375
+ },
3376
+ {
3377
+ name: "limit",
3378
+ type: "uint256",
3379
+ internalType: "uint256"
3380
+ }
3381
+ ],
3382
+ outputs: [
3383
+ {
3384
+ name: "apps",
3385
+ type: "address[]",
3386
+ internalType: "contractIApp[]"
3387
+ },
3388
+ {
3389
+ name: "appConfigsMem",
3390
+ type: "tuple[]",
3391
+ internalType: "structIAppController.AppConfig[]",
3392
+ components: [
3393
+ {
3394
+ name: "creator",
3395
+ type: "address",
3396
+ internalType: "address"
3397
+ },
3398
+ {
3399
+ name: "operatorSetId",
3400
+ type: "uint32",
3401
+ internalType: "uint32"
3402
+ },
3403
+ {
3404
+ name: "latestReleaseBlockNumber",
3405
+ type: "uint32",
3406
+ internalType: "uint32"
3407
+ },
3408
+ {
3409
+ name: "pendingReleaseBlockNumber",
3410
+ type: "uint32",
3411
+ internalType: "uint32"
3412
+ },
3413
+ {
3414
+ name: "status",
3415
+ type: "uint8",
3416
+ internalType: "enumIAppController.AppStatus"
3417
+ }
3418
+ ]
3419
+ }
3420
+ ],
3421
+ stateMutability: "view"
3422
+ },
3423
+ {
3424
+ type: "function",
3425
+ name: "getAppsByCreator",
3426
+ inputs: [
3427
+ {
3428
+ name: "creator",
3429
+ type: "address",
3430
+ internalType: "address"
3431
+ },
3432
+ {
3433
+ name: "offset",
3434
+ type: "uint256",
3435
+ internalType: "uint256"
3436
+ },
3437
+ {
3438
+ name: "limit",
3439
+ type: "uint256",
3440
+ internalType: "uint256"
3441
+ }
3442
+ ],
3443
+ outputs: [
3444
+ {
3445
+ name: "apps",
3446
+ type: "address[]",
3447
+ internalType: "contractIApp[]"
3448
+ },
3449
+ {
3450
+ name: "appConfigsMem",
3451
+ type: "tuple[]",
3452
+ internalType: "structIAppController.AppConfig[]",
3453
+ components: [
3454
+ {
3455
+ name: "creator",
3456
+ type: "address",
3457
+ internalType: "address"
3458
+ },
3459
+ {
3460
+ name: "operatorSetId",
3461
+ type: "uint32",
3462
+ internalType: "uint32"
3463
+ },
3464
+ {
3465
+ name: "latestReleaseBlockNumber",
3466
+ type: "uint32",
3467
+ internalType: "uint32"
3468
+ },
3469
+ {
3470
+ name: "pendingReleaseBlockNumber",
3471
+ type: "uint32",
3472
+ internalType: "uint32"
3473
+ },
3474
+ {
3475
+ name: "status",
3476
+ type: "uint8",
3477
+ internalType: "enumIAppController.AppStatus"
3478
+ }
3479
+ ]
3480
+ }
3481
+ ],
3482
+ stateMutability: "view"
3483
+ },
3484
+ {
3485
+ type: "function",
3486
+ name: "getAppsByDeveloper",
3487
+ inputs: [
3488
+ {
3489
+ name: "developer",
3490
+ type: "address",
3491
+ internalType: "address"
3492
+ },
3493
+ {
3494
+ name: "offset",
3495
+ type: "uint256",
3496
+ internalType: "uint256"
3497
+ },
3498
+ {
3499
+ name: "limit",
3500
+ type: "uint256",
3501
+ internalType: "uint256"
3502
+ }
3503
+ ],
3504
+ outputs: [
3505
+ {
3506
+ name: "apps",
3507
+ type: "address[]",
3508
+ internalType: "contractIApp[]"
3509
+ },
3510
+ {
3511
+ name: "appConfigsMem",
3512
+ type: "tuple[]",
3513
+ internalType: "structIAppController.AppConfig[]",
3514
+ components: [
3515
+ {
3516
+ name: "creator",
3517
+ type: "address",
3518
+ internalType: "address"
3519
+ },
3520
+ {
3521
+ name: "operatorSetId",
3522
+ type: "uint32",
3523
+ internalType: "uint32"
3524
+ },
3525
+ {
3526
+ name: "latestReleaseBlockNumber",
3527
+ type: "uint32",
3528
+ internalType: "uint32"
3529
+ },
3530
+ {
3531
+ name: "pendingReleaseBlockNumber",
3532
+ type: "uint32",
3533
+ internalType: "uint32"
3534
+ },
3535
+ {
3536
+ name: "status",
3537
+ type: "uint8",
3538
+ internalType: "enumIAppController.AppStatus"
3539
+ }
3540
+ ]
3541
+ }
3542
+ ],
3543
+ stateMutability: "view"
3544
+ },
3545
+ {
3546
+ type: "function",
3547
+ name: "getBillingAccount",
3548
+ inputs: [
3549
+ {
3550
+ name: "app",
3551
+ type: "address",
3552
+ internalType: "contractIApp"
3553
+ }
3554
+ ],
3555
+ outputs: [
3556
+ {
3557
+ name: "",
3558
+ type: "address",
3559
+ internalType: "address"
3560
+ }
3561
+ ],
3562
+ stateMutability: "view"
3563
+ },
3564
+ {
3565
+ type: "function",
3566
+ name: "getBillingType",
3567
+ inputs: [
3568
+ {
3569
+ name: "app",
3570
+ type: "address",
3571
+ internalType: "contractIApp"
3572
+ }
3573
+ ],
3574
+ outputs: [
3575
+ {
3576
+ name: "",
3577
+ type: "uint8",
3578
+ internalType: "enumIAppController.BillingType"
3579
+ }
3580
+ ],
3581
+ stateMutability: "view"
3582
+ },
3583
+ {
3584
+ type: "function",
3585
+ name: "getMaxActiveAppsPerUser",
3586
+ inputs: [
3587
+ {
3588
+ name: "user",
3589
+ type: "address",
3590
+ internalType: "address"
3591
+ }
3592
+ ],
3593
+ outputs: [
3594
+ {
3595
+ name: "",
3596
+ type: "uint32",
3597
+ internalType: "uint32"
3598
+ }
3599
+ ],
3600
+ stateMutability: "view"
3601
+ },
3602
+ {
3603
+ type: "function",
3604
+ name: "globalActiveAppCount",
3605
+ inputs: [],
3606
+ outputs: [
3607
+ {
3608
+ name: "",
3609
+ type: "uint32",
3610
+ internalType: "uint32"
3611
+ }
3612
+ ],
3613
+ stateMutability: "view"
3614
+ },
3615
+ {
3616
+ type: "function",
3617
+ name: "initialize",
3618
+ inputs: [
3619
+ {
3620
+ name: "admin",
3621
+ type: "address",
3622
+ internalType: "address"
3623
+ }
3624
+ ],
3625
+ outputs: [],
3626
+ stateMutability: "nonpayable"
3627
+ },
3628
+ {
3629
+ type: "function",
3630
+ name: "maxGlobalActiveApps",
3631
+ inputs: [],
3632
+ outputs: [
3633
+ {
3634
+ name: "",
3635
+ type: "uint32",
3636
+ internalType: "uint32"
3637
+ }
3638
+ ],
3639
+ stateMutability: "view"
3640
+ },
3641
+ {
3642
+ type: "function",
3643
+ name: "permissionController",
3644
+ inputs: [],
3645
+ outputs: [
3646
+ {
3647
+ name: "",
3648
+ type: "address",
3649
+ internalType: "contractIPermissionController"
3650
+ }
3651
+ ],
3652
+ stateMutability: "view"
3653
+ },
3654
+ {
3655
+ type: "function",
3656
+ name: "releaseManager",
3657
+ inputs: [],
3658
+ outputs: [
3659
+ {
3660
+ name: "",
3661
+ type: "address",
3662
+ internalType: "contractIReleaseManager"
3663
+ }
3664
+ ],
3665
+ stateMutability: "view"
3666
+ },
3667
+ {
3668
+ type: "function",
3669
+ name: "setMaxActiveAppsPerUser",
3670
+ inputs: [
3671
+ {
3672
+ name: "user",
3673
+ type: "address",
3674
+ internalType: "address"
3675
+ },
3676
+ {
3677
+ name: "limit",
3678
+ type: "uint32",
3679
+ internalType: "uint32"
3680
+ }
3681
+ ],
3682
+ outputs: [],
3683
+ stateMutability: "nonpayable"
3684
+ },
3685
+ {
3686
+ type: "function",
3687
+ name: "setMaxGlobalActiveApps",
3688
+ inputs: [
3689
+ {
3690
+ name: "limit",
3691
+ type: "uint32",
3692
+ internalType: "uint32"
3693
+ }
3694
+ ],
3695
+ outputs: [],
3696
+ stateMutability: "nonpayable"
3697
+ },
3698
+ {
3699
+ type: "function",
3700
+ name: "startApp",
3701
+ inputs: [
3702
+ {
3703
+ name: "app",
3704
+ type: "address",
3705
+ internalType: "contractIApp"
3706
+ }
3707
+ ],
3708
+ outputs: [],
3709
+ stateMutability: "nonpayable"
3710
+ },
3711
+ {
3712
+ type: "function",
3713
+ name: "stopApp",
3714
+ inputs: [
3715
+ {
3716
+ name: "app",
3717
+ type: "address",
3718
+ internalType: "contractIApp"
3719
+ }
3720
+ ],
3721
+ outputs: [],
3722
+ stateMutability: "nonpayable"
3723
+ },
3724
+ {
3725
+ type: "function",
3726
+ name: "suspend",
3727
+ inputs: [
3728
+ {
3729
+ name: "account",
3730
+ type: "address",
3731
+ internalType: "address"
3732
+ },
3733
+ {
3734
+ name: "apps",
3735
+ type: "address[]",
3736
+ internalType: "contractIApp[]"
3737
+ }
3738
+ ],
3739
+ outputs: [],
3740
+ stateMutability: "nonpayable"
3741
+ },
3742
+ {
3743
+ type: "function",
3744
+ name: "terminateApp",
3745
+ inputs: [
3746
+ {
3747
+ name: "app",
3748
+ type: "address",
3749
+ internalType: "contractIApp"
3750
+ }
3751
+ ],
3752
+ outputs: [],
3753
+ stateMutability: "nonpayable"
3754
+ },
3755
+ {
3756
+ type: "function",
3757
+ name: "terminateAppByAdmin",
3758
+ inputs: [
3759
+ {
3760
+ name: "app",
3761
+ type: "address",
3762
+ internalType: "contractIApp"
3763
+ }
3764
+ ],
3765
+ outputs: [],
3766
+ stateMutability: "nonpayable"
3767
+ },
3768
+ {
3769
+ type: "function",
3770
+ name: "updateAppMetadataURI",
3771
+ inputs: [
3772
+ {
3773
+ name: "app",
3774
+ type: "address",
3775
+ internalType: "contractIApp"
3776
+ },
3777
+ {
3778
+ name: "metadataURI",
3779
+ type: "string",
3780
+ internalType: "string"
3781
+ }
3782
+ ],
3783
+ outputs: [],
3784
+ stateMutability: "nonpayable"
3785
+ },
3786
+ {
3787
+ type: "function",
3788
+ name: "upgradeApp",
3789
+ inputs: [
3790
+ {
3791
+ name: "app",
3792
+ type: "address",
3793
+ internalType: "contractIApp"
3794
+ },
3795
+ {
3796
+ name: "release",
3797
+ type: "tuple",
3798
+ internalType: "structIAppController.Release",
3799
+ components: [
3800
+ {
3801
+ name: "rmsRelease",
3802
+ type: "tuple",
3803
+ internalType: "structIReleaseManagerTypes.Release",
3804
+ components: [
3805
+ {
3806
+ name: "artifacts",
3807
+ type: "tuple[]",
3808
+ internalType: "structIReleaseManagerTypes.Artifact[]",
3809
+ components: [
3810
+ {
3811
+ name: "digest",
3812
+ type: "bytes32",
3813
+ internalType: "bytes32"
3814
+ },
3815
+ {
3816
+ name: "registry",
3817
+ type: "string",
3818
+ internalType: "string"
3819
+ }
3820
+ ]
3821
+ },
3822
+ {
3823
+ name: "upgradeByTime",
3824
+ type: "uint32",
3825
+ internalType: "uint32"
3826
+ }
3827
+ ]
3828
+ },
3829
+ {
3830
+ name: "publicEnv",
3831
+ type: "bytes",
3832
+ internalType: "bytes"
3833
+ },
3834
+ {
3835
+ name: "encryptedEnv",
3836
+ type: "bytes",
3837
+ internalType: "bytes"
3838
+ },
3839
+ {
3840
+ name: "containerPolicy",
3841
+ type: "tuple",
3842
+ internalType: "structIAppController.ContainerPolicy",
3843
+ components: [
3844
+ {
3845
+ name: "args",
3846
+ type: "string[]",
3847
+ internalType: "string[]"
3848
+ },
3849
+ {
3850
+ name: "cmdOverride",
3851
+ type: "string[]",
3852
+ internalType: "string[]"
3853
+ },
3854
+ {
3855
+ name: "env",
3856
+ type: "tuple[]",
3857
+ internalType: "structIAppController.EnvVar[]",
3858
+ components: [
3859
+ {
3860
+ name: "key",
3861
+ type: "string",
3862
+ internalType: "string"
3863
+ },
3864
+ {
3865
+ name: "value",
3866
+ type: "string",
3867
+ internalType: "string"
3868
+ }
3869
+ ]
3870
+ },
3871
+ {
3872
+ name: "envOverride",
3873
+ type: "tuple[]",
3874
+ internalType: "structIAppController.EnvVar[]",
3875
+ components: [
3876
+ {
3877
+ name: "key",
3878
+ type: "string",
3879
+ internalType: "string"
3880
+ },
3881
+ {
3882
+ name: "value",
3883
+ type: "string",
3884
+ internalType: "string"
3885
+ }
3886
+ ]
3887
+ },
3888
+ {
3889
+ name: "restartPolicy",
3890
+ type: "string",
3891
+ internalType: "string"
3892
+ }
3893
+ ]
3894
+ }
3895
+ ]
3896
+ }
3897
+ ],
3898
+ outputs: [
3899
+ {
3900
+ name: "",
3901
+ type: "uint256",
3902
+ internalType: "uint256"
3903
+ }
3904
+ ],
3905
+ stateMutability: "nonpayable"
3906
+ },
3907
+ {
3908
+ type: "function",
3909
+ name: "version",
3910
+ inputs: [],
3911
+ outputs: [
3912
+ {
3913
+ name: "",
3914
+ type: "string",
3915
+ internalType: "string"
3916
+ }
3917
+ ],
3918
+ stateMutability: "view"
3919
+ },
3920
+ {
3921
+ type: "event",
3922
+ name: "AppCreated",
3923
+ inputs: [
3924
+ {
3925
+ name: "creator",
3926
+ type: "address",
3927
+ indexed: true,
3928
+ internalType: "address"
3929
+ },
3930
+ {
3931
+ name: "app",
3932
+ type: "address",
3933
+ indexed: true,
3934
+ internalType: "contractIApp"
3935
+ },
3936
+ {
3937
+ name: "operatorSetId",
3938
+ type: "uint32",
3939
+ indexed: false,
3940
+ internalType: "uint32"
3941
+ }
3942
+ ],
3943
+ anonymous: false
3944
+ },
3945
+ {
3946
+ type: "event",
3947
+ name: "AppMetadataURIUpdated",
3948
+ inputs: [
3949
+ {
3950
+ name: "app",
3951
+ type: "address",
3952
+ indexed: true,
3953
+ internalType: "contractIApp"
3954
+ },
3955
+ {
3956
+ name: "metadataURI",
3957
+ type: "string",
3958
+ indexed: false,
3959
+ internalType: "string"
3960
+ }
3961
+ ],
3962
+ anonymous: false
3963
+ },
3964
+ {
3965
+ type: "event",
3966
+ name: "AppStarted",
3967
+ inputs: [
3968
+ {
3969
+ name: "app",
3970
+ type: "address",
3971
+ indexed: true,
3972
+ internalType: "contractIApp"
3973
+ }
3974
+ ],
3975
+ anonymous: false
3976
+ },
3977
+ {
3978
+ type: "event",
3979
+ name: "AppStopped",
3980
+ inputs: [
3981
+ {
3982
+ name: "app",
3983
+ type: "address",
3984
+ indexed: true,
3985
+ internalType: "contractIApp"
3986
+ }
3987
+ ],
3988
+ anonymous: false
3989
+ },
3990
+ {
3991
+ type: "event",
3992
+ name: "AppSuspended",
3993
+ inputs: [
3994
+ {
3995
+ name: "app",
3996
+ type: "address",
3997
+ indexed: true,
3998
+ internalType: "contractIApp"
3999
+ }
4000
+ ],
4001
+ anonymous: false
4002
+ },
4003
+ {
4004
+ type: "event",
4005
+ name: "AppTerminated",
4006
+ inputs: [
4007
+ {
4008
+ name: "app",
4009
+ type: "address",
4010
+ indexed: true,
4011
+ internalType: "contractIApp"
4012
+ }
4013
+ ],
4014
+ anonymous: false
4015
+ },
4016
+ {
4017
+ type: "event",
4018
+ name: "AppTerminatedByAdmin",
4019
+ inputs: [
4020
+ {
4021
+ name: "app",
4022
+ type: "address",
4023
+ indexed: true,
4024
+ internalType: "contractIApp"
4025
+ }
4026
+ ],
4027
+ anonymous: false
4028
+ },
4029
+ {
4030
+ type: "event",
4031
+ name: "AppUpgraded",
4032
+ inputs: [
4033
+ {
4034
+ name: "app",
4035
+ type: "address",
4036
+ indexed: true,
4037
+ internalType: "contractIApp"
4038
+ },
4039
+ {
4040
+ name: "rmsReleaseId",
4041
+ type: "uint256",
4042
+ indexed: false,
4043
+ internalType: "uint256"
4044
+ },
4045
+ {
4046
+ name: "release",
4047
+ type: "tuple",
4048
+ indexed: false,
4049
+ internalType: "structIAppController.Release",
4050
+ components: [
4051
+ {
4052
+ name: "rmsRelease",
4053
+ type: "tuple",
4054
+ internalType: "structIReleaseManagerTypes.Release",
4055
+ components: [
4056
+ {
4057
+ name: "artifacts",
4058
+ type: "tuple[]",
4059
+ internalType: "structIReleaseManagerTypes.Artifact[]",
4060
+ components: [
4061
+ {
4062
+ name: "digest",
4063
+ type: "bytes32",
4064
+ internalType: "bytes32"
4065
+ },
4066
+ {
4067
+ name: "registry",
4068
+ type: "string",
4069
+ internalType: "string"
4070
+ }
4071
+ ]
4072
+ },
4073
+ {
4074
+ name: "upgradeByTime",
4075
+ type: "uint32",
4076
+ internalType: "uint32"
4077
+ }
4078
+ ]
4079
+ },
4080
+ {
4081
+ name: "publicEnv",
4082
+ type: "bytes",
4083
+ internalType: "bytes"
4084
+ },
4085
+ {
4086
+ name: "encryptedEnv",
4087
+ type: "bytes",
4088
+ internalType: "bytes"
4089
+ },
4090
+ {
4091
+ name: "containerPolicy",
4092
+ type: "tuple",
4093
+ internalType: "structIAppController.ContainerPolicy",
4094
+ components: [
4095
+ {
4096
+ name: "args",
4097
+ type: "string[]",
4098
+ internalType: "string[]"
4099
+ },
4100
+ {
4101
+ name: "cmdOverride",
4102
+ type: "string[]",
4103
+ internalType: "string[]"
4104
+ },
4105
+ {
4106
+ name: "env",
4107
+ type: "tuple[]",
4108
+ internalType: "structIAppController.EnvVar[]",
4109
+ components: [
4110
+ {
4111
+ name: "key",
4112
+ type: "string",
4113
+ internalType: "string"
4114
+ },
4115
+ {
4116
+ name: "value",
4117
+ type: "string",
4118
+ internalType: "string"
4119
+ }
4120
+ ]
4121
+ },
4122
+ {
4123
+ name: "envOverride",
4124
+ type: "tuple[]",
4125
+ internalType: "structIAppController.EnvVar[]",
4126
+ components: [
4127
+ {
4128
+ name: "key",
4129
+ type: "string",
4130
+ internalType: "string"
4131
+ },
4132
+ {
4133
+ name: "value",
4134
+ type: "string",
4135
+ internalType: "string"
4136
+ }
4137
+ ]
4138
+ },
4139
+ {
4140
+ name: "restartPolicy",
4141
+ type: "string",
4142
+ internalType: "string"
4143
+ }
4144
+ ]
4145
+ }
4146
+ ]
4147
+ }
4148
+ ],
4149
+ anonymous: false
4150
+ },
4151
+ {
4152
+ type: "event",
4153
+ name: "GlobalMaxActiveAppsSet",
4154
+ inputs: [
4155
+ {
4156
+ name: "limit",
4157
+ type: "uint32",
4158
+ indexed: false,
4159
+ internalType: "uint32"
4160
+ }
4161
+ ],
4162
+ anonymous: false
4163
+ },
4164
+ {
4165
+ type: "event",
4166
+ name: "Initialized",
4167
+ inputs: [
4168
+ {
4169
+ name: "version",
4170
+ type: "uint8",
4171
+ indexed: false,
4172
+ internalType: "uint8"
4173
+ }
4174
+ ],
4175
+ anonymous: false
4176
+ },
4177
+ {
4178
+ type: "event",
4179
+ name: "MaxActiveAppsSet",
4180
+ inputs: [
4181
+ {
4182
+ name: "user",
4183
+ type: "address",
4184
+ indexed: true,
4185
+ internalType: "address"
4186
+ },
4187
+ {
4188
+ name: "limit",
4189
+ type: "uint32",
4190
+ indexed: false,
4191
+ internalType: "uint32"
4192
+ }
4193
+ ],
4194
+ anonymous: false
4195
+ },
4196
+ {
4197
+ type: "event",
4198
+ name: "UpgradeConfirmed",
4199
+ inputs: [
4200
+ {
4201
+ name: "app",
4202
+ type: "address",
4203
+ indexed: true,
4204
+ internalType: "contractIApp"
4205
+ },
4206
+ {
4207
+ name: "pendingReleaseBlockNumber",
4208
+ type: "uint32",
4209
+ indexed: false,
4210
+ internalType: "uint32"
4211
+ }
4212
+ ],
4213
+ anonymous: false
4214
+ },
4215
+ {
4216
+ type: "error",
4217
+ name: "AccountHasActiveApps",
4218
+ inputs: []
4219
+ },
4220
+ {
4221
+ type: "error",
4222
+ name: "AppAlreadyExists",
4223
+ inputs: []
4224
+ },
4225
+ {
4226
+ type: "error",
4227
+ name: "AppDoesNotExist",
4228
+ inputs: []
4229
+ },
4230
+ {
4231
+ type: "error",
4232
+ name: "GlobalMaxActiveAppsExceeded",
4233
+ inputs: []
4234
+ },
4235
+ {
4236
+ type: "error",
4237
+ name: "InvalidAppStatus",
4238
+ inputs: []
4239
+ },
4240
+ {
4241
+ type: "error",
4242
+ name: "InvalidPermissions",
4243
+ inputs: []
4244
+ },
4245
+ {
4246
+ type: "error",
4247
+ name: "InvalidReleaseMetadataURI",
4248
+ inputs: []
4249
+ },
4250
+ {
4251
+ type: "error",
4252
+ name: "InvalidShortString",
4253
+ inputs: []
4254
+ },
4255
+ {
4256
+ type: "error",
4257
+ name: "InvalidSignature",
4258
+ inputs: []
4259
+ },
4260
+ {
4261
+ type: "error",
4262
+ name: "MaxActiveAppsExceeded",
4263
+ inputs: []
4264
+ },
4265
+ {
4266
+ type: "error",
4267
+ name: "MoreThanOneArtifact",
4268
+ inputs: []
4269
+ },
4270
+ {
4271
+ type: "error",
4272
+ name: "NoPendingUpgrade",
4273
+ inputs: []
4274
+ },
4275
+ {
4276
+ type: "error",
4277
+ name: "SignatureExpired",
4278
+ inputs: []
4279
+ },
4280
+ {
4281
+ type: "error",
4282
+ name: "StringTooLong",
4283
+ inputs: [
4284
+ {
4285
+ name: "str",
4286
+ type: "string",
4287
+ internalType: "string"
4288
+ }
4289
+ ]
2639
4290
  }
2640
- return hash;
2641
- }
2642
-
2643
- // src/client/common/contract/caller.ts
2644
- var import_viem3 = require("viem");
2645
-
2646
- // src/client/common/utils/helpers.ts
2647
- var import_viem2 = require("viem");
2648
- var import_chains2 = require("viem/chains");
2649
- var import_accounts = require("viem/accounts");
2650
- function getChainFromID(chainID, fallback2 = import_chains2.sepolia) {
2651
- const id = Number(chainID);
2652
- return (0, import_viem2.extractChain)({ chains: SUPPORTED_CHAINS, id }) || fallback2;
2653
- }
2654
- function createClients(options) {
2655
- const { privateKey, rpcUrl, chainId } = options;
2656
- const privateKeyHex = addHexPrefix(privateKey);
2657
- const account = (0, import_accounts.privateKeyToAccount)(privateKeyHex);
2658
- const chain = getChainFromID(chainId);
2659
- const transport = typeof rpcUrl === "string" ? (0, import_viem2.http)(rpcUrl) : (0, import_viem2.fallback)(rpcUrl.map((url) => (0, import_viem2.http)(url)));
2660
- const publicClient = (0, import_viem2.createPublicClient)({
2661
- chain,
2662
- transport
2663
- });
2664
- const walletClient = (0, import_viem2.createWalletClient)({
2665
- account,
2666
- chain,
2667
- transport
2668
- });
2669
- return { walletClient, publicClient };
2670
- }
2671
- function addHexPrefix(value) {
2672
- return value.startsWith("0x") ? value : `0x${value}`;
2673
- }
2674
- function stripHexPrefix(value) {
2675
- return value.startsWith("0x") ? value.slice(2) : value;
2676
- }
4291
+ ];
2677
4292
 
2678
- // src/client/common/abis/AppController.json
2679
- var AppController_default = [
4293
+ // src/client/common/abis/AppController.v1_4.json
4294
+ var AppController_v1_4_default = [
2680
4295
  {
2681
4296
  type: "constructor",
2682
4297
  inputs: [
@@ -4360,6 +5975,38 @@ var PermissionController_default = [
4360
5975
  ];
4361
5976
 
4362
5977
  // src/client/common/contract/caller.ts
5978
+ function appControllerAbiFor(environmentConfig) {
5979
+ return environmentConfig.releaseAbiVersion === "v1.4" ? AppController_v1_4_default : AppController_default;
5980
+ }
5981
+ function supportsContainerPolicy(environmentConfig) {
5982
+ return environmentConfig.releaseAbiVersion !== "v1.4";
5983
+ }
5984
+ function containerPolicyForViem(policy = EMPTY_CONTAINER_POLICY) {
5985
+ return {
5986
+ args: policy.args,
5987
+ cmdOverride: policy.cmdOverride,
5988
+ env: policy.env.map((e) => ({ key: e.key, value: e.value })),
5989
+ envOverride: policy.envOverride.map((e) => ({ key: e.key, value: e.value })),
5990
+ restartPolicy: policy.restartPolicy
5991
+ };
5992
+ }
5993
+ function releaseForViem(release, environmentConfig) {
5994
+ const base = {
5995
+ rmsRelease: {
5996
+ artifacts: release.rmsRelease.artifacts.map((artifact) => ({
5997
+ digest: `0x${(0, import_viem3.bytesToHex)(artifact.digest).slice(2).padStart(64, "0")}`,
5998
+ registry: artifact.registry
5999
+ })),
6000
+ upgradeByTime: release.rmsRelease.upgradeByTime
6001
+ },
6002
+ publicEnv: (0, import_viem3.bytesToHex)(release.publicEnv),
6003
+ encryptedEnv: (0, import_viem3.bytesToHex)(release.encryptedEnv)
6004
+ };
6005
+ if (!supportsContainerPolicy(environmentConfig)) {
6006
+ return base;
6007
+ }
6008
+ return { ...base, containerPolicy: containerPolicyForViem(release.containerPolicy) };
6009
+ }
4363
6010
  function formatETH(wei) {
4364
6011
  const eth = Number(wei) / 1e18;
4365
6012
  const costStr = eth.toFixed(6);
@@ -4397,7 +6044,7 @@ async function calculateAppID(options) {
4397
6044
  const saltHex = `0x${paddedSaltHex}`;
4398
6045
  const appID = await publicClient.readContract({
4399
6046
  address: environmentConfig.appControllerAddress,
4400
- abi: AppController_default,
6047
+ abi: appControllerAbiFor(environmentConfig),
4401
6048
  functionName: "calculateAppId",
4402
6049
  args: [ownerAddress, saltHex]
4403
6050
  });
@@ -4421,22 +6068,12 @@ async function prepareDeployBatch(options, logger = noopLogger) {
4421
6068
  const saltHexString = (0, import_viem3.bytesToHex)(salt).slice(2);
4422
6069
  const paddedSaltHex = saltHexString.padStart(64, "0");
4423
6070
  const saltHex = `0x${paddedSaltHex}`;
4424
- const releaseForViem = {
4425
- rmsRelease: {
4426
- artifacts: release.rmsRelease.artifacts.map((artifact) => ({
4427
- digest: `0x${(0, import_viem3.bytesToHex)(artifact.digest).slice(2).padStart(64, "0")}`,
4428
- registry: artifact.registry
4429
- })),
4430
- upgradeByTime: release.rmsRelease.upgradeByTime
4431
- },
4432
- publicEnv: (0, import_viem3.bytesToHex)(release.publicEnv),
4433
- encryptedEnv: (0, import_viem3.bytesToHex)(release.encryptedEnv)
4434
- };
6071
+ const release_ = releaseForViem(release, environmentConfig);
4435
6072
  const functionName = options.billTo === "app" ? "createAppWithIsolatedBilling" : "createApp";
4436
6073
  const createData = (0, import_viem3.encodeFunctionData)({
4437
- abi: AppController_default,
6074
+ abi: appControllerAbiFor(environmentConfig),
4438
6075
  functionName,
4439
- args: [saltHex, releaseForViem]
6076
+ args: [saltHex, release_]
4440
6077
  });
4441
6078
  const acceptAdminData = (0, import_viem3.encodeFunctionData)({
4442
6079
  abi: PermissionController_default,
@@ -4524,21 +6161,11 @@ async function prepareUpgradeBatch(options) {
4524
6161
  publicLogs,
4525
6162
  needsPermissionChange
4526
6163
  } = options;
4527
- const releaseForViem = {
4528
- rmsRelease: {
4529
- artifacts: release.rmsRelease.artifacts.map((artifact) => ({
4530
- digest: `0x${(0, import_viem3.bytesToHex)(artifact.digest).slice(2).padStart(64, "0")}`,
4531
- registry: artifact.registry
4532
- })),
4533
- upgradeByTime: release.rmsRelease.upgradeByTime
4534
- },
4535
- publicEnv: (0, import_viem3.bytesToHex)(release.publicEnv),
4536
- encryptedEnv: (0, import_viem3.bytesToHex)(release.encryptedEnv)
4537
- };
6164
+ const release_ = releaseForViem(release, environmentConfig);
4538
6165
  const upgradeData = (0, import_viem3.encodeFunctionData)({
4539
- abi: AppController_default,
6166
+ abi: appControllerAbiFor(environmentConfig),
4540
6167
  functionName: "upgradeApp",
4541
- args: [appID, releaseForViem]
6168
+ args: [appID, release_]
4542
6169
  });
4543
6170
  const executions = [
4544
6171
  {
@@ -4672,7 +6299,7 @@ ${pendingMessage}`);
4672
6299
  if (callError.data) {
4673
6300
  try {
4674
6301
  const decoded = (0, import_viem3.decodeErrorResult)({
4675
- abi: AppController_default,
6302
+ abi: appControllerAbiFor(environmentConfig),
4676
6303
  data: callError.data
4677
6304
  });
4678
6305
  const formattedError = formatAppControllerError(decoded);
@@ -4725,7 +6352,7 @@ function formatAppControllerError(decoded) {
4725
6352
  async function getActiveAppCount(publicClient, environmentConfig, user) {
4726
6353
  const count = await publicClient.readContract({
4727
6354
  address: environmentConfig.appControllerAddress,
4728
- abi: AppController_default,
6355
+ abi: appControllerAbiFor(environmentConfig),
4729
6356
  functionName: "getActiveAppCount",
4730
6357
  args: [user]
4731
6358
  });
@@ -4734,7 +6361,7 @@ async function getActiveAppCount(publicClient, environmentConfig, user) {
4734
6361
  async function getMaxActiveAppsPerUser(publicClient, environmentConfig, user) {
4735
6362
  const quota = await publicClient.readContract({
4736
6363
  address: environmentConfig.appControllerAddress,
4737
- abi: AppController_default,
6364
+ abi: appControllerAbiFor(environmentConfig),
4738
6365
  functionName: "getMaxActiveAppsPerUser",
4739
6366
  args: [user]
4740
6367
  });
@@ -4743,7 +6370,7 @@ async function getMaxActiveAppsPerUser(publicClient, environmentConfig, user) {
4743
6370
  async function getAppsByDeveloper(publicClient, environmentConfig, developer, offset, limit) {
4744
6371
  const result = await publicClient.readContract({
4745
6372
  address: environmentConfig.appControllerAddress,
4746
- abi: AppController_default,
6373
+ abi: appControllerAbiFor(environmentConfig),
4747
6374
  functionName: "getAppsByDeveloper",
4748
6375
  args: [developer, offset, limit]
4749
6376
  });
@@ -4755,7 +6382,7 @@ async function getAppsByDeveloper(publicClient, environmentConfig, developer, of
4755
6382
  async function getBillingType(publicClient, environmentConfig, app) {
4756
6383
  const result = await publicClient.readContract({
4757
6384
  address: environmentConfig.appControllerAddress,
4758
- abi: AppController_default,
6385
+ abi: appControllerAbiFor(environmentConfig),
4759
6386
  functionName: "getBillingType",
4760
6387
  args: [app]
4761
6388
  });
@@ -4764,7 +6391,7 @@ async function getBillingType(publicClient, environmentConfig, app) {
4764
6391
  async function getAppsByBillingAccount(publicClient, environmentConfig, account, offset, limit) {
4765
6392
  const result = await publicClient.readContract({
4766
6393
  address: environmentConfig.appControllerAddress,
4767
- abi: AppController_default,
6394
+ abi: appControllerAbiFor(environmentConfig),
4768
6395
  functionName: "getAppsByBillingAccount",
4769
6396
  args: [account, offset, limit]
4770
6397
  });
@@ -4798,7 +6425,7 @@ async function getAppLatestReleaseBlockNumbers(publicClient, environmentConfig,
4798
6425
  appIDs.map(
4799
6426
  (appID) => publicClient.readContract({
4800
6427
  address: environmentConfig.appControllerAddress,
4801
- abi: AppController_default,
6428
+ abi: appControllerAbiFor(environmentConfig),
4802
6429
  functionName: "getAppLatestReleaseBlockNumber",
4803
6430
  args: [appID]
4804
6431
  }).catch(() => null)
@@ -4877,12 +6504,41 @@ async function undelegate(options, logger = noopLogger) {
4877
6504
  return hash;
4878
6505
  }
4879
6506
 
6507
+ // src/client/common/gas/insufficientGas.ts
6508
+ var import_viem4 = require("viem");
6509
+ var InsufficientGasError = class extends Error {
6510
+ constructor(args) {
6511
+ const requiredEth = (0, import_viem4.formatEther)(args.requiredWei);
6512
+ const availableEth = (0, import_viem4.formatEther)(args.availableWei);
6513
+ super(
6514
+ `Insufficient ETH for gas: wallet ${args.address} has ${availableEth} ETH but this transaction needs ~${requiredEth} ETH.
6515
+ Compute credits do not pay on-chain gas \u2014 fund the wallet with ETH and retry.`
6516
+ );
6517
+ this.name = "InsufficientGasError";
6518
+ this.address = args.address;
6519
+ this.requiredWei = args.requiredWei;
6520
+ this.availableWei = args.availableWei;
6521
+ this.requiredEth = requiredEth;
6522
+ this.availableEth = availableEth;
6523
+ }
6524
+ };
6525
+ async function assertSufficientGas(args) {
6526
+ const availableWei = await args.publicClient.getBalance({ address: args.address });
6527
+ if (availableWei < args.gasEstimate.maxCostWei) {
6528
+ throw new InsufficientGasError({
6529
+ address: args.address,
6530
+ requiredWei: args.gasEstimate.maxCostWei,
6531
+ availableWei
6532
+ });
6533
+ }
6534
+ }
6535
+
4880
6536
  // src/client/common/utils/userapi.ts
4881
6537
  var import_axios2 = __toESM(require("axios"), 1);
4882
6538
 
4883
6539
  // src/client/common/utils/auth.ts
4884
- var import_viem4 = require("viem");
4885
- var APP_CONTROLLER_ABI = (0, import_viem4.parseAbi)([
6540
+ var import_viem5 = require("viem");
6541
+ var APP_CONTROLLER_ABI = (0, import_viem5.parseAbi)([
4886
6542
  "function calculateApiPermissionDigestHash(bytes4 permission, uint256 expiry) view returns (bytes32)"
4887
6543
  ]);
4888
6544
  async function calculatePermissionSignature(options) {
@@ -4940,6 +6596,7 @@ var import_axios = __toESM(require("axios"), 1);
4940
6596
  var MAX_RETRIES = 5;
4941
6597
  var INITIAL_BACKOFF_MS = 1e3;
4942
6598
  var MAX_BACKOFF_MS = 3e4;
6599
+ var RETRYABLE_STATUSES = /* @__PURE__ */ new Set([429, 502, 503, 504]);
4943
6600
  function sleep(ms) {
4944
6601
  return new Promise((resolve2) => setTimeout(resolve2, ms));
4945
6602
  }
@@ -4959,7 +6616,7 @@ async function requestWithRetry(config) {
4959
6616
  for (let attempt = 0; attempt <= MAX_RETRIES; attempt++) {
4960
6617
  const res = await (0, import_axios.default)({ ...config, validateStatus: () => true });
4961
6618
  lastResponse = res;
4962
- if (res.status !== 429) {
6619
+ if (!RETRYABLE_STATUSES.has(res.status)) {
4963
6620
  return res;
4964
6621
  }
4965
6622
  if (attempt < MAX_RETRIES) {
@@ -4988,7 +6645,7 @@ var CanViewAppLogsPermission = "0x2fd3f2fe";
4988
6645
  var CanViewSensitiveAppInfoPermission = "0x0e67b22f";
4989
6646
  var CanUpdateAppProfilePermission = "0x036fef61";
4990
6647
  function getDefaultClientId() {
4991
- const version = true ? "1.0.0-dev.6" : "0.0.0";
6648
+ const version = true ? "1.0.0-dev.8" : "0.0.0";
4992
6649
  return `ecloud-sdk/v${version}`;
4993
6650
  }
4994
6651
  var UserApiClient = class {
@@ -5326,8 +6983,36 @@ function transformAppRelease(raw) {
5326
6983
 
5327
6984
  // src/client/common/contract/watcher.ts
5328
6985
  var WATCH_POLL_INTERVAL_SECONDS = 5;
6986
+ var WATCH_HEARTBEAT_INTERVAL_SECONDS = 30;
6987
+ var WATCH_DEFAULT_TIMEOUT_SECONDS = 10 * 60;
5329
6988
  var APP_STATUS_RUNNING = "Running";
5330
6989
  var APP_STATUS_FAILED = "Failed";
6990
+ var WatchTimeoutError = class extends Error {
6991
+ constructor(args) {
6992
+ super(
6993
+ args.message ?? `Timed out after ${args.elapsedSeconds}s waiting for app ${args.appId} (last status: ${args.lastStatus ?? "unknown"})`
6994
+ );
6995
+ this.name = "WatchTimeoutError";
6996
+ this.appId = args.appId;
6997
+ this.elapsedSeconds = args.elapsedSeconds;
6998
+ this.lastStatus = args.lastStatus;
6999
+ this.timeoutSeconds = args.timeoutSeconds;
7000
+ }
7001
+ };
7002
+ function resolveWatchTimeoutSeconds(explicit) {
7003
+ if (typeof explicit === "number" && Number.isFinite(explicit) && explicit > 0) {
7004
+ return Math.floor(explicit);
7005
+ }
7006
+ const raw = process.env.ECLOUD_WATCH_TIMEOUT_SECONDS;
7007
+ if (raw === void 0 || raw === "") {
7008
+ return WATCH_DEFAULT_TIMEOUT_SECONDS;
7009
+ }
7010
+ const parsed = Number(raw);
7011
+ if (!Number.isFinite(parsed) || parsed <= 0) {
7012
+ return WATCH_DEFAULT_TIMEOUT_SECONDS;
7013
+ }
7014
+ return Math.floor(parsed);
7015
+ }
5331
7016
  async function watchUntilRunning(options, logger) {
5332
7017
  const { walletClient, publicClient, environmentConfig, appId } = options;
5333
7018
  const userApiClient = new UserApiClient(environmentConfig, walletClient, publicClient);
@@ -5358,8 +7043,20 @@ async function watchUntilRunning(options, logger) {
5358
7043
  return false;
5359
7044
  };
5360
7045
  const startTime = Date.now();
7046
+ const timeoutSeconds = resolveWatchTimeoutSeconds(options.timeoutSeconds);
5361
7047
  let lastLoggedStatus;
7048
+ let lastHeartbeatAt = startTime;
5362
7049
  while (true) {
7050
+ const elapsedMs = Date.now() - startTime;
7051
+ const elapsed = Math.round(elapsedMs / 1e3);
7052
+ if (elapsed >= timeoutSeconds) {
7053
+ throw new WatchTimeoutError({
7054
+ appId,
7055
+ elapsedSeconds: elapsed,
7056
+ lastStatus: lastLoggedStatus,
7057
+ timeoutSeconds
7058
+ });
7059
+ }
5363
7060
  try {
5364
7061
  const info = await userApiClient.getInfos([appId], 1);
5365
7062
  if (info.length === 0) {
@@ -5369,16 +7066,22 @@ async function watchUntilRunning(options, logger) {
5369
7066
  const appInfo = info[0];
5370
7067
  const currentStatus = appInfo.status;
5371
7068
  const currentIP = appInfo.ip || "";
5372
- const elapsed = Math.round((Date.now() - startTime) / 1e3);
5373
7069
  if (currentStatus !== lastLoggedStatus) {
5374
7070
  logger.info(`Status: ${currentStatus} (${elapsed}s)`);
5375
7071
  lastLoggedStatus = currentStatus;
7072
+ lastHeartbeatAt = Date.now();
7073
+ } else if (Date.now() - lastHeartbeatAt >= WATCH_HEARTBEAT_INTERVAL_SECONDS * 1e3) {
7074
+ logger.info(`Status: ${currentStatus} (${elapsed}s)`);
7075
+ lastHeartbeatAt = Date.now();
5376
7076
  }
5377
7077
  if (stopCondition(currentStatus, currentIP)) {
5378
7078
  return currentIP || void 0;
5379
7079
  }
5380
7080
  await sleep2(WATCH_POLL_INTERVAL_SECONDS * 1e3);
5381
7081
  } catch (error) {
7082
+ if (error instanceof WatchTimeoutError) {
7083
+ throw error;
7084
+ }
5382
7085
  logger.warn(`Failed to fetch app info: ${error.message}`);
5383
7086
  await sleep2(WATCH_POLL_INTERVAL_SECONDS * 1e3);
5384
7087
  }
@@ -5387,6 +7090,7 @@ async function watchUntilRunning(options, logger) {
5387
7090
  var APP_STATUS_STOPPED = "Stopped";
5388
7091
  async function watchUntilUpgradeComplete(options, logger) {
5389
7092
  const { walletClient, publicClient, environmentConfig, appId } = options;
7093
+ const timeoutSeconds = resolveWatchTimeoutSeconds(options.timeoutSeconds);
5390
7094
  const userApiClient = new UserApiClient(environmentConfig, walletClient, publicClient);
5391
7095
  let initialStatus;
5392
7096
  let initialIP;
@@ -5424,7 +7128,20 @@ async function watchUntilUpgradeComplete(options, logger) {
5424
7128
  }
5425
7129
  return false;
5426
7130
  };
7131
+ const startTime = Date.now();
7132
+ const deadline = startTime + timeoutSeconds * 1e3;
7133
+ let lastLoggedStatus;
7134
+ let lastObservedStatus;
5427
7135
  while (true) {
7136
+ if (Date.now() >= deadline) {
7137
+ const elapsedSeconds = Math.round((Date.now() - startTime) / 1e3);
7138
+ throw new WatchTimeoutError({
7139
+ appId,
7140
+ lastStatus: lastObservedStatus,
7141
+ elapsedSeconds,
7142
+ timeoutSeconds
7143
+ });
7144
+ }
5428
7145
  try {
5429
7146
  const info = await userApiClient.getInfos([appId], 1);
5430
7147
  if (info.length === 0) {
@@ -5434,11 +7151,23 @@ async function watchUntilUpgradeComplete(options, logger) {
5434
7151
  const appInfo = info[0];
5435
7152
  const currentStatus = appInfo.status;
5436
7153
  const currentIP = appInfo.ip || "";
7154
+ lastObservedStatus = currentStatus;
7155
+ const elapsed = Math.round((Date.now() - startTime) / 1e3);
7156
+ if (currentStatus !== lastLoggedStatus) {
7157
+ logger.info(`Status: ${currentStatus} (${elapsed}s)`);
7158
+ lastLoggedStatus = currentStatus;
7159
+ }
5437
7160
  if (stopCondition(currentStatus, currentIP)) {
5438
7161
  return;
5439
7162
  }
5440
7163
  await sleep2(WATCH_POLL_INTERVAL_SECONDS * 1e3);
5441
7164
  } catch (error) {
7165
+ if (error instanceof WatchTimeoutError) {
7166
+ throw error;
7167
+ }
7168
+ if (typeof error?.message === "string" && error.message.includes("Failed")) {
7169
+ throw error;
7170
+ }
5442
7171
  logger.warn(`Failed to fetch app info: ${error.message}`);
5443
7172
  await sleep2(WATCH_POLL_INTERVAL_SECONDS * 1e3);
5444
7173
  }
@@ -5451,7 +7180,7 @@ function sleep2(ms) {
5451
7180
  // src/client/common/utils/validation.ts
5452
7181
  var import_fs = __toESM(require("fs"), 1);
5453
7182
  var import_path = __toESM(require("path"), 1);
5454
- var import_viem5 = require("viem");
7183
+ var import_viem6 = require("viem");
5455
7184
  function validateAppName(name) {
5456
7185
  if (!name) {
5457
7186
  throw new Error("App name cannot be empty");
@@ -5603,7 +7332,7 @@ function validateAppID(appID) {
5603
7332
  throw new Error("App ID is required");
5604
7333
  }
5605
7334
  const normalized = typeof appID === "string" ? addHexPrefix(appID) : appID;
5606
- if ((0, import_viem5.isAddress)(normalized)) {
7335
+ if ((0, import_viem6.isAddress)(normalized)) {
5607
7336
  return normalized;
5608
7337
  }
5609
7338
  throw new Error(`Invalid app ID: '${appID}' is not a valid address`);
@@ -5772,6 +7501,8 @@ var ENVIRONMENTS = {
5772
7501
  name: "sepolia",
5773
7502
  build: "dev",
5774
7503
  appControllerAddress: "0xa86DC1C47cb2518327fB4f9A1627F51966c83B92",
7504
+ releaseAbiVersion: "v1.5",
7505
+ // AppController upgraded to v1.5.x (containerPolicy)
5775
7506
  permissionControllerAddress: ChainAddresses[SEPOLIA_CHAIN_ID].PermissionController,
5776
7507
  erc7702DelegatorAddress: CommonAddresses.ERC7702Delegator,
5777
7508
  kmsServerURL: "http://10.128.0.57:8080",
@@ -5785,6 +7516,8 @@ var ENVIRONMENTS = {
5785
7516
  name: "sepolia",
5786
7517
  build: "prod",
5787
7518
  appControllerAddress: "0x0dd810a6ffba6a9820a10d97b659f07d8d23d4E2",
7519
+ releaseAbiVersion: "v1.4",
7520
+ // prod still on AppController v1.4.0 (3-field Release)
5788
7521
  permissionControllerAddress: ChainAddresses[SEPOLIA_CHAIN_ID].PermissionController,
5789
7522
  erc7702DelegatorAddress: CommonAddresses.ERC7702Delegator,
5790
7523
  kmsServerURL: "http://10.128.15.203:8080",
@@ -5799,6 +7532,8 @@ var ENVIRONMENTS = {
5799
7532
  name: "mainnet-alpha",
5800
7533
  build: "prod",
5801
7534
  appControllerAddress: "0xc38d35Fc995e75342A21CBd6D770305b142Fbe67",
7535
+ releaseAbiVersion: "v1.4",
7536
+ // prod still on AppController v1.4.0 (3-field Release)
5802
7537
  permissionControllerAddress: ChainAddresses[MAINNET_CHAIN_ID].PermissionController,
5803
7538
  erc7702DelegatorAddress: CommonAddresses.ERC7702Delegator,
5804
7539
  kmsServerURL: "http://10.128.0.2:8080",
@@ -6653,6 +8388,11 @@ async function prepareDeployFromVerifiableBuild(options, logger = defaultLogger)
6653
8388
  executions: batch.executions,
6654
8389
  authorizationList
6655
8390
  });
8391
+ await assertSufficientGas({
8392
+ publicClient: batch.publicClient,
8393
+ address: batch.walletClient.account.address,
8394
+ gasEstimate
8395
+ });
6656
8396
  const data = {
6657
8397
  appId: batch.appId,
6658
8398
  salt: batch.salt,
@@ -6911,6 +8651,11 @@ async function prepareDeploy(options, logger = defaultLogger) {
6911
8651
  executions: batch.executions,
6912
8652
  authorizationList
6913
8653
  });
8654
+ await assertSufficientGas({
8655
+ publicClient: batch.publicClient,
8656
+ address: batch.walletClient.account.address,
8657
+ gasEstimate
8658
+ });
6914
8659
  const data = {
6915
8660
  appId: batch.appId,
6916
8661
  salt: batch.salt,
@@ -6947,7 +8692,7 @@ async function executeDeploy(options) {
6947
8692
  }
6948
8693
  );
6949
8694
  }
6950
- async function watchDeployment(appId, walletClient, publicClient, environmentConfig, logger = defaultLogger, skipTelemetry) {
8695
+ async function watchDeployment(appId, walletClient, publicClient, environmentConfig, logger = defaultLogger, skipTelemetry, opts) {
6951
8696
  return withSDKTelemetry(
6952
8697
  {
6953
8698
  functionName: "watchDeployment",
@@ -6963,7 +8708,8 @@ async function watchDeployment(appId, walletClient, publicClient, environmentCon
6963
8708
  walletClient,
6964
8709
  publicClient,
6965
8710
  environmentConfig,
6966
- appId
8711
+ appId,
8712
+ timeoutSeconds: opts?.timeoutSeconds
6967
8713
  },
6968
8714
  logger
6969
8715
  );
@@ -7059,6 +8805,11 @@ async function prepareUpgradeFromVerifiableBuild(options, logger = defaultLogger
7059
8805
  executions: batch.executions,
7060
8806
  authorizationList
7061
8807
  });
8808
+ await assertSufficientGas({
8809
+ publicClient: batch.publicClient,
8810
+ address: batch.walletClient.account.address,
8811
+ gasEstimate
8812
+ });
7062
8813
  const data = {
7063
8814
  appId: batch.appId,
7064
8815
  executions: batch.executions,
@@ -7248,6 +8999,11 @@ async function prepareUpgrade(options, logger = defaultLogger) {
7248
8999
  executions: batch.executions,
7249
9000
  authorizationList
7250
9001
  });
9002
+ await assertSufficientGas({
9003
+ publicClient: batch.publicClient,
9004
+ address: batch.walletClient.account.address,
9005
+ gasEstimate
9006
+ });
7251
9007
  const data = {
7252
9008
  appId: batch.appId,
7253
9009
  executions: batch.executions,
@@ -7282,7 +9038,7 @@ async function executeUpgrade(options) {
7282
9038
  }
7283
9039
  );
7284
9040
  }
7285
- async function watchUpgrade(appId, walletClient, publicClient, environmentConfig, logger = defaultLogger, skipTelemetry) {
9041
+ async function watchUpgrade(appId, walletClient, publicClient, environmentConfig, logger = defaultLogger, skipTelemetry, opts) {
7286
9042
  return withSDKTelemetry(
7287
9043
  {
7288
9044
  functionName: "watchUpgrade",
@@ -7298,7 +9054,8 @@ async function watchUpgrade(appId, walletClient, publicClient, environmentConfig
7298
9054
  walletClient,
7299
9055
  publicClient,
7300
9056
  environmentConfig,
7301
- appId
9057
+ appId,
9058
+ timeoutSeconds: opts?.timeoutSeconds
7302
9059
  },
7303
9060
  logger
7304
9061
  );
@@ -7956,27 +9713,27 @@ async function logs(options, walletClient, publicClient, environmentConfig, logg
7956
9713
  }
7957
9714
 
7958
9715
  // src/client/modules/compute/app/index.ts
7959
- var CONTROLLER_ABI = (0, import_viem6.parseAbi)([
9716
+ var CONTROLLER_ABI = (0, import_viem7.parseAbi)([
7960
9717
  "function startApp(address appId)",
7961
9718
  "function stopApp(address appId)",
7962
9719
  "function terminateApp(address appId)"
7963
9720
  ]);
7964
9721
  function encodeStartAppData(appId) {
7965
- return (0, import_viem6.encodeFunctionData)({
9722
+ return (0, import_viem7.encodeFunctionData)({
7966
9723
  abi: CONTROLLER_ABI,
7967
9724
  functionName: "startApp",
7968
9725
  args: [appId]
7969
9726
  });
7970
9727
  }
7971
9728
  function encodeStopAppData(appId) {
7972
- return (0, import_viem6.encodeFunctionData)({
9729
+ return (0, import_viem7.encodeFunctionData)({
7973
9730
  abi: CONTROLLER_ABI,
7974
9731
  functionName: "stopApp",
7975
9732
  args: [appId]
7976
9733
  });
7977
9734
  }
7978
9735
  function encodeTerminateAppData(appId) {
7979
- return (0, import_viem6.encodeFunctionData)({
9736
+ return (0, import_viem7.encodeFunctionData)({
7980
9737
  abi: CONTROLLER_ABI,
7981
9738
  functionName: "terminateApp",
7982
9739
  args: [appId]
@@ -7990,7 +9747,7 @@ function createAppModule(ctx) {
7990
9747
  }
7991
9748
  const account = walletClient.account;
7992
9749
  const environment = getEnvironmentConfig(ctx.environment);
7993
- const logger = getLogger(ctx.verbose);
9750
+ const logger = ctx.logger ?? getLogger(ctx.verbose);
7994
9751
  return {
7995
9752
  async create(opts) {
7996
9753
  return createApp(opts, logger);
@@ -8102,14 +9859,15 @@ function createAppModule(ctx) {
8102
9859
  imageRef: result.imageRef
8103
9860
  };
8104
9861
  },
8105
- async watchDeployment(appId) {
9862
+ async watchDeployment(appId, opts) {
8106
9863
  return watchDeployment(
8107
9864
  appId,
8108
9865
  walletClient,
8109
9866
  publicClient,
8110
9867
  environment,
8111
9868
  logger,
8112
- skipTelemetry
9869
+ skipTelemetry,
9870
+ opts
8113
9871
  );
8114
9872
  },
8115
9873
  // Granular upgrade control
@@ -8167,8 +9925,16 @@ function createAppModule(ctx) {
8167
9925
  imageRef: result.imageRef
8168
9926
  };
8169
9927
  },
8170
- async watchUpgrade(appId) {
8171
- return watchUpgrade(appId, walletClient, publicClient, environment, logger, skipTelemetry);
9928
+ async watchUpgrade(appId, opts) {
9929
+ return watchUpgrade(
9930
+ appId,
9931
+ walletClient,
9932
+ publicClient,
9933
+ environment,
9934
+ logger,
9935
+ skipTelemetry,
9936
+ opts
9937
+ );
8172
9938
  },
8173
9939
  // Profile management
8174
9940
  async setProfile(appId, profile) {
@@ -8219,7 +9985,7 @@ function createAppModule(ctx) {
8219
9985
  },
8220
9986
  async () => {
8221
9987
  const pendingMessage = `Starting app ${appId}...`;
8222
- const data = (0, import_viem6.encodeFunctionData)({
9988
+ const data = (0, import_viem7.encodeFunctionData)({
8223
9989
  abi: CONTROLLER_ABI,
8224
9990
  functionName: "startApp",
8225
9991
  args: [appId]
@@ -8251,7 +10017,7 @@ function createAppModule(ctx) {
8251
10017
  },
8252
10018
  async () => {
8253
10019
  const pendingMessage = `Stopping app ${appId}...`;
8254
- const data = (0, import_viem6.encodeFunctionData)({
10020
+ const data = (0, import_viem7.encodeFunctionData)({
8255
10021
  abi: CONTROLLER_ABI,
8256
10022
  functionName: "stopApp",
8257
10023
  args: [appId]
@@ -8283,7 +10049,7 @@ function createAppModule(ctx) {
8283
10049
  },
8284
10050
  async () => {
8285
10051
  const pendingMessage = `Terminating app ${appId}...`;
8286
- const data = (0, import_viem6.encodeFunctionData)({
10052
+ const data = (0, import_viem7.encodeFunctionData)({
8287
10053
  abi: CONTROLLER_ABI,
8288
10054
  functionName: "terminateApp",
8289
10055
  args: [appId]
@@ -8350,7 +10116,7 @@ function createComputeModule(config) {
8350
10116
  }
8351
10117
 
8352
10118
  // src/client/modules/billing/index.ts
8353
- var import_viem7 = require("viem");
10119
+ var import_viem8 = require("viem");
8354
10120
 
8355
10121
  // src/client/common/abis/USDCCredits.json
8356
10122
  var USDCCredits_default = [
@@ -8535,7 +10301,7 @@ function createBillingModule(config) {
8535
10301
  executions.push({
8536
10302
  target: usdcAddress,
8537
10303
  value: 0n,
8538
- callData: (0, import_viem7.encodeFunctionData)({
10304
+ callData: (0, import_viem8.encodeFunctionData)({
8539
10305
  abi: ERC20_default,
8540
10306
  functionName: "approve",
8541
10307
  args: [creditsAddress, opts.amount]
@@ -8545,7 +10311,7 @@ function createBillingModule(config) {
8545
10311
  executions.push({
8546
10312
  target: creditsAddress,
8547
10313
  value: 0n,
8548
- callData: (0, import_viem7.encodeFunctionData)({
10314
+ callData: (0, import_viem8.encodeFunctionData)({
8549
10315
  abi: USDCCredits_default,
8550
10316
  functionName: "purchaseCreditsFor",
8551
10317
  args: [opts.amount, targetAccount]
@@ -9679,8 +11445,10 @@ var JwtProvider = class {
9679
11445
  BuildError,
9680
11446
  BuildFailedError,
9681
11447
  ConflictError,
11448
+ EMPTY_CONTAINER_POLICY,
9682
11449
  ERC20ABI,
9683
11450
  ForbiddenError,
11451
+ InsufficientGasError,
9684
11452
  JwtProvider,
9685
11453
  NoopClient,
9686
11454
  NotFoundError,
@@ -9690,9 +11458,12 @@ var JwtProvider = class {
9690
11458
  TimeoutError,
9691
11459
  USDCCreditsABI,
9692
11460
  UserApiClient,
11461
+ WATCH_DEFAULT_TIMEOUT_SECONDS,
11462
+ WatchTimeoutError,
9693
11463
  addHexPrefix,
9694
11464
  addMetric,
9695
11465
  addMetricWithDimensions,
11466
+ assertSufficientGas,
9696
11467
  assertValidFilePath,
9697
11468
  assertValidImageReference,
9698
11469
  assertValidPrivateKey,