@layr-labs/ecloud-sdk 0.2.2-dev → 0.3.0-dev

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
@@ -5,6 +5,9 @@ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
5
  var __getOwnPropNames = Object.getOwnPropertyNames;
6
6
  var __getProtoOf = Object.getPrototypeOf;
7
7
  var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __esm = (fn, res) => function __init() {
9
+ return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
10
+ };
8
11
  var __export = (target, all) => {
9
12
  for (var name in all)
10
13
  __defProp(target, name, { get: all[name], enumerable: true });
@@ -27,6 +30,135 @@ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__ge
27
30
  ));
28
31
  var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
32
 
33
+ // src/client/common/auth/session.ts
34
+ function stripHexPrefix2(hex) {
35
+ return hex.startsWith("0x") ? hex.slice(2) : hex;
36
+ }
37
+ async function parseErrorResponse(response) {
38
+ try {
39
+ const data = await response.json();
40
+ return data.error || response.statusText;
41
+ } catch {
42
+ return response.statusText;
43
+ }
44
+ }
45
+ async function loginToComputeApi(config, request) {
46
+ let response;
47
+ try {
48
+ response = await fetch(`${config.baseUrl}/auth/siwe/login`, {
49
+ method: "POST",
50
+ credentials: "include",
51
+ // Include cookies for session management
52
+ headers: {
53
+ "Content-Type": "application/json"
54
+ },
55
+ body: JSON.stringify({
56
+ message: request.message,
57
+ signature: stripHexPrefix2(request.signature)
58
+ })
59
+ });
60
+ } catch (error) {
61
+ throw new SessionError(
62
+ `Network error connecting to ${config.baseUrl}: ${error instanceof Error ? error.message : String(error)}`,
63
+ "NETWORK_ERROR"
64
+ );
65
+ }
66
+ if (!response.ok) {
67
+ const errorMessage = await parseErrorResponse(response);
68
+ const status = response.status;
69
+ if (status === 400) {
70
+ if (errorMessage.toLowerCase().includes("siwe")) {
71
+ throw new SessionError(`Invalid SIWE message: ${errorMessage}`, "INVALID_MESSAGE", status);
72
+ }
73
+ throw new SessionError(`Bad request: ${errorMessage}`, "INVALID_MESSAGE", status);
74
+ }
75
+ if (status === 401) {
76
+ throw new SessionError(`Invalid signature: ${errorMessage}`, "INVALID_SIGNATURE", status);
77
+ }
78
+ throw new SessionError(`Login failed: ${errorMessage}`, "UNKNOWN", status);
79
+ }
80
+ const data = await response.json();
81
+ return {
82
+ success: data.success,
83
+ address: data.address
84
+ };
85
+ }
86
+ async function getComputeApiSession(config) {
87
+ let response;
88
+ try {
89
+ response = await fetch(`${config.baseUrl}/auth/session`, {
90
+ method: "GET",
91
+ credentials: "include",
92
+ // Include cookies for session management
93
+ headers: {
94
+ "Content-Type": "application/json"
95
+ }
96
+ });
97
+ } catch {
98
+ return {
99
+ authenticated: false
100
+ };
101
+ }
102
+ if (response.status === 401) {
103
+ return {
104
+ authenticated: false
105
+ };
106
+ }
107
+ if (!response.ok) {
108
+ const errorMessage = await parseErrorResponse(response);
109
+ throw new SessionError(`Failed to get session: ${errorMessage}`, "UNKNOWN", response.status);
110
+ }
111
+ const data = await response.json();
112
+ return {
113
+ authenticated: data.authenticated,
114
+ address: data.address,
115
+ chainId: data.chain_id
116
+ };
117
+ }
118
+ async function logoutFromComputeApi(config) {
119
+ let response;
120
+ try {
121
+ response = await fetch(`${config.baseUrl}/auth/logout`, {
122
+ method: "POST",
123
+ credentials: "include",
124
+ // Include cookies for session management
125
+ headers: {
126
+ "Content-Type": "application/json"
127
+ }
128
+ });
129
+ } catch (error) {
130
+ throw new SessionError(
131
+ `Network error connecting to ${config.baseUrl}: ${error instanceof Error ? error.message : String(error)}`,
132
+ "NETWORK_ERROR"
133
+ );
134
+ }
135
+ if (response.status === 401) {
136
+ return;
137
+ }
138
+ if (!response.ok) {
139
+ const errorMessage = await parseErrorResponse(response);
140
+ throw new SessionError(`Logout failed: ${errorMessage}`, "UNKNOWN", response.status);
141
+ }
142
+ }
143
+ async function isSessionValid(config) {
144
+ const session = await getComputeApiSession(config);
145
+ return session.authenticated;
146
+ }
147
+ var SessionError;
148
+ var init_session = __esm({
149
+ "src/client/common/auth/session.ts"() {
150
+ "use strict";
151
+ SessionError = class extends Error {
152
+ constructor(message, code, statusCode) {
153
+ super(message);
154
+ this.code = code;
155
+ this.statusCode = statusCode;
156
+ this.name = "SessionError";
157
+ }
158
+ };
159
+ }
160
+ });
161
+
30
162
  // src/index.ts
31
163
  var index_exports = {};
32
164
  __export(index_exports, {
@@ -4560,130 +4692,8 @@ async function calculateBillingAuthSignature(options) {
4560
4692
  return { signature, expiry };
4561
4693
  }
4562
4694
 
4563
- // src/client/common/auth/session.ts
4564
- var SessionError = class extends Error {
4565
- constructor(message, code, statusCode) {
4566
- super(message);
4567
- this.code = code;
4568
- this.statusCode = statusCode;
4569
- this.name = "SessionError";
4570
- }
4571
- };
4572
- function stripHexPrefix2(hex) {
4573
- return hex.startsWith("0x") ? hex.slice(2) : hex;
4574
- }
4575
- async function parseErrorResponse(response) {
4576
- try {
4577
- const data = await response.json();
4578
- return data.error || response.statusText;
4579
- } catch {
4580
- return response.statusText;
4581
- }
4582
- }
4583
- async function loginToComputeApi(config, request) {
4584
- let response;
4585
- try {
4586
- response = await fetch(`${config.baseUrl}/auth/siwe/login`, {
4587
- method: "POST",
4588
- credentials: "include",
4589
- // Include cookies for session management
4590
- headers: {
4591
- "Content-Type": "application/json"
4592
- },
4593
- body: JSON.stringify({
4594
- message: request.message,
4595
- signature: stripHexPrefix2(request.signature)
4596
- })
4597
- });
4598
- } catch (error) {
4599
- throw new SessionError(
4600
- `Network error connecting to ${config.baseUrl}: ${error instanceof Error ? error.message : String(error)}`,
4601
- "NETWORK_ERROR"
4602
- );
4603
- }
4604
- if (!response.ok) {
4605
- const errorMessage = await parseErrorResponse(response);
4606
- const status = response.status;
4607
- if (status === 400) {
4608
- if (errorMessage.toLowerCase().includes("siwe")) {
4609
- throw new SessionError(`Invalid SIWE message: ${errorMessage}`, "INVALID_MESSAGE", status);
4610
- }
4611
- throw new SessionError(`Bad request: ${errorMessage}`, "INVALID_MESSAGE", status);
4612
- }
4613
- if (status === 401) {
4614
- throw new SessionError(`Invalid signature: ${errorMessage}`, "INVALID_SIGNATURE", status);
4615
- }
4616
- throw new SessionError(`Login failed: ${errorMessage}`, "UNKNOWN", status);
4617
- }
4618
- const data = await response.json();
4619
- return {
4620
- success: data.success,
4621
- address: data.address
4622
- };
4623
- }
4624
- async function getComputeApiSession(config) {
4625
- let response;
4626
- try {
4627
- response = await fetch(`${config.baseUrl}/auth/session`, {
4628
- method: "GET",
4629
- credentials: "include",
4630
- // Include cookies for session management
4631
- headers: {
4632
- "Content-Type": "application/json"
4633
- }
4634
- });
4635
- } catch {
4636
- return {
4637
- authenticated: false
4638
- };
4639
- }
4640
- if (response.status === 401) {
4641
- return {
4642
- authenticated: false
4643
- };
4644
- }
4645
- if (!response.ok) {
4646
- const errorMessage = await parseErrorResponse(response);
4647
- throw new SessionError(`Failed to get session: ${errorMessage}`, "UNKNOWN", response.status);
4648
- }
4649
- const data = await response.json();
4650
- return {
4651
- authenticated: data.authenticated,
4652
- address: data.address,
4653
- chainId: data.chain_id
4654
- };
4655
- }
4656
- async function logoutFromComputeApi(config) {
4657
- let response;
4658
- try {
4659
- response = await fetch(`${config.baseUrl}/auth/logout`, {
4660
- method: "POST",
4661
- credentials: "include",
4662
- // Include cookies for session management
4663
- headers: {
4664
- "Content-Type": "application/json"
4665
- }
4666
- });
4667
- } catch (error) {
4668
- throw new SessionError(
4669
- `Network error connecting to ${config.baseUrl}: ${error instanceof Error ? error.message : String(error)}`,
4670
- "NETWORK_ERROR"
4671
- );
4672
- }
4673
- if (response.status === 401) {
4674
- return;
4675
- }
4676
- if (!response.ok) {
4677
- const errorMessage = await parseErrorResponse(response);
4678
- throw new SessionError(`Logout failed: ${errorMessage}`, "UNKNOWN", response.status);
4679
- }
4680
- }
4681
- async function isSessionValid(config) {
4682
- const session = await getComputeApiSession(config);
4683
- return session.authenticated;
4684
- }
4685
-
4686
4695
  // src/client/common/utils/userapi.ts
4696
+ init_session();
4687
4697
  function isJsonObject(value) {
4688
4698
  return typeof value === "object" && value !== null && !Array.isArray(value);
4689
4699
  }
@@ -4700,7 +4710,7 @@ var CanViewAppLogsPermission = "0x2fd3f2fe";
4700
4710
  var CanViewSensitiveAppInfoPermission = "0x0e67b22f";
4701
4711
  var CanUpdateAppProfilePermission = "0x036fef61";
4702
4712
  function getDefaultClientId() {
4703
- const version = true ? "0.2.2-dev" : "0.0.0";
4713
+ const version = true ? "0.3.0-dev" : "0.0.0";
4704
4714
  return `ecloud-sdk/v${version}`;
4705
4715
  }
4706
4716
  var UserApiClient = class {
@@ -5608,21 +5618,214 @@ function isSubscriptionActive(status) {
5608
5618
 
5609
5619
  // src/client/common/utils/billingapi.ts
5610
5620
  var import_axios2 = __toESM(require("axios"), 1);
5621
+
5622
+ // src/client/common/auth/billingSession.ts
5623
+ var BillingSessionError = class extends Error {
5624
+ constructor(message, code, statusCode) {
5625
+ super(message);
5626
+ this.code = code;
5627
+ this.statusCode = statusCode;
5628
+ this.name = "BillingSessionError";
5629
+ }
5630
+ };
5631
+ function stripHexPrefix3(hex) {
5632
+ return hex.startsWith("0x") ? hex.slice(2) : hex;
5633
+ }
5634
+ async function parseErrorResponse2(response) {
5635
+ try {
5636
+ const data = await response.json();
5637
+ return data.error || response.statusText;
5638
+ } catch {
5639
+ return response.statusText;
5640
+ }
5641
+ }
5642
+ async function loginToBillingApi(config, request) {
5643
+ let response;
5644
+ try {
5645
+ response = await fetch(`${config.baseUrl}/auth/siwe/login`, {
5646
+ method: "POST",
5647
+ credentials: "include",
5648
+ // Include cookies for session management
5649
+ headers: {
5650
+ "Content-Type": "application/json"
5651
+ },
5652
+ body: JSON.stringify({
5653
+ message: request.message,
5654
+ signature: stripHexPrefix3(request.signature)
5655
+ })
5656
+ });
5657
+ } catch (error) {
5658
+ throw new BillingSessionError(
5659
+ `Network error connecting to ${config.baseUrl}: ${error instanceof Error ? error.message : String(error)}`,
5660
+ "NETWORK_ERROR"
5661
+ );
5662
+ }
5663
+ if (!response.ok) {
5664
+ const errorMessage = await parseErrorResponse2(response);
5665
+ const status = response.status;
5666
+ if (status === 400) {
5667
+ if (errorMessage.toLowerCase().includes("siwe")) {
5668
+ throw new BillingSessionError(`Invalid SIWE message: ${errorMessage}`, "INVALID_MESSAGE", status);
5669
+ }
5670
+ throw new BillingSessionError(`Bad request: ${errorMessage}`, "INVALID_MESSAGE", status);
5671
+ }
5672
+ if (status === 401) {
5673
+ throw new BillingSessionError(`Invalid signature: ${errorMessage}`, "INVALID_SIGNATURE", status);
5674
+ }
5675
+ throw new BillingSessionError(`Login failed: ${errorMessage}`, "UNKNOWN", status);
5676
+ }
5677
+ const data = await response.json();
5678
+ return {
5679
+ success: data.success,
5680
+ address: data.address
5681
+ };
5682
+ }
5683
+ async function getBillingApiSession(config) {
5684
+ let response;
5685
+ try {
5686
+ response = await fetch(`${config.baseUrl}/auth/session`, {
5687
+ method: "GET",
5688
+ credentials: "include",
5689
+ // Include cookies for session management
5690
+ headers: {
5691
+ "Content-Type": "application/json"
5692
+ }
5693
+ });
5694
+ } catch {
5695
+ return {
5696
+ authenticated: false
5697
+ };
5698
+ }
5699
+ if (response.status === 401) {
5700
+ return {
5701
+ authenticated: false
5702
+ };
5703
+ }
5704
+ if (!response.ok) {
5705
+ const errorMessage = await parseErrorResponse2(response);
5706
+ throw new BillingSessionError(`Failed to get session: ${errorMessage}`, "UNKNOWN", response.status);
5707
+ }
5708
+ const data = await response.json();
5709
+ return {
5710
+ authenticated: data.authenticated,
5711
+ address: data.address,
5712
+ chainId: data.chainId,
5713
+ authenticatedAt: data.authenticatedAt
5714
+ };
5715
+ }
5716
+ async function logoutFromBillingApi(config) {
5717
+ let response;
5718
+ try {
5719
+ response = await fetch(`${config.baseUrl}/auth/logout`, {
5720
+ method: "POST",
5721
+ credentials: "include",
5722
+ // Include cookies for session management
5723
+ headers: {
5724
+ "Content-Type": "application/json"
5725
+ }
5726
+ });
5727
+ } catch (error) {
5728
+ throw new BillingSessionError(
5729
+ `Network error connecting to ${config.baseUrl}: ${error instanceof Error ? error.message : String(error)}`,
5730
+ "NETWORK_ERROR"
5731
+ );
5732
+ }
5733
+ if (response.status === 401) {
5734
+ return;
5735
+ }
5736
+ if (!response.ok) {
5737
+ const errorMessage = await parseErrorResponse2(response);
5738
+ throw new BillingSessionError(`Logout failed: ${errorMessage}`, "UNKNOWN", response.status);
5739
+ }
5740
+ }
5741
+
5742
+ // src/client/common/utils/billingapi.ts
5611
5743
  var BillingApiClient = class {
5612
- constructor(config, walletClient) {
5744
+ constructor(config, walletClient, options = {}) {
5613
5745
  this.config = config;
5614
5746
  this.walletClient = walletClient;
5747
+ this.options = options;
5748
+ this.useSession = options.useSession ?? false;
5749
+ if (!this.useSession && !walletClient) {
5750
+ throw new Error("WalletClient is required when not using session authentication");
5751
+ }
5615
5752
  }
5616
5753
  /**
5617
5754
  * Get the address of the connected wallet
5755
+ * Returns undefined if using session auth without a wallet client
5618
5756
  */
5619
5757
  get address() {
5620
- const account = this.walletClient.account;
5758
+ const account = this.walletClient?.account;
5621
5759
  if (!account) {
5622
- throw new Error("WalletClient must have an account attached");
5760
+ if (!this.useSession) {
5761
+ throw new Error("WalletClient must have an account attached");
5762
+ }
5763
+ return void 0;
5623
5764
  }
5624
5765
  return account.address;
5625
5766
  }
5767
+ /**
5768
+ * Get the base URL of the billing API
5769
+ */
5770
+ get baseUrl() {
5771
+ return this.config.billingApiServerURL;
5772
+ }
5773
+ // ==========================================================================
5774
+ // SIWE Session Methods
5775
+ // ==========================================================================
5776
+ /**
5777
+ * Login to the billing API using SIWE
5778
+ *
5779
+ * This establishes a session with the billing API by verifying the SIWE message
5780
+ * and signature. On success, a session cookie is set in the browser.
5781
+ *
5782
+ * @param request - Login request containing SIWE message and signature
5783
+ * @returns Login result with the authenticated address
5784
+ *
5785
+ * @example
5786
+ * ```typescript
5787
+ * const { message } = createSiweMessage({
5788
+ * address: userAddress,
5789
+ * chainId: 11155111,
5790
+ * domain: window.location.host,
5791
+ * uri: window.location.origin,
5792
+ * });
5793
+ *
5794
+ * const signature = await signMessageAsync({ message });
5795
+ * const result = await billingClient.siweLogin({ message, signature });
5796
+ * ```
5797
+ */
5798
+ async siweLogin(request) {
5799
+ return loginToBillingApi({ baseUrl: this.baseUrl }, request);
5800
+ }
5801
+ /**
5802
+ * Logout from the billing API
5803
+ *
5804
+ * This destroys the current session and clears the session cookie.
5805
+ */
5806
+ async siweLogout() {
5807
+ return logoutFromBillingApi({ baseUrl: this.baseUrl });
5808
+ }
5809
+ /**
5810
+ * Get the current session status from the billing API
5811
+ *
5812
+ * @returns Session information including authentication status and address
5813
+ */
5814
+ async getSession() {
5815
+ return getBillingApiSession({ baseUrl: this.baseUrl });
5816
+ }
5817
+ /**
5818
+ * Check if there is a valid session
5819
+ *
5820
+ * @returns True if session is authenticated, false otherwise
5821
+ */
5822
+ async isSessionValid() {
5823
+ const session = await this.getSession();
5824
+ return session.authenticated;
5825
+ }
5826
+ // ==========================================================================
5827
+ // Subscription Methods
5828
+ // ==========================================================================
5626
5829
  async createSubscription(productId = "compute", options) {
5627
5830
  const endpoint = `${this.config.billingApiServerURL}/products/${productId}/subscription`;
5628
5831
  const body = options ? {
@@ -5641,10 +5844,72 @@ var BillingApiClient = class {
5641
5844
  const endpoint = `${this.config.billingApiServerURL}/products/${productId}/subscription`;
5642
5845
  await this.makeAuthenticatedRequest(endpoint, "DELETE", productId);
5643
5846
  }
5847
+ // ==========================================================================
5848
+ // Internal Methods
5849
+ // ==========================================================================
5644
5850
  /**
5645
5851
  * Make an authenticated request to the billing API
5852
+ *
5853
+ * Uses session auth if useSession is true, otherwise uses EIP-712 signature auth.
5646
5854
  */
5647
5855
  async makeAuthenticatedRequest(url, method, productId, body) {
5856
+ if (this.useSession) {
5857
+ return this.makeSessionAuthenticatedRequest(url, method, body);
5858
+ }
5859
+ return this.makeSignatureAuthenticatedRequest(url, method, productId, body);
5860
+ }
5861
+ /**
5862
+ * Make a request using session-based authentication (cookies)
5863
+ */
5864
+ async makeSessionAuthenticatedRequest(url, method, body) {
5865
+ const headers = {};
5866
+ if (body) {
5867
+ headers["Content-Type"] = "application/json";
5868
+ }
5869
+ try {
5870
+ const response = await fetch(url, {
5871
+ method,
5872
+ credentials: "include",
5873
+ // Include cookies for session management
5874
+ headers,
5875
+ body: body ? JSON.stringify(body) : void 0
5876
+ });
5877
+ const status = response.status;
5878
+ const statusText = status >= 200 && status < 300 ? "OK" : "Error";
5879
+ if (status < 200 || status >= 300) {
5880
+ let errorBody;
5881
+ try {
5882
+ errorBody = await response.text();
5883
+ } catch {
5884
+ errorBody = statusText;
5885
+ }
5886
+ throw new Error(`BillingAPI request failed: ${status} ${statusText} - ${errorBody}`);
5887
+ }
5888
+ const responseData = await response.json();
5889
+ return {
5890
+ json: async () => responseData,
5891
+ text: async () => JSON.stringify(responseData)
5892
+ };
5893
+ } catch (error) {
5894
+ if (error.name === "TypeError" || error.message?.includes("fetch")) {
5895
+ throw new Error(
5896
+ `Failed to connect to BillingAPI at ${url}: ${error.message}
5897
+ Please check:
5898
+ 1. Your internet connection
5899
+ 2. The API server is accessible: ${this.config.billingApiServerURL}
5900
+ 3. Firewall/proxy settings`
5901
+ );
5902
+ }
5903
+ throw error;
5904
+ }
5905
+ }
5906
+ /**
5907
+ * Make a request using EIP-712 signature authentication
5908
+ */
5909
+ async makeSignatureAuthenticatedRequest(url, method, productId, body) {
5910
+ if (!this.walletClient) {
5911
+ throw new Error("WalletClient is required for signature authentication");
5912
+ }
5648
5913
  const expiry = BigInt(Math.floor(Date.now() / 1e3) + 5 * 60);
5649
5914
  const { signature } = await calculateBillingAuthSignature({
5650
5915
  walletClient: this.walletClient,
@@ -7659,7 +7924,10 @@ function createBillingModule(config) {
7659
7924
  };
7660
7925
  }
7661
7926
  logger.debug(`Creating subscription for ${productId}...`);
7662
- const result = await billingApi.createSubscription(productId);
7927
+ const result = await billingApi.createSubscription(productId, {
7928
+ successUrl: opts?.successUrl,
7929
+ cancelUrl: opts?.cancelUrl
7930
+ });
7663
7931
  logger.debug(`Checkout URL: ${result.checkoutUrl}`);
7664
7932
  return {
7665
7933
  type: "checkout_created",
@@ -7751,9 +8019,22 @@ async function requestWithRetry(config) {
7751
8019
  }
7752
8020
  var BuildApiClient = class {
7753
8021
  constructor(options) {
7754
- this.baseUrl = options.baseUrl.replace(/\/+$/, "");
8022
+ let url = options.baseUrl;
8023
+ while (url.endsWith("/")) {
8024
+ url = url.slice(0, -1);
8025
+ }
8026
+ this.baseUrl = url;
7755
8027
  this.clientId = options.clientId;
7756
8028
  this.walletClient = options.walletClient;
8029
+ this.useSession = options.useSession ?? false;
8030
+ this.billingSessionId = options.billingSessionId;
8031
+ }
8032
+ /**
8033
+ * Update the billing session ID.
8034
+ * Call this after logging into the billing API to enable session-based auth for builds.
8035
+ */
8036
+ setBillingSessionId(sessionId) {
8037
+ this.billingSessionId = sessionId;
7757
8038
  }
7758
8039
  /**
7759
8040
  * Get the address of the connected wallet
@@ -7765,8 +8046,17 @@ var BuildApiClient = class {
7765
8046
  }
7766
8047
  return account.address;
7767
8048
  }
8049
+ /**
8050
+ * Submit a new build request.
8051
+ * Supports two auth modes (session auth is tried first when billingSessionId is available):
8052
+ * 1. Session-based auth: X-Billing-Session header (forwarded billing_session cookie)
8053
+ * 2. Signature-based auth: Authorization + X-Account + X-eigenx-expiry headers (requires walletClient)
8054
+ */
7768
8055
  async submitBuild(payload) {
7769
- return this.authenticatedJsonRequest("/builds", "POST", payload);
8056
+ if (this.useSession && this.billingSessionId) {
8057
+ return this.billingSessionAuthJsonRequest("/builds", "POST", payload);
8058
+ }
8059
+ return this.signatureAuthJsonRequest("/builds", "POST", payload);
7770
8060
  }
7771
8061
  async getBuild(buildId) {
7772
8062
  return this.publicJsonRequest(`/builds/${encodeURIComponent(buildId)}`);
@@ -7777,8 +8067,11 @@ var BuildApiClient = class {
7777
8067
  async verify(identifier) {
7778
8068
  return this.publicJsonRequest(`/builds/verify/${encodeURIComponent(identifier)}`);
7779
8069
  }
8070
+ /**
8071
+ * Get build logs. Supports session auth (identity verification only, no billing check).
8072
+ */
7780
8073
  async getLogs(buildId) {
7781
- return this.authenticatedTextRequest(`/builds/${encodeURIComponent(buildId)}/logs`);
8074
+ return this.sessionOrSignatureTextRequest(`/builds/${encodeURIComponent(buildId)}/logs`);
7782
8075
  }
7783
8076
  async listBuilds(params) {
7784
8077
  const res = await requestWithRetry({
@@ -7786,7 +8079,9 @@ var BuildApiClient = class {
7786
8079
  method: "GET",
7787
8080
  params,
7788
8081
  headers: this.clientId ? { "x-client-id": this.clientId } : void 0,
7789
- timeout: 6e4
8082
+ timeout: 6e4,
8083
+ validateStatus: () => true,
8084
+ withCredentials: this.useSession
7790
8085
  });
7791
8086
  if (res.status < 200 || res.status >= 300) throw buildApiHttpError(res);
7792
8087
  return res.data;
@@ -7796,12 +8091,18 @@ var BuildApiClient = class {
7796
8091
  url: `${this.baseUrl}${path8}`,
7797
8092
  method: "GET",
7798
8093
  headers: this.clientId ? { "x-client-id": this.clientId } : void 0,
7799
- timeout: 6e4
8094
+ timeout: 6e4,
8095
+ validateStatus: () => true,
8096
+ withCredentials: this.useSession
7800
8097
  });
7801
8098
  if (res.status < 200 || res.status >= 300) throw buildApiHttpError(res);
7802
8099
  return res.data;
7803
8100
  }
7804
- async authenticatedJsonRequest(path8, method, body) {
8101
+ /**
8102
+ * Make a request that ALWAYS requires signature auth (for billing verification).
8103
+ * Used for endpoints like POST /builds that need to verify subscription status.
8104
+ */
8105
+ async signatureAuthJsonRequest(path8, method, body) {
7805
8106
  if (!this.walletClient?.account) {
7806
8107
  throw new Error("WalletClient with account required for authenticated requests");
7807
8108
  }
@@ -7823,32 +8124,69 @@ var BuildApiClient = class {
7823
8124
  method,
7824
8125
  headers,
7825
8126
  data: body,
7826
- timeout: 6e4
8127
+ timeout: 6e4,
8128
+ validateStatus: () => true,
8129
+ withCredentials: this.useSession
7827
8130
  });
7828
8131
  if (res.status < 200 || res.status >= 300) throw buildApiHttpError(res);
7829
8132
  return res.data;
7830
8133
  }
7831
- async authenticatedTextRequest(path8) {
7832
- if (!this.walletClient?.account) {
7833
- throw new Error("WalletClient with account required for authenticated requests");
8134
+ /**
8135
+ * Make a request using billing session auth (for billing verification without wallet signature).
8136
+ * Forwards the billing_session cookie value via X-Billing-Session header.
8137
+ * Used for endpoints that need to verify subscription status when using session-based auth.
8138
+ */
8139
+ async billingSessionAuthJsonRequest(path8, method, body) {
8140
+ if (!this.billingSessionId) {
8141
+ throw new Error("billingSessionId required for session-based billing auth");
7834
8142
  }
7835
- const headers = {};
8143
+ const headers = {
8144
+ "Content-Type": "application/json",
8145
+ "X-Billing-Session": this.billingSessionId
8146
+ };
7836
8147
  if (this.clientId) headers["x-client-id"] = this.clientId;
7837
- const expiry = BigInt(Math.floor(Date.now() / 1e3) + 60);
7838
- const { signature } = await calculateBillingAuthSignature({
7839
- walletClient: this.walletClient,
7840
- product: "compute",
7841
- expiry
8148
+ const res = await requestWithRetry({
8149
+ url: `${this.baseUrl}${path8}`,
8150
+ method,
8151
+ headers,
8152
+ data: body,
8153
+ timeout: 6e4,
8154
+ validateStatus: () => true,
8155
+ withCredentials: this.useSession
7842
8156
  });
7843
- headers.Authorization = `Bearer ${signature}`;
7844
- headers["X-eigenx-expiry"] = expiry.toString();
7845
- headers["X-Account"] = this.address;
8157
+ if (res.status < 200 || res.status >= 300) throw buildApiHttpError(res);
8158
+ return res.data;
8159
+ }
8160
+ /**
8161
+ * Make an authenticated request that can use session OR signature auth.
8162
+ * When useSession is true, relies on cookies for identity verification.
8163
+ * Used for endpoints that only need identity verification (not billing).
8164
+ */
8165
+ async sessionOrSignatureTextRequest(path8) {
8166
+ const headers = {};
8167
+ if (this.clientId) headers["x-client-id"] = this.clientId;
8168
+ if (!this.useSession) {
8169
+ if (!this.walletClient?.account) {
8170
+ throw new Error("WalletClient with account required for authenticated requests");
8171
+ }
8172
+ const expiry = BigInt(Math.floor(Date.now() / 1e3) + 60);
8173
+ const { signature } = await calculateBillingAuthSignature({
8174
+ walletClient: this.walletClient,
8175
+ product: "compute",
8176
+ expiry
8177
+ });
8178
+ headers.Authorization = `Bearer ${signature}`;
8179
+ headers["X-eigenx-expiry"] = expiry.toString();
8180
+ headers["X-Account"] = this.address;
8181
+ }
7846
8182
  const res = await requestWithRetry({
7847
8183
  url: `${this.baseUrl}${path8}`,
7848
8184
  method: "GET",
7849
8185
  headers,
7850
8186
  timeout: 6e4,
7851
- responseType: "text"
8187
+ responseType: "text",
8188
+ validateStatus: () => true,
8189
+ withCredentials: this.useSession
7852
8190
  });
7853
8191
  if (res.status < 200 || res.status >= 300) throw buildApiHttpError(res);
7854
8192
  return typeof res.data === "string" ? res.data : JSON.stringify(res.data);
@@ -8415,6 +8753,9 @@ function isSiweMessageNotYetValid(params) {
8415
8753
  return /* @__PURE__ */ new Date() < params.notBefore;
8416
8754
  }
8417
8755
 
8756
+ // src/client/common/auth/index.ts
8757
+ init_session();
8758
+
8418
8759
  // src/client/common/utils/instance.ts
8419
8760
  async function getCurrentInstanceType(preflightCtx, appID, logger, clientId) {
8420
8761
  try {