netsuite-sdk 0.1.2 → 0.1.3

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.js CHANGED
@@ -1,839 +1,2083 @@
1
1
  'use strict';
2
2
 
3
- var axios = require('axios');
4
- var http = require('http');
5
- var https = require('https');
6
- var OAuth = require('oauth-1.0a');
7
3
  var crypto = require('crypto');
8
4
 
9
- function _interopDefault (e) { return e && e.__esModule ? e : { default: e }; }
10
-
11
- var axios__default = /*#__PURE__*/_interopDefault(axios);
12
- var http__default = /*#__PURE__*/_interopDefault(http);
13
- var https__default = /*#__PURE__*/_interopDefault(https);
14
- var OAuth__default = /*#__PURE__*/_interopDefault(OAuth);
15
-
16
- // src/transport/http-transport.ts
17
- function createOAuthSigner(config) {
18
- const oauth = new OAuth__default.default({
19
- consumer: { key: config.consumerKey, secret: config.consumerSecret },
20
- signature_method: "HMAC-SHA256",
21
- hash_function: (baseString, key) => crypto.createHmac("sha256", key).update(baseString).digest("base64"),
22
- realm: config.realm
23
- });
24
- const token = { key: config.tokenKey, secret: config.tokenSecret };
25
- return (url, method) => {
26
- const requestData = { url, method };
27
- const authorization = oauth.authorize(requestData, token);
28
- return oauth.toHeader(authorization);
29
- };
30
- }
31
-
32
- // src/types/errors.ts
33
- var NetSuiteError = class _NetSuiteError extends Error {
34
- status;
35
- code;
36
- details;
37
- requestUrl;
38
- requestMethod;
39
- constructor(message, status, code, details, requestUrl, requestMethod) {
40
- super(message);
41
- this.name = "NetSuiteError";
42
- this.status = status;
43
- this.code = code;
44
- this.details = details;
45
- this.requestUrl = requestUrl;
46
- this.requestMethod = requestMethod;
47
- if (Error.captureStackTrace) {
48
- Error.captureStackTrace(this, _NetSuiteError);
49
- }
50
- }
51
- /** Whether this is a retryable error (5xx, timeout, network) */
52
- get isRetryable() {
53
- return this.status >= 500 || this.code === "TIMEOUT" || this.code === "NETWORK_ERROR";
54
- }
55
- /** Whether this is an auth error (401, 403) */
56
- get isAuthError() {
57
- return this.status === 401 || this.status === 403;
58
- }
59
- static isNetSuiteError(error) {
60
- return error instanceof _NetSuiteError;
5
+ var __create = Object.create;
6
+ var __defProp = Object.defineProperty;
7
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
8
+ var __getOwnPropNames = Object.getOwnPropertyNames;
9
+ var __getProtoOf = Object.getPrototypeOf;
10
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
11
+ var __require = /* @__PURE__ */ ((x) => typeof require !== "undefined" ? require : typeof Proxy !== "undefined" ? new Proxy(x, {
12
+ get: (a, b) => (typeof require !== "undefined" ? require : a)[b]
13
+ }) : x)(function(x) {
14
+ if (typeof require !== "undefined") return require.apply(this, arguments);
15
+ throw Error('Dynamic require of "' + x + '" is not supported');
16
+ });
17
+ var __commonJS = (cb, mod) => function __require2() {
18
+ return mod || (0, cb[__getOwnPropNames(cb)[0]])((mod = { exports: {} }).exports, mod), mod.exports;
19
+ };
20
+ var __copyProps = (to, from, except, desc) => {
21
+ if (from && typeof from === "object" || typeof from === "function") {
22
+ for (let key of __getOwnPropNames(from))
23
+ if (!__hasOwnProp.call(to, key) && key !== except)
24
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
61
25
  }
26
+ return to;
62
27
  };
28
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
29
+ // If the importer is in node compatibility mode or this is not an ESM
30
+ // file that has been converted to a CommonJS file using a Babel-
31
+ // compatible transform (i.e. "__esModule" has not been set), then set
32
+ // "default" to the CommonJS "module.exports" for node compatibility.
33
+ !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
34
+ mod
35
+ ));
63
36
 
64
- // src/transport/retry.ts
65
- var DEFAULT_RETRY_CONFIG = {
66
- maxRetries: 3,
67
- initialDelay: 1e3,
68
- maxDelay: 3e4,
69
- backoffFactor: 2,
70
- shouldRetry: (error) => {
71
- if (error instanceof NetSuiteError) {
72
- return error.isRetryable;
37
+ // src/transport/oauth.js
38
+ var require_oauth = __commonJS({
39
+ "src/transport/oauth.js"(exports$1) {
40
+ Object.defineProperty(exports$1, "__esModule", { value: true });
41
+ exports$1.createOAuthSigner = createOAuthSigner;
42
+ var oauth_1_0a_1 = __require("oauth-1.0a");
43
+ var node_crypto_1 = __require("crypto");
44
+ function createOAuthSigner(config) {
45
+ var oauth = new oauth_1_0a_1.default({
46
+ consumer: { key: config.consumerKey, secret: config.consumerSecret },
47
+ signature_method: "HMAC-SHA256",
48
+ hash_function: function(baseString, key) {
49
+ return (0, node_crypto_1.createHmac)("sha256", key).update(baseString).digest("base64");
50
+ },
51
+ realm: config.realm
52
+ });
53
+ var token = { key: config.tokenKey, secret: config.tokenSecret };
54
+ return function(url, method) {
55
+ var requestData = { url, method };
56
+ var authorization = oauth.authorize(requestData, token);
57
+ return oauth.toHeader(authorization);
58
+ };
73
59
  }
74
- return true;
75
60
  }
76
- };
77
- async function withRetry(fn, config = {}) {
78
- const opts = { ...DEFAULT_RETRY_CONFIG, ...config };
79
- for (let attempt = 0; attempt <= opts.maxRetries; attempt++) {
80
- try {
81
- return await fn();
82
- } catch (error) {
83
- const isLastAttempt = attempt === opts.maxRetries;
84
- if (isLastAttempt || !opts.shouldRetry(error, attempt)) {
85
- throw error;
86
- }
87
- opts.onRetry?.(error, attempt + 1);
88
- const delay = Math.min(
89
- opts.initialDelay * Math.pow(opts.backoffFactor, attempt),
90
- opts.maxDelay
91
- );
92
- const jitter = delay * 0.25 * (Math.random() * 2 - 1);
93
- await new Promise((resolve) => setTimeout(resolve, delay + jitter));
61
+ });
62
+
63
+ // src/types/errors.js
64
+ var require_errors = __commonJS({
65
+ "src/types/errors.js"(exports$1) {
66
+ var __extends = exports$1 && exports$1.__extends || /* @__PURE__ */ (function() {
67
+ var extendStatics = function(d, b) {
68
+ extendStatics = Object.setPrototypeOf || { __proto__: [] } instanceof Array && function(d2, b2) {
69
+ d2.__proto__ = b2;
70
+ } || function(d2, b2) {
71
+ for (var p in b2) if (Object.prototype.hasOwnProperty.call(b2, p)) d2[p] = b2[p];
72
+ };
73
+ return extendStatics(d, b);
74
+ };
75
+ return function(d, b) {
76
+ if (typeof b !== "function" && b !== null)
77
+ throw new TypeError("Class extends value " + String(b) + " is not a constructor or null");
78
+ extendStatics(d, b);
79
+ function __() {
80
+ this.constructor = d;
81
+ }
82
+ d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
83
+ };
84
+ })();
85
+ Object.defineProperty(exports$1, "__esModule", { value: true });
86
+ exports$1.NetSuiteError = void 0;
87
+ var NetSuiteError2 = (
88
+ /** @class */
89
+ (function(_super) {
90
+ __extends(NetSuiteError3, _super);
91
+ function NetSuiteError3(message, status, code, details, requestUrl, requestMethod) {
92
+ var _this = _super.call(this, message) || this;
93
+ _this.name = "NetSuiteError";
94
+ _this.status = status;
95
+ _this.code = code;
96
+ _this.details = details;
97
+ _this.requestUrl = requestUrl;
98
+ _this.requestMethod = requestMethod;
99
+ if (Error.captureStackTrace) {
100
+ Error.captureStackTrace(_this, NetSuiteError3);
101
+ }
102
+ return _this;
103
+ }
104
+ Object.defineProperty(NetSuiteError3.prototype, "isRetryable", {
105
+ /** Whether this is a retryable error (5xx, timeout, network) */
106
+ get: function() {
107
+ return this.status >= 500 || this.code === "TIMEOUT" || this.code === "NETWORK_ERROR";
108
+ },
109
+ enumerable: false,
110
+ configurable: true
111
+ });
112
+ Object.defineProperty(NetSuiteError3.prototype, "isAuthError", {
113
+ /** Whether this is an auth error (401, 403) */
114
+ get: function() {
115
+ return this.status === 401 || this.status === 403;
116
+ },
117
+ enumerable: false,
118
+ configurable: true
119
+ });
120
+ NetSuiteError3.isNetSuiteError = function(error) {
121
+ return error instanceof NetSuiteError3;
122
+ };
123
+ return NetSuiteError3;
124
+ })(Error)
125
+ );
126
+ exports$1.NetSuiteError = NetSuiteError2;
127
+ }
128
+ });
129
+
130
+ // src/transport/retry.js
131
+ var require_retry = __commonJS({
132
+ "src/transport/retry.js"(exports$1) {
133
+ var __assign = exports$1 && exports$1.__assign || function() {
134
+ __assign = Object.assign || function(t) {
135
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
136
+ s = arguments[i];
137
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
138
+ t[p] = s[p];
139
+ }
140
+ return t;
141
+ };
142
+ return __assign.apply(this, arguments);
143
+ };
144
+ var __awaiter = exports$1 && exports$1.__awaiter || function(thisArg, _arguments, P, generator) {
145
+ function adopt(value) {
146
+ return value instanceof P ? value : new P(function(resolve) {
147
+ resolve(value);
148
+ });
149
+ }
150
+ return new (P || (P = Promise))(function(resolve, reject) {
151
+ function fulfilled(value) {
152
+ try {
153
+ step(generator.next(value));
154
+ } catch (e) {
155
+ reject(e);
156
+ }
157
+ }
158
+ function rejected(value) {
159
+ try {
160
+ step(generator["throw"](value));
161
+ } catch (e) {
162
+ reject(e);
163
+ }
164
+ }
165
+ function step(result) {
166
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
167
+ }
168
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
169
+ });
170
+ };
171
+ var __generator = exports$1 && exports$1.__generator || function(thisArg, body) {
172
+ var _ = { label: 0, sent: function() {
173
+ if (t[0] & 1) throw t[1];
174
+ return t[1];
175
+ }, trys: [], ops: [] }, f, y, t, g;
176
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() {
177
+ return this;
178
+ }), g;
179
+ function verb(n) {
180
+ return function(v) {
181
+ return step([n, v]);
182
+ };
183
+ }
184
+ function step(op) {
185
+ if (f) throw new TypeError("Generator is already executing.");
186
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
187
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
188
+ if (y = 0, t) op = [op[0] & 2, t.value];
189
+ switch (op[0]) {
190
+ case 0:
191
+ case 1:
192
+ t = op;
193
+ break;
194
+ case 4:
195
+ _.label++;
196
+ return { value: op[1], done: false };
197
+ case 5:
198
+ _.label++;
199
+ y = op[1];
200
+ op = [0];
201
+ continue;
202
+ case 7:
203
+ op = _.ops.pop();
204
+ _.trys.pop();
205
+ continue;
206
+ default:
207
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) {
208
+ _ = 0;
209
+ continue;
210
+ }
211
+ if (op[0] === 3 && (!t || op[1] > t[0] && op[1] < t[3])) {
212
+ _.label = op[1];
213
+ break;
214
+ }
215
+ if (op[0] === 6 && _.label < t[1]) {
216
+ _.label = t[1];
217
+ t = op;
218
+ break;
219
+ }
220
+ if (t && _.label < t[2]) {
221
+ _.label = t[2];
222
+ _.ops.push(op);
223
+ break;
224
+ }
225
+ if (t[2]) _.ops.pop();
226
+ _.trys.pop();
227
+ continue;
228
+ }
229
+ op = body.call(thisArg, _);
230
+ } catch (e) {
231
+ op = [6, e];
232
+ y = 0;
233
+ } finally {
234
+ f = t = 0;
235
+ }
236
+ if (op[0] & 5) throw op[1];
237
+ return { value: op[0] ? op[1] : void 0, done: true };
238
+ }
239
+ };
240
+ Object.defineProperty(exports$1, "__esModule", { value: true });
241
+ exports$1.withRetry = withRetry;
242
+ var errors_js_1 = require_errors();
243
+ var DEFAULT_RETRY_CONFIG = {
244
+ maxRetries: 3,
245
+ initialDelay: 1e3,
246
+ maxDelay: 3e4,
247
+ backoffFactor: 2,
248
+ shouldRetry: function(error) {
249
+ if (error instanceof errors_js_1.NetSuiteError) {
250
+ return error.isRetryable;
251
+ }
252
+ return true;
253
+ }
254
+ };
255
+ function withRetry(fn_1) {
256
+ return __awaiter(this, arguments, void 0, function(fn, config) {
257
+ var opts, _loop_1, attempt, state_1;
258
+ var _a;
259
+ if (config === void 0) {
260
+ config = {};
261
+ }
262
+ return __generator(this, function(_b) {
263
+ switch (_b.label) {
264
+ case 0:
265
+ opts = __assign(__assign({}, DEFAULT_RETRY_CONFIG), config);
266
+ _loop_1 = function(attempt2) {
267
+ var _c, error_1, isLastAttempt, delay_1, jitter_1;
268
+ return __generator(this, function(_d) {
269
+ switch (_d.label) {
270
+ case 0:
271
+ _d.trys.push([0, 2, , 4]);
272
+ _c = {};
273
+ return [4, fn()];
274
+ case 1:
275
+ return [2, (_c.value = _d.sent(), _c)];
276
+ case 2:
277
+ error_1 = _d.sent();
278
+ isLastAttempt = attempt2 === opts.maxRetries;
279
+ if (isLastAttempt || !opts.shouldRetry(error_1, attempt2)) {
280
+ throw error_1;
281
+ }
282
+ (_a = opts.onRetry) === null || _a === void 0 ? void 0 : _a.call(opts, error_1, attempt2 + 1);
283
+ delay_1 = Math.min(opts.initialDelay * Math.pow(opts.backoffFactor, attempt2), opts.maxDelay);
284
+ jitter_1 = delay_1 * 0.25 * (Math.random() * 2 - 1);
285
+ return [4, new Promise(function(resolve) {
286
+ return setTimeout(resolve, delay_1 + jitter_1);
287
+ })];
288
+ case 3:
289
+ _d.sent();
290
+ return [3, 4];
291
+ case 4:
292
+ return [
293
+ 2
294
+ /*return*/
295
+ ];
296
+ }
297
+ });
298
+ };
299
+ attempt = 0;
300
+ _b.label = 1;
301
+ case 1:
302
+ if (!(attempt <= opts.maxRetries)) return [3, 4];
303
+ return [5, _loop_1(attempt)];
304
+ case 2:
305
+ state_1 = _b.sent();
306
+ if (typeof state_1 === "object")
307
+ return [2, state_1.value];
308
+ _b.label = 3;
309
+ case 3:
310
+ attempt++;
311
+ return [3, 1];
312
+ case 4:
313
+ throw new Error("Retry loop exited unexpectedly");
314
+ }
315
+ });
316
+ });
94
317
  }
95
318
  }
96
- throw new Error("Retry loop exited unexpectedly");
97
- }
319
+ });
98
320
 
99
- // src/transport/middleware-chain.ts
100
- function executeMiddlewareChain(middlewares, context, finalHandler) {
101
- let index = 0;
102
- function next() {
103
- if (index >= middlewares.length) {
104
- return finalHandler();
321
+ // src/transport/middleware-chain.js
322
+ var require_middleware_chain = __commonJS({
323
+ "src/transport/middleware-chain.js"(exports$1) {
324
+ Object.defineProperty(exports$1, "__esModule", { value: true });
325
+ exports$1.executeMiddlewareChain = executeMiddlewareChain;
326
+ function executeMiddlewareChain(middlewares, context, finalHandler) {
327
+ var index = 0;
328
+ function next() {
329
+ if (index >= middlewares.length) {
330
+ return finalHandler();
331
+ }
332
+ var middleware = middlewares[index++];
333
+ return middleware(context, next);
334
+ }
335
+ return next();
105
336
  }
106
- const middleware = middlewares[index++];
107
- return middleware(context, next);
108
337
  }
109
- return next();
110
- }
338
+ });
111
339
 
112
- // src/types/http.ts
113
- function extractHeaders(response) {
114
- const headers = {};
115
- if (response.headers) {
116
- for (const [key, value] of Object.entries(response.headers)) {
117
- if (typeof value === "string") {
118
- headers[key] = value;
340
+ // src/types/http.js
341
+ var require_http = __commonJS({
342
+ "src/types/http.js"(exports$1) {
343
+ Object.defineProperty(exports$1, "__esModule", { value: true });
344
+ exports$1.extractHeaders = extractHeaders;
345
+ function extractHeaders(response) {
346
+ var headers = {};
347
+ if (response.headers) {
348
+ for (var _i = 0, _a = Object.entries(response.headers); _i < _a.length; _i++) {
349
+ var _b = _a[_i], key = _b[0], value = _b[1];
350
+ if (typeof value === "string") {
351
+ headers[key] = value;
352
+ }
353
+ }
119
354
  }
355
+ return headers;
120
356
  }
121
357
  }
122
- return headers;
123
- }
358
+ });
124
359
 
125
- // src/transport/http-transport.ts
126
- var HttpTransport = class {
127
- sign;
128
- axiosInstance;
129
- middlewares = [];
130
- config;
131
- constructor(config) {
132
- this.config = {
133
- timeout: config.timeout ?? 3e4,
134
- maxRetries: config.maxRetries ?? 3,
135
- retryDelay: config.retryDelay ?? 1e3,
136
- defaultHeaders: config.defaultHeaders ?? {},
137
- logger: config.logger
360
+ // src/transport/http-transport.js
361
+ var require_http_transport = __commonJS({
362
+ "src/transport/http-transport.js"(exports$1) {
363
+ var __assign = exports$1 && exports$1.__assign || function() {
364
+ __assign = Object.assign || function(t) {
365
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
366
+ s = arguments[i];
367
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
368
+ t[p] = s[p];
369
+ }
370
+ return t;
371
+ };
372
+ return __assign.apply(this, arguments);
138
373
  };
139
- this.sign = createOAuthSigner(config.auth);
140
- this.axiosInstance = axios__default.default.create({
141
- timeout: this.config.timeout,
142
- headers: {
143
- "Content-Type": "application/json",
144
- "Accept-Encoding": "gzip, deflate"
145
- },
146
- httpAgent: new http__default.default.Agent({ keepAlive: true }),
147
- httpsAgent: new https__default.default.Agent({ keepAlive: true }),
148
- maxRedirects: 5,
149
- // Let us handle all status codes in our error handling
150
- validateStatus: () => true
151
- });
152
- }
153
- /** Add a middleware to the chain. Returns `this` for chaining. */
154
- use(middleware) {
155
- this.middlewares.push(middleware);
156
- return this;
157
- }
158
- /** Execute an HTTP request with OAuth signing, retry, and middleware. */
159
- async request(url, options = {}) {
160
- const method = options.method ?? "GET";
161
- const timeout = options.timeout ?? this.config.timeout;
162
- const maxRetries = options.maxRetries ?? this.config.maxRetries;
163
- return withRetry(
164
- async () => {
165
- const authHeaders = this.sign(url, method);
166
- const headers = {
167
- "Content-Type": "application/json",
168
- ...this.config.defaultHeaders,
169
- ...authHeaders,
170
- ...options.headers
171
- };
172
- const context = {
173
- url,
174
- method,
175
- headers,
176
- body: options.body,
177
- metadata: {}
178
- };
179
- const response = await executeMiddlewareChain(
180
- this.middlewares,
181
- context,
182
- () => this.executeRequest(context, timeout)
183
- );
184
- return {
185
- data: response.body,
186
- status: response.status,
187
- headers: response.headers,
188
- duration: response.duration
374
+ var __awaiter = exports$1 && exports$1.__awaiter || function(thisArg, _arguments, P, generator) {
375
+ function adopt(value) {
376
+ return value instanceof P ? value : new P(function(resolve) {
377
+ resolve(value);
378
+ });
379
+ }
380
+ return new (P || (P = Promise))(function(resolve, reject) {
381
+ function fulfilled(value) {
382
+ try {
383
+ step(generator.next(value));
384
+ } catch (e) {
385
+ reject(e);
386
+ }
387
+ }
388
+ function rejected(value) {
389
+ try {
390
+ step(generator["throw"](value));
391
+ } catch (e) {
392
+ reject(e);
393
+ }
394
+ }
395
+ function step(result) {
396
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
397
+ }
398
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
399
+ });
400
+ };
401
+ var __generator = exports$1 && exports$1.__generator || function(thisArg, body) {
402
+ var _ = { label: 0, sent: function() {
403
+ if (t[0] & 1) throw t[1];
404
+ return t[1];
405
+ }, trys: [], ops: [] }, f, y, t, g;
406
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() {
407
+ return this;
408
+ }), g;
409
+ function verb(n) {
410
+ return function(v) {
411
+ return step([n, v]);
189
412
  };
190
- },
191
- {
192
- maxRetries,
193
- initialDelay: this.config.retryDelay,
194
- shouldRetry: (error) => {
195
- if (error instanceof NetSuiteError) {
196
- return error.isRetryable;
197
- }
198
- return true;
199
- },
200
- onRetry: (error, attempt) => {
201
- this.config.logger?.warn(`Retry attempt ${attempt}/${maxRetries}`, {
202
- url,
203
- method,
204
- error
205
- });
413
+ }
414
+ function step(op) {
415
+ if (f) throw new TypeError("Generator is already executing.");
416
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
417
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
418
+ if (y = 0, t) op = [op[0] & 2, t.value];
419
+ switch (op[0]) {
420
+ case 0:
421
+ case 1:
422
+ t = op;
423
+ break;
424
+ case 4:
425
+ _.label++;
426
+ return { value: op[1], done: false };
427
+ case 5:
428
+ _.label++;
429
+ y = op[1];
430
+ op = [0];
431
+ continue;
432
+ case 7:
433
+ op = _.ops.pop();
434
+ _.trys.pop();
435
+ continue;
436
+ default:
437
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) {
438
+ _ = 0;
439
+ continue;
440
+ }
441
+ if (op[0] === 3 && (!t || op[1] > t[0] && op[1] < t[3])) {
442
+ _.label = op[1];
443
+ break;
444
+ }
445
+ if (op[0] === 6 && _.label < t[1]) {
446
+ _.label = t[1];
447
+ t = op;
448
+ break;
449
+ }
450
+ if (t && _.label < t[2]) {
451
+ _.label = t[2];
452
+ _.ops.push(op);
453
+ break;
454
+ }
455
+ if (t[2]) _.ops.pop();
456
+ _.trys.pop();
457
+ continue;
458
+ }
459
+ op = body.call(thisArg, _);
460
+ } catch (e) {
461
+ op = [6, e];
462
+ y = 0;
463
+ } finally {
464
+ f = t = 0;
206
465
  }
466
+ if (op[0] & 5) throw op[1];
467
+ return { value: op[0] ? op[1] : void 0, done: true };
207
468
  }
469
+ };
470
+ Object.defineProperty(exports$1, "__esModule", { value: true });
471
+ exports$1.HttpTransport = void 0;
472
+ var axios_1 = __require("axios");
473
+ var node_http_1 = __require("http");
474
+ var node_https_1 = __require("https");
475
+ var oauth_js_1 = require_oauth();
476
+ var retry_js_1 = require_retry();
477
+ var middleware_chain_js_1 = require_middleware_chain();
478
+ var errors_js_1 = require_errors();
479
+ var http_js_1 = require_http();
480
+ var HttpTransport = (
481
+ /** @class */
482
+ (function() {
483
+ function HttpTransport2(config) {
484
+ var _a, _b, _c, _d;
485
+ this.middlewares = [];
486
+ this.config = {
487
+ timeout: (_a = config.timeout) !== null && _a !== void 0 ? _a : 3e4,
488
+ maxRetries: (_b = config.maxRetries) !== null && _b !== void 0 ? _b : 3,
489
+ retryDelay: (_c = config.retryDelay) !== null && _c !== void 0 ? _c : 1e3,
490
+ defaultHeaders: (_d = config.defaultHeaders) !== null && _d !== void 0 ? _d : {},
491
+ logger: config.logger
492
+ };
493
+ this.sign = (0, oauth_js_1.createOAuthSigner)(config.auth);
494
+ this.axiosInstance = axios_1.default.create({
495
+ timeout: this.config.timeout,
496
+ headers: {
497
+ "Content-Type": "application/json",
498
+ "Accept-Encoding": "gzip, deflate"
499
+ },
500
+ httpAgent: new node_http_1.default.Agent({ keepAlive: true }),
501
+ httpsAgent: new node_https_1.default.Agent({ keepAlive: true }),
502
+ maxRedirects: 5,
503
+ // Let us handle all status codes in our error handling
504
+ validateStatus: function() {
505
+ return true;
506
+ }
507
+ });
508
+ }
509
+ HttpTransport2.prototype.use = function(middleware) {
510
+ this.middlewares.push(middleware);
511
+ return this;
512
+ };
513
+ HttpTransport2.prototype.request = function(url_1) {
514
+ return __awaiter(this, arguments, void 0, function(url, options) {
515
+ var method, timeout, maxRetries;
516
+ var _this = this;
517
+ var _a, _b, _c;
518
+ if (options === void 0) {
519
+ options = {};
520
+ }
521
+ return __generator(this, function(_d) {
522
+ method = (_a = options.method) !== null && _a !== void 0 ? _a : "GET";
523
+ timeout = (_b = options.timeout) !== null && _b !== void 0 ? _b : this.config.timeout;
524
+ maxRetries = (_c = options.maxRetries) !== null && _c !== void 0 ? _c : this.config.maxRetries;
525
+ return [2, (0, retry_js_1.withRetry)(function() {
526
+ return __awaiter(_this, void 0, void 0, function() {
527
+ var authHeaders, headers, context, response;
528
+ var _this2 = this;
529
+ return __generator(this, function(_a2) {
530
+ switch (_a2.label) {
531
+ case 0:
532
+ authHeaders = this.sign(url, method);
533
+ headers = __assign(__assign(__assign({ "Content-Type": "application/json" }, this.config.defaultHeaders), authHeaders), options.headers);
534
+ context = {
535
+ url,
536
+ method,
537
+ headers,
538
+ body: options.body,
539
+ metadata: {}
540
+ };
541
+ return [4, (0, middleware_chain_js_1.executeMiddlewareChain)(this.middlewares, context, function() {
542
+ return _this2.executeRequest(context, timeout);
543
+ })];
544
+ case 1:
545
+ response = _a2.sent();
546
+ return [2, {
547
+ data: response.body,
548
+ status: response.status,
549
+ headers: response.headers,
550
+ duration: response.duration
551
+ }];
552
+ }
553
+ });
554
+ });
555
+ }, {
556
+ maxRetries,
557
+ initialDelay: this.config.retryDelay,
558
+ shouldRetry: function(error) {
559
+ if (error instanceof errors_js_1.NetSuiteError) {
560
+ return error.isRetryable;
561
+ }
562
+ return true;
563
+ },
564
+ onRetry: function(error, attempt) {
565
+ var _a2;
566
+ (_a2 = _this.config.logger) === null || _a2 === void 0 ? void 0 : _a2.warn("Retry attempt ".concat(attempt, "/").concat(maxRetries), {
567
+ url,
568
+ method,
569
+ error
570
+ });
571
+ }
572
+ })];
573
+ });
574
+ });
575
+ };
576
+ HttpTransport2.prototype.executeRequest = function(context, timeout) {
577
+ return __awaiter(this, void 0, void 0, function() {
578
+ var startTime, response, duration, errorBody, message, code, error_1, duration, axiosError;
579
+ var _a, _b, _c, _d, _e, _f, _g, _h;
580
+ return __generator(this, function(_j) {
581
+ switch (_j.label) {
582
+ case 0:
583
+ startTime = performance.now();
584
+ _j.label = 1;
585
+ case 1:
586
+ _j.trys.push([1, 3, , 4]);
587
+ (_a = this.config.logger) === null || _a === void 0 ? void 0 : _a.debug("".concat(context.method, " ").concat(context.url), {
588
+ headers: Object.keys(context.headers)
589
+ });
590
+ return [4, this.axiosInstance.request({
591
+ url: context.url,
592
+ method: context.method,
593
+ headers: context.headers,
594
+ data: context.body && ["POST", "PUT", "PATCH"].includes(context.method) ? context.body : void 0,
595
+ timeout
596
+ })];
597
+ case 2:
598
+ response = _j.sent();
599
+ duration = Math.round(performance.now() - startTime);
600
+ (_b = this.config.logger) === null || _b === void 0 ? void 0 : _b.info("".concat(context.method, " ").concat(context.url, " \u2192 ").concat(response.status), {
601
+ duration
602
+ });
603
+ if (response.status >= 400) {
604
+ errorBody = (_c = response.data) !== null && _c !== void 0 ? _c : {};
605
+ message = (_f = (_e = (_d = errorBody.detail) !== null && _d !== void 0 ? _d : errorBody.title) !== null && _e !== void 0 ? _e : errorBody.message) !== null && _f !== void 0 ? _f : "HTTP ".concat(response.status);
606
+ code = (_h = (_g = errorBody["o:errorCode"]) !== null && _g !== void 0 ? _g : errorBody.code) !== null && _h !== void 0 ? _h : "HTTP_".concat(response.status);
607
+ throw new errors_js_1.NetSuiteError(message, response.status, code, errorBody, context.url, context.method);
608
+ }
609
+ return [2, {
610
+ status: response.status,
611
+ headers: (0, http_js_1.extractHeaders)(response),
612
+ body: response.status === 204 ? void 0 : response.data,
613
+ duration
614
+ }];
615
+ case 3:
616
+ error_1 = _j.sent();
617
+ if (error_1 instanceof errors_js_1.NetSuiteError) {
618
+ throw error_1;
619
+ }
620
+ duration = Math.round(performance.now() - startTime);
621
+ axiosError = error_1;
622
+ if (axiosError.code === "ECONNABORTED" || axiosError.code === "ERR_CANCELED") {
623
+ throw new errors_js_1.NetSuiteError("Request timed out after ".concat(timeout, "ms"), 504, "TIMEOUT", void 0, context.url, context.method);
624
+ }
625
+ throw new errors_js_1.NetSuiteError(axiosError.message || "Network error", 0, "NETWORK_ERROR", void 0, context.url, context.method);
626
+ case 4:
627
+ return [
628
+ 2
629
+ /*return*/
630
+ ];
631
+ }
632
+ });
633
+ });
634
+ };
635
+ return HttpTransport2;
636
+ })()
208
637
  );
638
+ exports$1.HttpTransport = HttpTransport;
209
639
  }
210
- async executeRequest(context, timeout) {
211
- const startTime = performance.now();
212
- try {
213
- this.config.logger?.debug(`${context.method} ${context.url}`, {
214
- headers: Object.keys(context.headers)
215
- });
216
- const response = await this.axiosInstance.request({
217
- url: context.url,
218
- method: context.method,
219
- headers: context.headers,
220
- data: context.body && ["POST", "PUT", "PATCH"].includes(context.method) ? context.body : void 0,
221
- timeout
222
- });
223
- const duration = Math.round(performance.now() - startTime);
224
- this.config.logger?.info(`${context.method} ${context.url} \u2192 ${response.status}`, {
225
- duration
640
+ });
641
+
642
+ // src/suiteql/suiteql-client.js
643
+ var require_suiteql_client = __commonJS({
644
+ "src/suiteql/suiteql-client.js"(exports$1) {
645
+ var __assign = exports$1 && exports$1.__assign || function() {
646
+ __assign = Object.assign || function(t) {
647
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
648
+ s = arguments[i];
649
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
650
+ t[p] = s[p];
651
+ }
652
+ return t;
653
+ };
654
+ return __assign.apply(this, arguments);
655
+ };
656
+ var __awaiter = exports$1 && exports$1.__awaiter || function(thisArg, _arguments, P, generator) {
657
+ function adopt(value) {
658
+ return value instanceof P ? value : new P(function(resolve) {
659
+ resolve(value);
660
+ });
661
+ }
662
+ return new (P || (P = Promise))(function(resolve, reject) {
663
+ function fulfilled(value) {
664
+ try {
665
+ step(generator.next(value));
666
+ } catch (e) {
667
+ reject(e);
668
+ }
669
+ }
670
+ function rejected(value) {
671
+ try {
672
+ step(generator["throw"](value));
673
+ } catch (e) {
674
+ reject(e);
675
+ }
676
+ }
677
+ function step(result) {
678
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
679
+ }
680
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
226
681
  });
227
- if (response.status >= 400) {
228
- const errorBody = response.data ?? {};
229
- const message = errorBody.detail ?? errorBody.title ?? errorBody.message ?? `HTTP ${response.status}`;
230
- const code = errorBody["o:errorCode"] ?? errorBody.code ?? `HTTP_${response.status}`;
231
- throw new NetSuiteError(
232
- message,
233
- response.status,
234
- code,
235
- errorBody,
236
- context.url,
237
- context.method
238
- );
682
+ };
683
+ var __generator = exports$1 && exports$1.__generator || function(thisArg, body) {
684
+ var _ = { label: 0, sent: function() {
685
+ if (t[0] & 1) throw t[1];
686
+ return t[1];
687
+ }, trys: [], ops: [] }, f, y, t, g;
688
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() {
689
+ return this;
690
+ }), g;
691
+ function verb(n) {
692
+ return function(v) {
693
+ return step([n, v]);
694
+ };
239
695
  }
240
- return {
241
- status: response.status,
242
- headers: extractHeaders(response),
243
- body: response.status === 204 ? void 0 : response.data,
244
- duration
245
- };
246
- } catch (error) {
247
- if (error instanceof NetSuiteError) {
248
- throw error;
249
- }
250
- Math.round(performance.now() - startTime);
251
- const axiosError = error;
252
- if (axiosError.code === "ECONNABORTED" || axiosError.code === "ERR_CANCELED") {
253
- throw new NetSuiteError(
254
- `Request timed out after ${timeout}ms`,
255
- 504,
256
- "TIMEOUT",
257
- void 0,
258
- context.url,
259
- context.method
260
- );
261
- }
262
- throw new NetSuiteError(
263
- axiosError.message || "Network error",
264
- 0,
265
- "NETWORK_ERROR",
266
- void 0,
267
- context.url,
268
- context.method
269
- );
270
- }
696
+ function step(op) {
697
+ if (f) throw new TypeError("Generator is already executing.");
698
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
699
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
700
+ if (y = 0, t) op = [op[0] & 2, t.value];
701
+ switch (op[0]) {
702
+ case 0:
703
+ case 1:
704
+ t = op;
705
+ break;
706
+ case 4:
707
+ _.label++;
708
+ return { value: op[1], done: false };
709
+ case 5:
710
+ _.label++;
711
+ y = op[1];
712
+ op = [0];
713
+ continue;
714
+ case 7:
715
+ op = _.ops.pop();
716
+ _.trys.pop();
717
+ continue;
718
+ default:
719
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) {
720
+ _ = 0;
721
+ continue;
722
+ }
723
+ if (op[0] === 3 && (!t || op[1] > t[0] && op[1] < t[3])) {
724
+ _.label = op[1];
725
+ break;
726
+ }
727
+ if (op[0] === 6 && _.label < t[1]) {
728
+ _.label = t[1];
729
+ t = op;
730
+ break;
731
+ }
732
+ if (t && _.label < t[2]) {
733
+ _.label = t[2];
734
+ _.ops.push(op);
735
+ break;
736
+ }
737
+ if (t[2]) _.ops.pop();
738
+ _.trys.pop();
739
+ continue;
740
+ }
741
+ op = body.call(thisArg, _);
742
+ } catch (e) {
743
+ op = [6, e];
744
+ y = 0;
745
+ } finally {
746
+ f = t = 0;
747
+ }
748
+ if (op[0] & 5) throw op[1];
749
+ return { value: op[0] ? op[1] : void 0, done: true };
750
+ }
751
+ };
752
+ var __await = exports$1 && exports$1.__await || function(v) {
753
+ return this instanceof __await ? (this.v = v, this) : new __await(v);
754
+ };
755
+ var __asyncGenerator = exports$1 && exports$1.__asyncGenerator || function(thisArg, _arguments, generator) {
756
+ if (!Symbol.asyncIterator) throw new TypeError("Symbol.asyncIterator is not defined.");
757
+ var g = generator.apply(thisArg, _arguments || []), i, q = [];
758
+ return i = {}, verb("next"), verb("throw"), verb("return", awaitReturn), i[Symbol.asyncIterator] = function() {
759
+ return this;
760
+ }, i;
761
+ function awaitReturn(f) {
762
+ return function(v) {
763
+ return Promise.resolve(v).then(f, reject);
764
+ };
765
+ }
766
+ function verb(n, f) {
767
+ if (g[n]) {
768
+ i[n] = function(v) {
769
+ return new Promise(function(a, b) {
770
+ q.push([n, v, a, b]) > 1 || resume(n, v);
771
+ });
772
+ };
773
+ if (f) i[n] = f(i[n]);
774
+ }
775
+ }
776
+ function resume(n, v) {
777
+ try {
778
+ step(g[n](v));
779
+ } catch (e) {
780
+ settle(q[0][3], e);
781
+ }
782
+ }
783
+ function step(r) {
784
+ r.value instanceof __await ? Promise.resolve(r.value.v).then(fulfill, reject) : settle(q[0][2], r);
785
+ }
786
+ function fulfill(value) {
787
+ resume("next", value);
788
+ }
789
+ function reject(value) {
790
+ resume("throw", value);
791
+ }
792
+ function settle(f, v) {
793
+ if (f(v), q.shift(), q.length) resume(q[0][0], q[0][1]);
794
+ }
795
+ };
796
+ Object.defineProperty(exports$1, "__esModule", { value: true });
797
+ exports$1.SuiteQLClient = void 0;
798
+ var SuiteQLClient = (
799
+ /** @class */
800
+ (function() {
801
+ function SuiteQLClient2(transport, accountId) {
802
+ this.transport = transport;
803
+ var normalizedId = accountId.toLowerCase().replace(/_/g, "-");
804
+ this.baseUrl = "https://".concat(normalizedId, ".suitetalk.api.netsuite.com/services/rest/query/v1/suiteql");
805
+ }
806
+ SuiteQLClient2.prototype.query = function(sql_1) {
807
+ return __awaiter(this, arguments, void 0, function(sql, options) {
808
+ var _a, pageSize, _b, startOffset, _c, maxRows, timeout, allItems, currentOffset, totalResults, pagesFetched, startTime, effectiveLimit, url, response, page, hasMore;
809
+ if (options === void 0) {
810
+ options = {};
811
+ }
812
+ return __generator(this, function(_d) {
813
+ switch (_d.label) {
814
+ case 0:
815
+ _a = options.pageSize, pageSize = _a === void 0 ? 1e3 : _a, _b = options.offset, startOffset = _b === void 0 ? 0 : _b, _c = options.maxRows, maxRows = _c === void 0 ? Infinity : _c, timeout = options.timeout;
816
+ allItems = [];
817
+ currentOffset = startOffset;
818
+ totalResults = 0;
819
+ pagesFetched = 0;
820
+ startTime = performance.now();
821
+ _d.label = 1;
822
+ case 1:
823
+ effectiveLimit = Math.min(pageSize, maxRows - allItems.length);
824
+ if (effectiveLimit <= 0)
825
+ return [3, 3];
826
+ url = "".concat(this.baseUrl, "?limit=").concat(effectiveLimit, "&offset=").concat(currentOffset);
827
+ return [4, this.transport.request(url, {
828
+ method: "POST",
829
+ body: { q: sql },
830
+ headers: { Prefer: "transient" },
831
+ timeout
832
+ })];
833
+ case 2:
834
+ response = _d.sent();
835
+ page = response.data;
836
+ totalResults = page.totalResults;
837
+ pagesFetched++;
838
+ allItems.push.apply(allItems, page.items);
839
+ hasMore = page.hasMore || currentOffset + page.items.length < totalResults;
840
+ if (!hasMore || allItems.length >= maxRows || page.items.length === 0)
841
+ return [3, 3];
842
+ currentOffset += page.items.length;
843
+ return [3, 1];
844
+ case 3:
845
+ return [2, {
846
+ items: allItems,
847
+ totalResults,
848
+ pagesFetched,
849
+ hasMore: allItems.length < totalResults,
850
+ duration: Math.round(performance.now() - startTime)
851
+ }];
852
+ }
853
+ });
854
+ });
855
+ };
856
+ SuiteQLClient2.prototype.queryOne = function(sql, options) {
857
+ return __awaiter(this, void 0, void 0, function() {
858
+ var result;
859
+ var _a;
860
+ return __generator(this, function(_b) {
861
+ switch (_b.label) {
862
+ case 0:
863
+ return [4, this.query(sql, __assign(__assign({}, options), { maxRows: 1 }))];
864
+ case 1:
865
+ result = _b.sent();
866
+ return [2, (_a = result.items[0]) !== null && _a !== void 0 ? _a : null];
867
+ }
868
+ });
869
+ });
870
+ };
871
+ SuiteQLClient2.prototype.queryPages = function(sql_1) {
872
+ return __asyncGenerator(this, arguments, function queryPages_1(sql, options) {
873
+ var _a, pageSize, _b, startOffset, _c, maxRows, timeout, currentOffset, totalYielded, effectiveLimit, url, response, page, hasMore;
874
+ if (options === void 0) {
875
+ options = {};
876
+ }
877
+ return __generator(this, function(_d) {
878
+ switch (_d.label) {
879
+ case 0:
880
+ _a = options.pageSize, pageSize = _a === void 0 ? 1e3 : _a, _b = options.offset, startOffset = _b === void 0 ? 0 : _b, _c = options.maxRows, maxRows = _c === void 0 ? Infinity : _c, timeout = options.timeout;
881
+ currentOffset = startOffset;
882
+ totalYielded = 0;
883
+ _d.label = 1;
884
+ case 1:
885
+ effectiveLimit = Math.min(pageSize, maxRows - totalYielded);
886
+ if (!(effectiveLimit <= 0)) return [3, 3];
887
+ return [4, __await(void 0)];
888
+ case 2:
889
+ return [2, _d.sent()];
890
+ case 3:
891
+ url = "".concat(this.baseUrl, "?limit=").concat(effectiveLimit, "&offset=").concat(currentOffset);
892
+ return [4, __await(this.transport.request(url, {
893
+ method: "POST",
894
+ body: { q: sql },
895
+ headers: { Prefer: "transient" },
896
+ timeout
897
+ }))];
898
+ case 4:
899
+ response = _d.sent();
900
+ page = response.data;
901
+ if (!(page.items.length === 0)) return [3, 6];
902
+ return [4, __await(void 0)];
903
+ case 5:
904
+ return [2, _d.sent()];
905
+ case 6:
906
+ return [4, __await(page.items)];
907
+ case 7:
908
+ return [4, _d.sent()];
909
+ case 8:
910
+ _d.sent();
911
+ totalYielded += page.items.length;
912
+ hasMore = page.hasMore || currentOffset + page.items.length < page.totalResults;
913
+ if (!(!hasMore || totalYielded >= maxRows)) return [3, 10];
914
+ return [4, __await(void 0)];
915
+ case 9:
916
+ return [2, _d.sent()];
917
+ case 10:
918
+ currentOffset += page.items.length;
919
+ return [3, 1];
920
+ case 11:
921
+ return [
922
+ 2
923
+ /*return*/
924
+ ];
925
+ }
926
+ });
927
+ });
928
+ };
929
+ return SuiteQLClient2;
930
+ })()
931
+ );
932
+ exports$1.SuiteQLClient = SuiteQLClient;
271
933
  }
272
- };
934
+ });
273
935
 
274
- // src/suiteql/suiteql-client.ts
275
- var SuiteQLClient = class {
276
- transport;
277
- baseUrl;
278
- constructor(transport, accountId) {
279
- this.transport = transport;
280
- const normalizedId = accountId.toLowerCase().replace(/_/g, "-");
281
- this.baseUrl = `https://${normalizedId}.suitetalk.api.netsuite.com/services/rest/query/v1/suiteql`;
282
- }
283
- /**
284
- * Execute a SuiteQL query and return all matching rows.
285
- * Automatically paginates across multiple pages.
286
- *
287
- * @example
288
- * ```ts
289
- * const result = await client.suiteql.query<Customer>(
290
- * 'SELECT id, companyname, email FROM customer WHERE isinactive = \'F\'',
291
- * { pageSize: 500 }
292
- * );
293
- * console.log(result.items); // all rows
294
- * console.log(result.totalResults); // total count from NetSuite
295
- * ```
296
- */
297
- async query(sql, options = {}) {
298
- const {
299
- pageSize = 1e3,
300
- offset: startOffset = 0,
301
- maxRows = Infinity,
302
- timeout
303
- } = options;
304
- const allItems = [];
305
- let currentOffset = startOffset;
306
- let totalResults = 0;
307
- let pagesFetched = 0;
308
- const startTime = performance.now();
309
- while (true) {
310
- const effectiveLimit = Math.min(pageSize, maxRows - allItems.length);
311
- if (effectiveLimit <= 0) break;
312
- const url = `${this.baseUrl}?limit=${effectiveLimit}&offset=${currentOffset}`;
313
- const response = await this.transport.request(url, {
314
- method: "POST",
315
- body: { q: sql },
316
- headers: { Prefer: "transient" },
317
- timeout
936
+ // src/records/record-client.js
937
+ var require_record_client = __commonJS({
938
+ "src/records/record-client.js"(exports$1) {
939
+ var __awaiter = exports$1 && exports$1.__awaiter || function(thisArg, _arguments, P, generator) {
940
+ function adopt(value) {
941
+ return value instanceof P ? value : new P(function(resolve) {
942
+ resolve(value);
943
+ });
944
+ }
945
+ return new (P || (P = Promise))(function(resolve, reject) {
946
+ function fulfilled(value) {
947
+ try {
948
+ step(generator.next(value));
949
+ } catch (e) {
950
+ reject(e);
951
+ }
952
+ }
953
+ function rejected(value) {
954
+ try {
955
+ step(generator["throw"](value));
956
+ } catch (e) {
957
+ reject(e);
958
+ }
959
+ }
960
+ function step(result) {
961
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
962
+ }
963
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
318
964
  });
319
- const page = response.data;
320
- totalResults = page.totalResults;
321
- pagesFetched++;
322
- allItems.push(...page.items);
323
- const hasMore = page.hasMore || currentOffset + page.items.length < totalResults;
324
- if (!hasMore || allItems.length >= maxRows || page.items.length === 0) break;
325
- currentOffset += page.items.length;
326
- }
327
- return {
328
- items: allItems,
329
- totalResults,
330
- pagesFetched,
331
- hasMore: allItems.length < totalResults,
332
- duration: Math.round(performance.now() - startTime)
333
965
  };
966
+ var __generator = exports$1 && exports$1.__generator || function(thisArg, body) {
967
+ var _ = { label: 0, sent: function() {
968
+ if (t[0] & 1) throw t[1];
969
+ return t[1];
970
+ }, trys: [], ops: [] }, f, y, t, g;
971
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() {
972
+ return this;
973
+ }), g;
974
+ function verb(n) {
975
+ return function(v) {
976
+ return step([n, v]);
977
+ };
978
+ }
979
+ function step(op) {
980
+ if (f) throw new TypeError("Generator is already executing.");
981
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
982
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
983
+ if (y = 0, t) op = [op[0] & 2, t.value];
984
+ switch (op[0]) {
985
+ case 0:
986
+ case 1:
987
+ t = op;
988
+ break;
989
+ case 4:
990
+ _.label++;
991
+ return { value: op[1], done: false };
992
+ case 5:
993
+ _.label++;
994
+ y = op[1];
995
+ op = [0];
996
+ continue;
997
+ case 7:
998
+ op = _.ops.pop();
999
+ _.trys.pop();
1000
+ continue;
1001
+ default:
1002
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) {
1003
+ _ = 0;
1004
+ continue;
1005
+ }
1006
+ if (op[0] === 3 && (!t || op[1] > t[0] && op[1] < t[3])) {
1007
+ _.label = op[1];
1008
+ break;
1009
+ }
1010
+ if (op[0] === 6 && _.label < t[1]) {
1011
+ _.label = t[1];
1012
+ t = op;
1013
+ break;
1014
+ }
1015
+ if (t && _.label < t[2]) {
1016
+ _.label = t[2];
1017
+ _.ops.push(op);
1018
+ break;
1019
+ }
1020
+ if (t[2]) _.ops.pop();
1021
+ _.trys.pop();
1022
+ continue;
1023
+ }
1024
+ op = body.call(thisArg, _);
1025
+ } catch (e) {
1026
+ op = [6, e];
1027
+ y = 0;
1028
+ } finally {
1029
+ f = t = 0;
1030
+ }
1031
+ if (op[0] & 5) throw op[1];
1032
+ return { value: op[0] ? op[1] : void 0, done: true };
1033
+ }
1034
+ };
1035
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1036
+ exports$1.RecordClient = void 0;
1037
+ var RecordClient = (
1038
+ /** @class */
1039
+ (function() {
1040
+ function RecordClient2(transport, accountId) {
1041
+ this.transport = transport;
1042
+ var normalizedId = accountId.toLowerCase().replace(/_/g, "-");
1043
+ this.baseUrl = "https://".concat(normalizedId, ".suitetalk.api.netsuite.com/services/rest/record/v1");
1044
+ }
1045
+ RecordClient2.prototype.get = function(recordType, id, options) {
1046
+ return __awaiter(this, void 0, void 0, function() {
1047
+ var params, qs, url;
1048
+ var _a;
1049
+ return __generator(this, function(_b) {
1050
+ params = new URLSearchParams();
1051
+ if ((_a = options === null || options === void 0 ? void 0 : options.fields) === null || _a === void 0 ? void 0 : _a.length) {
1052
+ params.set("fields", options.fields.join(","));
1053
+ }
1054
+ if (options === null || options === void 0 ? void 0 : options.expandSubResources) {
1055
+ params.set("expandSubResources", "true");
1056
+ }
1057
+ qs = params.toString();
1058
+ url = "".concat(this.baseUrl, "/").concat(recordType, "/").concat(id).concat(qs ? "?".concat(qs) : "");
1059
+ return [2, this.transport.request(url)];
1060
+ });
1061
+ });
1062
+ };
1063
+ RecordClient2.prototype.list = function(recordType, options) {
1064
+ return __awaiter(this, void 0, void 0, function() {
1065
+ var params, _i, _a, _b, key, value, qs, url;
1066
+ var _c;
1067
+ return __generator(this, function(_d) {
1068
+ params = new URLSearchParams();
1069
+ if ((options === null || options === void 0 ? void 0 : options.limit) != null)
1070
+ params.set("limit", String(options.limit));
1071
+ if ((options === null || options === void 0 ? void 0 : options.offset) != null)
1072
+ params.set("offset", String(options.offset));
1073
+ if ((_c = options === null || options === void 0 ? void 0 : options.fields) === null || _c === void 0 ? void 0 : _c.length)
1074
+ params.set("fields", options.fields.join(","));
1075
+ if (options === null || options === void 0 ? void 0 : options.expandSubResources)
1076
+ params.set("expandSubResources", "true");
1077
+ if (options === null || options === void 0 ? void 0 : options.query) {
1078
+ for (_i = 0, _a = Object.entries(options.query); _i < _a.length; _i++) {
1079
+ _b = _a[_i], key = _b[0], value = _b[1];
1080
+ params.set(key, value);
1081
+ }
1082
+ }
1083
+ qs = params.toString();
1084
+ url = "".concat(this.baseUrl, "/").concat(recordType).concat(qs ? "?".concat(qs) : "");
1085
+ return [2, this.transport.request(url)];
1086
+ });
1087
+ });
1088
+ };
1089
+ RecordClient2.prototype.create = function(recordType, body) {
1090
+ return __awaiter(this, void 0, void 0, function() {
1091
+ return __generator(this, function(_a) {
1092
+ return [2, this.transport.request("".concat(this.baseUrl, "/").concat(recordType), {
1093
+ method: "POST",
1094
+ body
1095
+ })];
1096
+ });
1097
+ });
1098
+ };
1099
+ RecordClient2.prototype.update = function(recordType, id, body) {
1100
+ return __awaiter(this, void 0, void 0, function() {
1101
+ return __generator(this, function(_a) {
1102
+ return [2, this.transport.request("".concat(this.baseUrl, "/").concat(recordType, "/").concat(id), {
1103
+ method: "PATCH",
1104
+ body
1105
+ })];
1106
+ });
1107
+ });
1108
+ };
1109
+ RecordClient2.prototype.replace = function(recordType, id, body) {
1110
+ return __awaiter(this, void 0, void 0, function() {
1111
+ return __generator(this, function(_a) {
1112
+ return [2, this.transport.request("".concat(this.baseUrl, "/").concat(recordType, "/").concat(id), {
1113
+ method: "PUT",
1114
+ body
1115
+ })];
1116
+ });
1117
+ });
1118
+ };
1119
+ RecordClient2.prototype.delete = function(recordType, id) {
1120
+ return __awaiter(this, void 0, void 0, function() {
1121
+ return __generator(this, function(_a) {
1122
+ return [2, this.transport.request("".concat(this.baseUrl, "/").concat(recordType, "/").concat(id), {
1123
+ method: "DELETE"
1124
+ })];
1125
+ });
1126
+ });
1127
+ };
1128
+ RecordClient2.prototype.upsert = function(recordType, externalIdField, externalIdValue, body) {
1129
+ return __awaiter(this, void 0, void 0, function() {
1130
+ return __generator(this, function(_a) {
1131
+ return [2, this.transport.request("".concat(this.baseUrl, "/").concat(recordType, "/eid:").concat(externalIdField, "=").concat(externalIdValue), { method: "PUT", body })];
1132
+ });
1133
+ });
1134
+ };
1135
+ return RecordClient2;
1136
+ })()
1137
+ );
1138
+ exports$1.RecordClient = RecordClient;
334
1139
  }
335
- /**
336
- * Execute a query and return a single row, or null if not found.
337
- *
338
- * @example
339
- * ```ts
340
- * const customer = await client.suiteql.queryOne<Customer>(
341
- * 'SELECT id, companyname FROM customer WHERE id = 123'
342
- * );
343
- * ```
344
- */
345
- async queryOne(sql, options) {
346
- const result = await this.query(sql, { ...options, maxRows: 1 });
347
- return result.items[0] ?? null;
348
- }
349
- /**
350
- * Execute a query and yield pages as an async generator.
351
- * Useful for streaming large result sets without holding everything in memory.
352
- *
353
- * @example
354
- * ```ts
355
- * for await (const page of client.suiteql.queryPages<Transaction>(
356
- * 'SELECT id, tranid, total FROM transaction',
357
- * { pageSize: 500 }
358
- * )) {
359
- * await processBatch(page);
360
- * }
361
- * ```
362
- */
363
- async *queryPages(sql, options = {}) {
364
- const {
365
- pageSize = 1e3,
366
- offset: startOffset = 0,
367
- maxRows = Infinity,
368
- timeout
369
- } = options;
370
- let currentOffset = startOffset;
371
- let totalYielded = 0;
372
- while (true) {
373
- const effectiveLimit = Math.min(pageSize, maxRows - totalYielded);
374
- if (effectiveLimit <= 0) return;
375
- const url = `${this.baseUrl}?limit=${effectiveLimit}&offset=${currentOffset}`;
376
- const response = await this.transport.request(url, {
377
- method: "POST",
378
- body: { q: sql },
379
- headers: { Prefer: "transient" },
380
- timeout
1140
+ });
1141
+
1142
+ // src/restlets/restlet-client.js
1143
+ var require_restlet_client = __commonJS({
1144
+ "src/restlets/restlet-client.js"(exports$1) {
1145
+ var __awaiter = exports$1 && exports$1.__awaiter || function(thisArg, _arguments, P, generator) {
1146
+ function adopt(value) {
1147
+ return value instanceof P ? value : new P(function(resolve) {
1148
+ resolve(value);
1149
+ });
1150
+ }
1151
+ return new (P || (P = Promise))(function(resolve, reject) {
1152
+ function fulfilled(value) {
1153
+ try {
1154
+ step(generator.next(value));
1155
+ } catch (e) {
1156
+ reject(e);
1157
+ }
1158
+ }
1159
+ function rejected(value) {
1160
+ try {
1161
+ step(generator["throw"](value));
1162
+ } catch (e) {
1163
+ reject(e);
1164
+ }
1165
+ }
1166
+ function step(result) {
1167
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
1168
+ }
1169
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
381
1170
  });
382
- const page = response.data;
383
- if (page.items.length === 0) return;
384
- yield page.items;
385
- totalYielded += page.items.length;
386
- const hasMore = page.hasMore || currentOffset + page.items.length < page.totalResults;
387
- if (!hasMore || totalYielded >= maxRows) return;
388
- currentOffset += page.items.length;
389
- }
1171
+ };
1172
+ var __generator = exports$1 && exports$1.__generator || function(thisArg, body) {
1173
+ var _ = { label: 0, sent: function() {
1174
+ if (t[0] & 1) throw t[1];
1175
+ return t[1];
1176
+ }, trys: [], ops: [] }, f, y, t, g;
1177
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() {
1178
+ return this;
1179
+ }), g;
1180
+ function verb(n) {
1181
+ return function(v) {
1182
+ return step([n, v]);
1183
+ };
1184
+ }
1185
+ function step(op) {
1186
+ if (f) throw new TypeError("Generator is already executing.");
1187
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
1188
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
1189
+ if (y = 0, t) op = [op[0] & 2, t.value];
1190
+ switch (op[0]) {
1191
+ case 0:
1192
+ case 1:
1193
+ t = op;
1194
+ break;
1195
+ case 4:
1196
+ _.label++;
1197
+ return { value: op[1], done: false };
1198
+ case 5:
1199
+ _.label++;
1200
+ y = op[1];
1201
+ op = [0];
1202
+ continue;
1203
+ case 7:
1204
+ op = _.ops.pop();
1205
+ _.trys.pop();
1206
+ continue;
1207
+ default:
1208
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) {
1209
+ _ = 0;
1210
+ continue;
1211
+ }
1212
+ if (op[0] === 3 && (!t || op[1] > t[0] && op[1] < t[3])) {
1213
+ _.label = op[1];
1214
+ break;
1215
+ }
1216
+ if (op[0] === 6 && _.label < t[1]) {
1217
+ _.label = t[1];
1218
+ t = op;
1219
+ break;
1220
+ }
1221
+ if (t && _.label < t[2]) {
1222
+ _.label = t[2];
1223
+ _.ops.push(op);
1224
+ break;
1225
+ }
1226
+ if (t[2]) _.ops.pop();
1227
+ _.trys.pop();
1228
+ continue;
1229
+ }
1230
+ op = body.call(thisArg, _);
1231
+ } catch (e) {
1232
+ op = [6, e];
1233
+ y = 0;
1234
+ } finally {
1235
+ f = t = 0;
1236
+ }
1237
+ if (op[0] & 5) throw op[1];
1238
+ return { value: op[0] ? op[1] : void 0, done: true };
1239
+ }
1240
+ };
1241
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1242
+ exports$1.RestletClient = void 0;
1243
+ var RestletClient = (
1244
+ /** @class */
1245
+ (function() {
1246
+ function RestletClient2(transport, accountId) {
1247
+ this.transport = transport;
1248
+ var normalizedId = accountId.toLowerCase().replace(/_/g, "-");
1249
+ this.baseUrl = "https://".concat(normalizedId, ".restlets.api.netsuite.com/app/site/hosting/restlet.nl");
1250
+ }
1251
+ RestletClient2.prototype.call = function(restlet, options) {
1252
+ return __awaiter(this, void 0, void 0, function() {
1253
+ var searchParams, _i, _a, _b, key, value, url;
1254
+ return __generator(this, function(_c) {
1255
+ searchParams = new URLSearchParams({
1256
+ script: String(restlet.script),
1257
+ deploy: String(restlet.deploy)
1258
+ });
1259
+ if (restlet.params) {
1260
+ for (_i = 0, _a = Object.entries(restlet.params); _i < _a.length; _i++) {
1261
+ _b = _a[_i], key = _b[0], value = _b[1];
1262
+ searchParams.set(key, String(value));
1263
+ }
1264
+ }
1265
+ url = "".concat(this.baseUrl, "?").concat(searchParams.toString());
1266
+ return [2, this.transport.request(url, options)];
1267
+ });
1268
+ });
1269
+ };
1270
+ return RestletClient2;
1271
+ })()
1272
+ );
1273
+ exports$1.RestletClient = RestletClient;
390
1274
  }
391
- };
1275
+ });
392
1276
 
393
- // src/records/record-client.ts
394
- var RecordClient = class {
395
- transport;
396
- baseUrl;
397
- constructor(transport, accountId) {
398
- this.transport = transport;
399
- const normalizedId = accountId.toLowerCase().replace(/_/g, "-");
400
- this.baseUrl = `https://${normalizedId}.suitetalk.api.netsuite.com/services/rest/record/v1`;
401
- }
402
- /** Get a record by type and internal ID */
403
- async get(recordType, id, options) {
404
- const params = new URLSearchParams();
405
- if (options?.fields?.length) {
406
- params.set("fields", options.fields.join(","));
407
- }
408
- if (options?.expandSubResources) {
409
- params.set("expandSubResources", "true");
410
- }
411
- const qs = params.toString();
412
- const url = `${this.baseUrl}/${recordType}/${id}${qs ? `?${qs}` : ""}`;
413
- return this.transport.request(url);
414
- }
415
- /** List records of a given type */
416
- async list(recordType, options) {
417
- const params = new URLSearchParams();
418
- if (options?.limit != null) params.set("limit", String(options.limit));
419
- if (options?.offset != null) params.set("offset", String(options.offset));
420
- if (options?.fields?.length) params.set("fields", options.fields.join(","));
421
- if (options?.expandSubResources) params.set("expandSubResources", "true");
422
- if (options?.query) {
423
- for (const [key, value] of Object.entries(options.query)) {
424
- params.set(key, value);
1277
+ // src/utils/validation.js
1278
+ var require_validation = __commonJS({
1279
+ "src/utils/validation.js"(exports$1) {
1280
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1281
+ exports$1.validateConfig = validateConfig2;
1282
+ function validateConfig2(config) {
1283
+ var errors = [];
1284
+ if (!config || typeof config !== "object") {
1285
+ return ["Config must be a non-null object"];
1286
+ }
1287
+ var c = config;
1288
+ if (!c.auth || typeof c.auth !== "object") {
1289
+ errors.push("auth is required and must be an object");
1290
+ } else {
1291
+ var auth = c.auth;
1292
+ var requiredFields = ["consumerKey", "consumerSecret", "tokenKey", "tokenSecret", "realm"];
1293
+ for (var _i = 0, requiredFields_1 = requiredFields; _i < requiredFields_1.length; _i++) {
1294
+ var field = requiredFields_1[_i];
1295
+ if (!auth[field] || typeof auth[field] !== "string") {
1296
+ errors.push("auth.".concat(field, " is required and must be a non-empty string"));
1297
+ }
1298
+ }
1299
+ }
1300
+ if (!c.accountId || typeof c.accountId !== "string") {
1301
+ errors.push("accountId is required and must be a non-empty string");
425
1302
  }
1303
+ return errors;
426
1304
  }
427
- const qs = params.toString();
428
- const url = `${this.baseUrl}/${recordType}${qs ? `?${qs}` : ""}`;
429
- return this.transport.request(url);
430
- }
431
- /** Create a new record */
432
- async create(recordType, body) {
433
- return this.transport.request(`${this.baseUrl}/${recordType}`, {
434
- method: "POST",
435
- body
436
- });
437
- }
438
- /** Update an existing record (partial update via PATCH) */
439
- async update(recordType, id, body) {
440
- return this.transport.request(`${this.baseUrl}/${recordType}/${id}`, {
441
- method: "PATCH",
442
- body
443
- });
444
- }
445
- /** Replace an existing record (full replace via PUT) */
446
- async replace(recordType, id, body) {
447
- return this.transport.request(`${this.baseUrl}/${recordType}/${id}`, {
448
- method: "PUT",
449
- body
450
- });
451
1305
  }
452
- /** Delete a record */
453
- async delete(recordType, id) {
454
- return this.transport.request(`${this.baseUrl}/${recordType}/${id}`, {
455
- method: "DELETE"
456
- });
457
- }
458
- /** Upsert: create or update based on external ID */
459
- async upsert(recordType, externalIdField, externalIdValue, body) {
460
- return this.transport.request(
461
- `${this.baseUrl}/${recordType}/eid:${externalIdField}=${externalIdValue}`,
462
- { method: "PUT", body }
1306
+ });
1307
+
1308
+ // src/client.js
1309
+ var require_client = __commonJS({
1310
+ "src/client.js"(exports$1) {
1311
+ var __assign = exports$1 && exports$1.__assign || function() {
1312
+ __assign = Object.assign || function(t) {
1313
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
1314
+ s = arguments[i];
1315
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
1316
+ t[p] = s[p];
1317
+ }
1318
+ return t;
1319
+ };
1320
+ return __assign.apply(this, arguments);
1321
+ };
1322
+ var __awaiter = exports$1 && exports$1.__awaiter || function(thisArg, _arguments, P, generator) {
1323
+ function adopt(value) {
1324
+ return value instanceof P ? value : new P(function(resolve) {
1325
+ resolve(value);
1326
+ });
1327
+ }
1328
+ return new (P || (P = Promise))(function(resolve, reject) {
1329
+ function fulfilled(value) {
1330
+ try {
1331
+ step(generator.next(value));
1332
+ } catch (e) {
1333
+ reject(e);
1334
+ }
1335
+ }
1336
+ function rejected(value) {
1337
+ try {
1338
+ step(generator["throw"](value));
1339
+ } catch (e) {
1340
+ reject(e);
1341
+ }
1342
+ }
1343
+ function step(result) {
1344
+ result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected);
1345
+ }
1346
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
1347
+ });
1348
+ };
1349
+ var __generator = exports$1 && exports$1.__generator || function(thisArg, body) {
1350
+ var _ = { label: 0, sent: function() {
1351
+ if (t[0] & 1) throw t[1];
1352
+ return t[1];
1353
+ }, trys: [], ops: [] }, f, y, t, g;
1354
+ return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() {
1355
+ return this;
1356
+ }), g;
1357
+ function verb(n) {
1358
+ return function(v) {
1359
+ return step([n, v]);
1360
+ };
1361
+ }
1362
+ function step(op) {
1363
+ if (f) throw new TypeError("Generator is already executing.");
1364
+ while (g && (g = 0, op[0] && (_ = 0)), _) try {
1365
+ if (f = 1, y && (t = op[0] & 2 ? y["return"] : op[0] ? y["throw"] || ((t = y["return"]) && t.call(y), 0) : y.next) && !(t = t.call(y, op[1])).done) return t;
1366
+ if (y = 0, t) op = [op[0] & 2, t.value];
1367
+ switch (op[0]) {
1368
+ case 0:
1369
+ case 1:
1370
+ t = op;
1371
+ break;
1372
+ case 4:
1373
+ _.label++;
1374
+ return { value: op[1], done: false };
1375
+ case 5:
1376
+ _.label++;
1377
+ y = op[1];
1378
+ op = [0];
1379
+ continue;
1380
+ case 7:
1381
+ op = _.ops.pop();
1382
+ _.trys.pop();
1383
+ continue;
1384
+ default:
1385
+ if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) {
1386
+ _ = 0;
1387
+ continue;
1388
+ }
1389
+ if (op[0] === 3 && (!t || op[1] > t[0] && op[1] < t[3])) {
1390
+ _.label = op[1];
1391
+ break;
1392
+ }
1393
+ if (op[0] === 6 && _.label < t[1]) {
1394
+ _.label = t[1];
1395
+ t = op;
1396
+ break;
1397
+ }
1398
+ if (t && _.label < t[2]) {
1399
+ _.label = t[2];
1400
+ _.ops.push(op);
1401
+ break;
1402
+ }
1403
+ if (t[2]) _.ops.pop();
1404
+ _.trys.pop();
1405
+ continue;
1406
+ }
1407
+ op = body.call(thisArg, _);
1408
+ } catch (e) {
1409
+ op = [6, e];
1410
+ y = 0;
1411
+ } finally {
1412
+ f = t = 0;
1413
+ }
1414
+ if (op[0] & 5) throw op[1];
1415
+ return { value: op[0] ? op[1] : void 0, done: true };
1416
+ }
1417
+ };
1418
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1419
+ exports$1.NetSuiteClient = void 0;
1420
+ var http_transport_js_1 = require_http_transport();
1421
+ var suiteql_client_js_1 = require_suiteql_client();
1422
+ var record_client_js_1 = require_record_client();
1423
+ var restlet_client_js_1 = require_restlet_client();
1424
+ var validation_js_1 = require_validation();
1425
+ var NetSuiteClient2 = (
1426
+ /** @class */
1427
+ (function() {
1428
+ function NetSuiteClient3(config) {
1429
+ var errors = (0, validation_js_1.validateConfig)(config);
1430
+ if (errors.length > 0) {
1431
+ throw new Error("Invalid NetSuite configuration:\n - ".concat(errors.join("\n - ")));
1432
+ }
1433
+ this.transport = new http_transport_js_1.HttpTransport(config);
1434
+ this.suiteql = new suiteql_client_js_1.SuiteQLClient(this.transport, config.accountId);
1435
+ this.records = new record_client_js_1.RecordClient(this.transport, config.accountId);
1436
+ this.restlets = new restlet_client_js_1.RestletClient(this.transport, config.accountId);
1437
+ }
1438
+ NetSuiteClient3.prototype.use = function(middleware) {
1439
+ this.transport.use(middleware);
1440
+ return this;
1441
+ };
1442
+ NetSuiteClient3.prototype.request = function(url, options) {
1443
+ return __awaiter(this, void 0, void 0, function() {
1444
+ return __generator(this, function(_a) {
1445
+ return [2, this.transport.request(url, options)];
1446
+ });
1447
+ });
1448
+ };
1449
+ NetSuiteClient3.prototype.get = function(url, options) {
1450
+ return __awaiter(this, void 0, void 0, function() {
1451
+ return __generator(this, function(_a) {
1452
+ return [2, this.transport.request(url, __assign(__assign({}, options), { method: "GET" }))];
1453
+ });
1454
+ });
1455
+ };
1456
+ NetSuiteClient3.prototype.post = function(url, body, options) {
1457
+ return __awaiter(this, void 0, void 0, function() {
1458
+ return __generator(this, function(_a) {
1459
+ return [2, this.transport.request(url, __assign(__assign({}, options), { method: "POST", body }))];
1460
+ });
1461
+ });
1462
+ };
1463
+ NetSuiteClient3.prototype.put = function(url, body, options) {
1464
+ return __awaiter(this, void 0, void 0, function() {
1465
+ return __generator(this, function(_a) {
1466
+ return [2, this.transport.request(url, __assign(__assign({}, options), { method: "PUT", body }))];
1467
+ });
1468
+ });
1469
+ };
1470
+ NetSuiteClient3.prototype.patch = function(url, body, options) {
1471
+ return __awaiter(this, void 0, void 0, function() {
1472
+ return __generator(this, function(_a) {
1473
+ return [2, this.transport.request(url, __assign(__assign({}, options), { method: "PATCH", body }))];
1474
+ });
1475
+ });
1476
+ };
1477
+ NetSuiteClient3.prototype.delete = function(url, options) {
1478
+ return __awaiter(this, void 0, void 0, function() {
1479
+ return __generator(this, function(_a) {
1480
+ return [2, this.transport.request(url, __assign(__assign({}, options), { method: "DELETE" }))];
1481
+ });
1482
+ });
1483
+ };
1484
+ return NetSuiteClient3;
1485
+ })()
463
1486
  );
1487
+ exports$1.NetSuiteClient = NetSuiteClient2;
464
1488
  }
465
- };
1489
+ });
466
1490
 
467
- // src/restlets/restlet-client.ts
468
- var RestletClient = class {
469
- transport;
470
- baseUrl;
471
- constructor(transport, accountId) {
472
- this.transport = transport;
473
- const normalizedId = accountId.toLowerCase().replace(/_/g, "-");
474
- this.baseUrl = `https://${normalizedId}.restlets.api.netsuite.com/app/site/hosting/restlet.nl`;
475
- }
476
- /** Execute a RESTlet call */
477
- async call(restlet, options) {
478
- const searchParams = new URLSearchParams({
479
- script: String(restlet.script),
480
- deploy: String(restlet.deploy)
481
- });
482
- if (restlet.params) {
483
- for (const [key, value] of Object.entries(restlet.params)) {
484
- searchParams.set(key, String(value));
1491
+ // src/suiteql/query-builder.js
1492
+ var require_query_builder = __commonJS({
1493
+ "src/suiteql/query-builder.js"(exports$1) {
1494
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1495
+ exports$1.SuiteQLBuilder = void 0;
1496
+ exports$1.suiteql = suiteql2;
1497
+ var SuiteQLBuilder2 = (
1498
+ /** @class */
1499
+ (function() {
1500
+ function SuiteQLBuilder3() {
1501
+ this._select = [];
1502
+ this._from = "";
1503
+ this._joins = [];
1504
+ this._where = [];
1505
+ this._groupBy = [];
1506
+ this._orderBy = [];
1507
+ this._having = [];
1508
+ }
1509
+ SuiteQLBuilder3.prototype.select = function() {
1510
+ var _a;
1511
+ var columns = [];
1512
+ for (var _i = 0; _i < arguments.length; _i++) {
1513
+ columns[_i] = arguments[_i];
1514
+ }
1515
+ (_a = this._select).push.apply(_a, columns);
1516
+ return this;
1517
+ };
1518
+ SuiteQLBuilder3.prototype.from = function(table, alias) {
1519
+ this._from = alias ? "".concat(table, " ").concat(alias) : table;
1520
+ return this;
1521
+ };
1522
+ SuiteQLBuilder3.prototype.join = function(table, condition, type) {
1523
+ if (type === void 0) {
1524
+ type = "INNER";
1525
+ }
1526
+ this._joins.push("".concat(type, " JOIN ").concat(table, " ON ").concat(condition));
1527
+ return this;
1528
+ };
1529
+ SuiteQLBuilder3.prototype.leftJoin = function(table, condition) {
1530
+ return this.join(table, condition, "LEFT");
1531
+ };
1532
+ SuiteQLBuilder3.prototype.rightJoin = function(table, condition) {
1533
+ return this.join(table, condition, "RIGHT");
1534
+ };
1535
+ SuiteQLBuilder3.prototype.where = function(condition) {
1536
+ this._where.push(condition);
1537
+ return this;
1538
+ };
1539
+ SuiteQLBuilder3.prototype.whereEquals = function(column, value) {
1540
+ this._where.push("".concat(column, " = ").concat(escapeValue(value)));
1541
+ return this;
1542
+ };
1543
+ SuiteQLBuilder3.prototype.whereNotEquals = function(column, value) {
1544
+ this._where.push("".concat(column, " != ").concat(escapeValue(value)));
1545
+ return this;
1546
+ };
1547
+ SuiteQLBuilder3.prototype.whereIn = function(column, values) {
1548
+ var escaped = values.map(escapeValue);
1549
+ this._where.push("".concat(column, " IN (").concat(escaped.join(", "), ")"));
1550
+ return this;
1551
+ };
1552
+ SuiteQLBuilder3.prototype.whereNull = function(column) {
1553
+ this._where.push("".concat(column, " IS NULL"));
1554
+ return this;
1555
+ };
1556
+ SuiteQLBuilder3.prototype.whereNotNull = function(column) {
1557
+ this._where.push("".concat(column, " IS NOT NULL"));
1558
+ return this;
1559
+ };
1560
+ SuiteQLBuilder3.prototype.whereBetween = function(column, start, end) {
1561
+ this._where.push("".concat(column, " BETWEEN ").concat(escapeValue(start), " AND ").concat(escapeValue(end)));
1562
+ return this;
1563
+ };
1564
+ SuiteQLBuilder3.prototype.whereLike = function(column, pattern) {
1565
+ this._where.push("".concat(column, " LIKE ").concat(escapeValue(pattern)));
1566
+ return this;
1567
+ };
1568
+ SuiteQLBuilder3.prototype.groupBy = function() {
1569
+ var _a;
1570
+ var columns = [];
1571
+ for (var _i = 0; _i < arguments.length; _i++) {
1572
+ columns[_i] = arguments[_i];
1573
+ }
1574
+ (_a = this._groupBy).push.apply(_a, columns);
1575
+ return this;
1576
+ };
1577
+ SuiteQLBuilder3.prototype.having = function(condition) {
1578
+ this._having.push(condition);
1579
+ return this;
1580
+ };
1581
+ SuiteQLBuilder3.prototype.orderBy = function(column, direction) {
1582
+ if (direction === void 0) {
1583
+ direction = "ASC";
1584
+ }
1585
+ this._orderBy.push("".concat(column, " ").concat(direction));
1586
+ return this;
1587
+ };
1588
+ SuiteQLBuilder3.prototype.build = function() {
1589
+ if (this._select.length === 0) {
1590
+ throw new Error("SuiteQLBuilder: SELECT clause is required");
1591
+ }
1592
+ if (!this._from) {
1593
+ throw new Error("SuiteQLBuilder: FROM clause is required");
1594
+ }
1595
+ var parts = [
1596
+ "SELECT ".concat(this._select.join(", ")),
1597
+ "FROM ".concat(this._from)
1598
+ ];
1599
+ if (this._joins.length > 0) {
1600
+ parts.push(this._joins.join(" "));
1601
+ }
1602
+ if (this._where.length > 0) {
1603
+ parts.push("WHERE ".concat(this._where.join(" AND ")));
1604
+ }
1605
+ if (this._groupBy.length > 0) {
1606
+ parts.push("GROUP BY ".concat(this._groupBy.join(", ")));
1607
+ }
1608
+ if (this._having.length > 0) {
1609
+ parts.push("HAVING ".concat(this._having.join(" AND ")));
1610
+ }
1611
+ if (this._orderBy.length > 0) {
1612
+ parts.push("ORDER BY ".concat(this._orderBy.join(", ")));
1613
+ }
1614
+ return parts.join(" ");
1615
+ };
1616
+ SuiteQLBuilder3.prototype.toString = function() {
1617
+ return this.build();
1618
+ };
1619
+ return SuiteQLBuilder3;
1620
+ })()
1621
+ );
1622
+ exports$1.SuiteQLBuilder = SuiteQLBuilder2;
1623
+ function escapeValue(value) {
1624
+ if (typeof value === "number") {
1625
+ return String(value);
1626
+ }
1627
+ if (typeof value === "boolean") {
1628
+ return value ? "'T'" : "'F'";
485
1629
  }
1630
+ var escaped = value.replace(/'/g, "''");
1631
+ return "'".concat(escaped, "'");
1632
+ }
1633
+ function suiteql2() {
1634
+ return new SuiteQLBuilder2();
486
1635
  }
487
- const url = `${this.baseUrl}?${searchParams.toString()}`;
488
- return this.transport.request(url, options);
489
1636
  }
490
- };
1637
+ });
491
1638
 
492
- // src/utils/validation.ts
493
- function validateConfig(config) {
494
- const errors = [];
495
- if (!config || typeof config !== "object") {
496
- return ["Config must be a non-null object"];
497
- }
498
- const c = config;
499
- if (!c.auth || typeof c.auth !== "object") {
500
- errors.push("auth is required and must be an object");
501
- } else {
502
- const auth = c.auth;
503
- const requiredFields = ["consumerKey", "consumerSecret", "tokenKey", "tokenSecret", "realm"];
504
- for (const field of requiredFields) {
505
- if (!auth[field] || typeof auth[field] !== "string") {
506
- errors.push(`auth.${field} is required and must be a non-empty string`);
1639
+ // src/utils/response-cache.js
1640
+ var require_response_cache = __commonJS({
1641
+ "src/utils/response-cache.js"(exports$1) {
1642
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1643
+ exports$1.ResponseCache = void 0;
1644
+ exports$1.createCacheKey = createCacheKey2;
1645
+ var ResponseCache2 = (
1646
+ /** @class */
1647
+ (function() {
1648
+ function ResponseCache3() {
1649
+ this.cache = /* @__PURE__ */ new Map();
1650
+ }
1651
+ ResponseCache3.prototype.get = function(key) {
1652
+ var entry = this.cache.get(key);
1653
+ if (!entry)
1654
+ return null;
1655
+ if (Date.now() > entry.expiresAt) {
1656
+ this.cache.delete(key);
1657
+ return null;
1658
+ }
1659
+ return entry.data;
1660
+ };
1661
+ ResponseCache3.prototype.set = function(key, data, ttlSeconds) {
1662
+ this.cache.set(key, {
1663
+ data,
1664
+ expiresAt: Date.now() + ttlSeconds * 1e3
1665
+ });
1666
+ };
1667
+ ResponseCache3.prototype.delete = function(key) {
1668
+ return this.cache.delete(key);
1669
+ };
1670
+ ResponseCache3.prototype.clear = function() {
1671
+ this.cache.clear();
1672
+ };
1673
+ Object.defineProperty(ResponseCache3.prototype, "size", {
1674
+ /** Get the number of entries (including expired). */
1675
+ get: function() {
1676
+ return this.cache.size;
1677
+ },
1678
+ enumerable: false,
1679
+ configurable: true
1680
+ });
1681
+ return ResponseCache3;
1682
+ })()
1683
+ );
1684
+ exports$1.ResponseCache = ResponseCache2;
1685
+ function createCacheKey2(url, method, params) {
1686
+ var base = "".concat(method, ":").concat(url);
1687
+ if (params) {
1688
+ return "".concat(base, ":").concat(JSON.stringify(params));
507
1689
  }
1690
+ return base;
508
1691
  }
509
1692
  }
510
- if (!c.accountId || typeof c.accountId !== "string") {
511
- errors.push("accountId is required and must be a non-empty string");
512
- }
513
- return errors;
514
- }
1693
+ });
515
1694
 
516
- // src/client.ts
517
- var NetSuiteClient = class {
518
- /** SuiteQL query execution and builder */
519
- suiteql;
520
- /** REST Record API CRUD */
521
- records;
522
- /** RESTlet caller */
523
- restlets;
524
- transport;
525
- constructor(config) {
526
- const errors = validateConfig(config);
527
- if (errors.length > 0) {
528
- throw new Error(`Invalid NetSuite configuration:
529
- - ${errors.join("\n - ")}`);
530
- }
531
- this.transport = new HttpTransport(config);
532
- this.suiteql = new SuiteQLClient(this.transport, config.accountId);
533
- this.records = new RecordClient(this.transport, config.accountId);
534
- this.restlets = new RestletClient(this.transport, config.accountId);
535
- }
536
- /** Add middleware to all requests. Returns `this` for chaining. */
537
- use(middleware) {
538
- this.transport.use(middleware);
539
- return this;
540
- }
541
- /** Make a raw HTTP request (escape hatch for custom endpoints). */
542
- async request(url, options) {
543
- return this.transport.request(url, options);
544
- }
545
- /** Convenience: GET request */
546
- async get(url, options) {
547
- return this.transport.request(url, { ...options, method: "GET" });
548
- }
549
- /** Convenience: POST request */
550
- async post(url, body, options) {
551
- return this.transport.request(url, { ...options, method: "POST", body });
552
- }
553
- /** Convenience: PUT request */
554
- async put(url, body, options) {
555
- return this.transport.request(url, { ...options, method: "PUT", body });
556
- }
557
- /** Convenience: PATCH request */
558
- async patch(url, body, options) {
559
- return this.transport.request(url, { ...options, method: "PATCH", body });
560
- }
561
- /** Convenience: DELETE request */
562
- async delete(url, options) {
563
- return this.transport.request(url, { ...options, method: "DELETE" });
1695
+ // src/utils/rate-limiter.js
1696
+ var require_rate_limiter = __commonJS({
1697
+ "src/utils/rate-limiter.js"(exports$1) {
1698
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1699
+ exports$1.RateLimiter = void 0;
1700
+ var RateLimiter2 = (
1701
+ /** @class */
1702
+ (function() {
1703
+ function RateLimiter3(maxRequests, windowMs) {
1704
+ if (maxRequests === void 0) {
1705
+ maxRequests = 100;
1706
+ }
1707
+ if (windowMs === void 0) {
1708
+ windowMs = 6e4;
1709
+ }
1710
+ this.timestamps = [];
1711
+ this.maxRequests = maxRequests;
1712
+ this.windowMs = windowMs;
1713
+ }
1714
+ RateLimiter3.prototype.canMakeRequest = function() {
1715
+ this.pruneExpired();
1716
+ return this.timestamps.length < this.maxRequests;
1717
+ };
1718
+ RateLimiter3.prototype.recordRequest = function() {
1719
+ this.pruneExpired();
1720
+ this.timestamps.push(Date.now());
1721
+ };
1722
+ RateLimiter3.prototype.getRemainingRequests = function() {
1723
+ this.pruneExpired();
1724
+ return Math.max(0, this.maxRequests - this.timestamps.length);
1725
+ };
1726
+ RateLimiter3.prototype.getTimeUntilNextSlot = function() {
1727
+ this.pruneExpired();
1728
+ if (this.timestamps.length < this.maxRequests)
1729
+ return 0;
1730
+ var oldest = this.timestamps[0];
1731
+ return Math.max(0, oldest + this.windowMs - Date.now());
1732
+ };
1733
+ RateLimiter3.prototype.pruneExpired = function() {
1734
+ var cutoff = Date.now() - this.windowMs;
1735
+ while (this.timestamps.length > 0 && this.timestamps[0] <= cutoff) {
1736
+ this.timestamps.shift();
1737
+ }
1738
+ };
1739
+ return RateLimiter3;
1740
+ })()
1741
+ );
1742
+ exports$1.RateLimiter = RateLimiter2;
564
1743
  }
565
- };
1744
+ });
566
1745
 
567
- // src/suiteql/query-builder.ts
568
- var SuiteQLBuilder = class {
569
- _select = [];
570
- _from = "";
571
- _joins = [];
572
- _where = [];
573
- _groupBy = [];
574
- _orderBy = [];
575
- _having = [];
576
- /** Add columns to SELECT clause */
577
- select(...columns) {
578
- this._select.push(...columns);
579
- return this;
580
- }
581
- /** Set the FROM table, with optional alias */
582
- from(table, alias) {
583
- this._from = alias ? `${table} ${alias}` : table;
584
- return this;
585
- }
586
- /** Add a JOIN clause */
587
- join(table, condition, type = "INNER") {
588
- this._joins.push(`${type} JOIN ${table} ON ${condition}`);
589
- return this;
590
- }
591
- /** Add a LEFT JOIN clause */
592
- leftJoin(table, condition) {
593
- return this.join(table, condition, "LEFT");
594
- }
595
- /** Add a RIGHT JOIN clause */
596
- rightJoin(table, condition) {
597
- return this.join(table, condition, "RIGHT");
598
- }
599
- /** Add a raw WHERE condition */
600
- where(condition) {
601
- this._where.push(condition);
602
- return this;
603
- }
604
- /** Add a WHERE column = value condition. Values are escaped. */
605
- whereEquals(column, value) {
606
- this._where.push(`${column} = ${escapeValue(value)}`);
607
- return this;
608
- }
609
- /** Add a WHERE column != value condition. Values are escaped. */
610
- whereNotEquals(column, value) {
611
- this._where.push(`${column} != ${escapeValue(value)}`);
612
- return this;
613
- }
614
- /** Add a WHERE column IN (...) condition. Values are escaped. */
615
- whereIn(column, values) {
616
- const escaped = values.map(escapeValue);
617
- this._where.push(`${column} IN (${escaped.join(", ")})`);
618
- return this;
619
- }
620
- /** Add a WHERE column IS NULL condition */
621
- whereNull(column) {
622
- this._where.push(`${column} IS NULL`);
623
- return this;
624
- }
625
- /** Add a WHERE column IS NOT NULL condition */
626
- whereNotNull(column) {
627
- this._where.push(`${column} IS NOT NULL`);
628
- return this;
629
- }
630
- /** Add a WHERE column BETWEEN start AND end condition. Values are escaped. */
631
- whereBetween(column, start, end) {
632
- this._where.push(`${column} BETWEEN ${escapeValue(start)} AND ${escapeValue(end)}`);
633
- return this;
634
- }
635
- /** Add a WHERE column LIKE pattern condition. Value is escaped. */
636
- whereLike(column, pattern) {
637
- this._where.push(`${column} LIKE ${escapeValue(pattern)}`);
638
- return this;
639
- }
640
- /** Add columns to GROUP BY clause */
641
- groupBy(...columns) {
642
- this._groupBy.push(...columns);
643
- return this;
644
- }
645
- /** Add a HAVING condition (used with GROUP BY) */
646
- having(condition) {
647
- this._having.push(condition);
648
- return this;
649
- }
650
- /** Add a column to ORDER BY clause */
651
- orderBy(column, direction = "ASC") {
652
- this._orderBy.push(`${column} ${direction}`);
653
- return this;
654
- }
655
- /** Build the SQL string. Throws if SELECT or FROM is missing. */
656
- build() {
657
- if (this._select.length === 0) {
658
- throw new Error("SuiteQLBuilder: SELECT clause is required");
659
- }
660
- if (!this._from) {
661
- throw new Error("SuiteQLBuilder: FROM clause is required");
662
- }
663
- const parts = [
664
- `SELECT ${this._select.join(", ")}`,
665
- `FROM ${this._from}`
666
- ];
667
- if (this._joins.length > 0) {
668
- parts.push(this._joins.join(" "));
1746
+ // src/utils/date.js
1747
+ var require_date = __commonJS({
1748
+ "src/utils/date.js"(exports$1) {
1749
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1750
+ exports$1.formatNetSuiteDate = formatNetSuiteDate2;
1751
+ exports$1.parseNetSuiteDate = parseNetSuiteDate2;
1752
+ function formatNetSuiteDate2(date) {
1753
+ var year = date.getFullYear();
1754
+ var month = String(date.getMonth() + 1).padStart(2, "0");
1755
+ var day = String(date.getDate()).padStart(2, "0");
1756
+ return "".concat(year, "-").concat(month, "-").concat(day);
669
1757
  }
670
- if (this._where.length > 0) {
671
- parts.push(`WHERE ${this._where.join(" AND ")}`);
672
- }
673
- if (this._groupBy.length > 0) {
674
- parts.push(`GROUP BY ${this._groupBy.join(", ")}`);
675
- }
676
- if (this._having.length > 0) {
677
- parts.push(`HAVING ${this._having.join(" AND ")}`);
678
- }
679
- if (this._orderBy.length > 0) {
680
- parts.push(`ORDER BY ${this._orderBy.join(", ")}`);
1758
+ function parseNetSuiteDate2(dateString) {
1759
+ if (dateString.includes("/")) {
1760
+ var _a = dateString.split("/"), month_1 = _a[0], day_1 = _a[1], year_1 = _a[2];
1761
+ return new Date(Number(year_1), Number(month_1) - 1, Number(day_1));
1762
+ }
1763
+ var _b = dateString.split("-"), year = _b[0], month = _b[1], day = _b[2];
1764
+ return new Date(Number(year), Number(month) - 1, Number(day));
681
1765
  }
682
- return parts.join(" ");
683
- }
684
- /** Alias for build() */
685
- toString() {
686
- return this.build();
687
- }
688
- };
689
- function escapeValue(value) {
690
- if (typeof value === "number") {
691
- return String(value);
692
- }
693
- if (typeof value === "boolean") {
694
- return value ? "'T'" : "'F'";
695
1766
  }
696
- const escaped = value.replace(/'/g, "''");
697
- return `'${escaped}'`;
698
- }
699
- function suiteql() {
700
- return new SuiteQLBuilder();
701
- }
1767
+ });
702
1768
 
703
- // src/utils/response-cache.ts
704
- var ResponseCache = class {
705
- cache = /* @__PURE__ */ new Map();
706
- /** Get a cached value, or null if not found or expired. */
707
- get(key) {
708
- const entry = this.cache.get(key);
709
- if (!entry) return null;
710
- if (Date.now() > entry.expiresAt) {
711
- this.cache.delete(key);
712
- return null;
1769
+ // src/utils/error-parser.js
1770
+ var require_error_parser = __commonJS({
1771
+ "src/utils/error-parser.js"(exports$1) {
1772
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1773
+ exports$1.parseNetSuiteError = parseNetSuiteError2;
1774
+ function parseNetSuiteError2(error) {
1775
+ var _a, _b;
1776
+ if (!error || typeof error !== "object") {
1777
+ return { message: String(error) };
1778
+ }
1779
+ var e = error;
1780
+ if (e.title || e.detail) {
1781
+ return {
1782
+ message: String((_b = (_a = e.detail) !== null && _a !== void 0 ? _a : e.title) !== null && _b !== void 0 ? _b : "Unknown error"),
1783
+ code: e["o:errorCode"],
1784
+ details: e
1785
+ };
1786
+ }
1787
+ if (e.message) {
1788
+ return {
1789
+ message: String(e.message),
1790
+ code: e.code
1791
+ };
1792
+ }
1793
+ return { message: JSON.stringify(error) };
713
1794
  }
714
- return entry.data;
715
- }
716
- /** Set a cached value with a TTL in seconds. */
717
- set(key, data, ttlSeconds) {
718
- this.cache.set(key, {
719
- data,
720
- expiresAt: Date.now() + ttlSeconds * 1e3
721
- });
722
- }
723
- /** Delete a specific cache entry. */
724
- delete(key) {
725
- return this.cache.delete(key);
726
- }
727
- /** Clear all cached entries. */
728
- clear() {
729
- this.cache.clear();
730
- }
731
- /** Get the number of entries (including expired). */
732
- get size() {
733
- return this.cache.size;
734
- }
735
- };
736
- function createCacheKey(url, method, params) {
737
- const base = `${method}:${url}`;
738
- if (params) {
739
- return `${base}:${JSON.stringify(params)}`;
740
1795
  }
741
- return base;
742
- }
1796
+ });
743
1797
 
744
- // src/utils/rate-limiter.ts
745
- var RateLimiter = class {
746
- timestamps = [];
747
- maxRequests;
748
- windowMs;
749
- constructor(maxRequests = 100, windowMs = 6e4) {
750
- this.maxRequests = maxRequests;
751
- this.windowMs = windowMs;
752
- }
753
- /** Check if a request can be made without exceeding the limit. */
754
- canMakeRequest() {
755
- this.pruneExpired();
756
- return this.timestamps.length < this.maxRequests;
757
- }
758
- /** Record that a request was made. */
759
- recordRequest() {
760
- this.pruneExpired();
761
- this.timestamps.push(Date.now());
762
- }
763
- /** Get the number of remaining requests in the current window. */
764
- getRemainingRequests() {
765
- this.pruneExpired();
766
- return Math.max(0, this.maxRequests - this.timestamps.length);
767
- }
768
- /** Get ms until the next request slot opens. Returns 0 if a slot is available. */
769
- getTimeUntilNextSlot() {
770
- this.pruneExpired();
771
- if (this.timestamps.length < this.maxRequests) return 0;
772
- const oldest = this.timestamps[0];
773
- return Math.max(0, oldest + this.windowMs - Date.now());
774
- }
775
- pruneExpired() {
776
- const cutoff = Date.now() - this.windowMs;
777
- while (this.timestamps.length > 0 && this.timestamps[0] <= cutoff) {
778
- this.timestamps.shift();
1798
+ // src/utils/url-builder.js
1799
+ var require_url_builder = __commonJS({
1800
+ "src/utils/url-builder.js"(exports$1) {
1801
+ Object.defineProperty(exports$1, "__esModule", { value: true });
1802
+ exports$1.normalizeAccountId = normalizeAccountId2;
1803
+ exports$1.buildSuiteTalkUrl = buildSuiteTalkUrl;
1804
+ exports$1.buildRestletUrl = buildRestletUrl;
1805
+ function normalizeAccountId2(accountId) {
1806
+ return accountId.toLowerCase().replace(/_/g, "-");
1807
+ }
1808
+ function buildSuiteTalkUrl(accountId) {
1809
+ return "https://".concat(normalizeAccountId2(accountId), ".suitetalk.api.netsuite.com");
1810
+ }
1811
+ function buildRestletUrl(accountId) {
1812
+ return "https://".concat(normalizeAccountId2(accountId), ".restlets.api.netsuite.com");
779
1813
  }
780
1814
  }
781
- };
1815
+ });
782
1816
 
783
- // src/utils/date.ts
784
- function formatNetSuiteDate(date) {
785
- const year = date.getFullYear();
786
- const month = String(date.getMonth() + 1).padStart(2, "0");
787
- const day = String(date.getDate()).padStart(2, "0");
788
- return `${year}-${month}-${day}`;
789
- }
790
- function parseNetSuiteDate(dateString) {
791
- if (dateString.includes("/")) {
792
- const [month2, day2, year2] = dateString.split("/");
793
- return new Date(Number(year2), Number(month2) - 1, Number(day2));
1817
+ // src/index.ts
1818
+ var import_client = __toESM(require_client());
1819
+ var import_query_builder = __toESM(require_query_builder());
1820
+ var import_errors = __toESM(require_errors());
1821
+ var SOAP_ONLY_FIELDS = {
1822
+ assemblyItem: ["taxSchedule"],
1823
+ inventoryItem: ["taxSchedule"],
1824
+ nonInventoryItem: ["taxSchedule"],
1825
+ kitItem: ["taxSchedule"],
1826
+ serviceItem: ["taxSchedule"],
1827
+ otherChargeItem: ["taxSchedule"],
1828
+ lotNumberedInventoryItem: ["taxSchedule"],
1829
+ serializedInventoryItem: ["taxSchedule"]
1830
+ };
1831
+ var SOAP_RECORD_TYPES = {
1832
+ assemblyItem: { type: "AssemblyItem", namespace: "listAcct" },
1833
+ inventoryItem: { type: "InventoryItem", namespace: "listAcct" },
1834
+ nonInventoryItem: { type: "NonInventorySaleItem", namespace: "listAcct" },
1835
+ kitItem: { type: "KitItem", namespace: "listAcct" },
1836
+ serviceItem: { type: "ServiceSaleItem", namespace: "listAcct" },
1837
+ otherChargeItem: { type: "OtherChargeSaleItem", namespace: "listAcct" },
1838
+ lotNumberedInventoryItem: { type: "LotNumberedInventoryItem", namespace: "listAcct" },
1839
+ serializedInventoryItem: { type: "SerializedInventoryItem", namespace: "listAcct" },
1840
+ customer: { type: "Customer", namespace: "listRel" },
1841
+ vendor: { type: "Vendor", namespace: "listRel" },
1842
+ salesOrder: { type: "SalesOrder", namespace: "tranSales" },
1843
+ purchaseOrder: { type: "PurchaseOrder", namespace: "tranPurch" },
1844
+ invoice: { type: "Invoice", namespace: "tranSales" }
1845
+ };
1846
+ var NS_NAMESPACES = {
1847
+ listAcct: "urn:accounting_2024_1.lists.webservices.netsuite.com",
1848
+ listRel: "urn:relationships_2024_1.lists.webservices.netsuite.com",
1849
+ tranSales: "urn:sales_2024_1.transactions.webservices.netsuite.com",
1850
+ tranPurch: "urn:purchases_2024_1.transactions.webservices.netsuite.com",
1851
+ core: "urn:core_2024_1.platform.webservices.netsuite.com",
1852
+ messages: "urn:messages_2024_1.platform.webservices.netsuite.com"
1853
+ };
1854
+ function extractSoapOnlyFields(recordType, body) {
1855
+ const knownSoapFields = SOAP_ONLY_FIELDS[recordType] ?? [];
1856
+ const soapFields = {};
1857
+ const restBody = {};
1858
+ for (const [key, value] of Object.entries(body)) {
1859
+ if (knownSoapFields.includes(key)) {
1860
+ soapFields[key] = value;
1861
+ } else {
1862
+ restBody[key] = value;
1863
+ }
794
1864
  }
795
- const [year, month, day] = dateString.split("-");
796
- return new Date(Number(year), Number(month) - 1, Number(day));
1865
+ return { soapFields, restBody };
797
1866
  }
798
-
799
- // src/utils/error-parser.ts
800
- function parseNetSuiteError(error) {
801
- if (!error || typeof error !== "object") {
802
- return { message: String(error) };
1867
+ var SoapFieldClient = class {
1868
+ auth;
1869
+ accountId;
1870
+ constructor(auth, accountId) {
1871
+ this.auth = auth;
1872
+ this.accountId = accountId;
803
1873
  }
804
- const e = error;
805
- if (e.title || e.detail) {
1874
+ /**
1875
+ * Update SOAP-only fields on an existing record.
1876
+ */
1877
+ async updateFields(recordType, internalId, fields) {
1878
+ const soapType = SOAP_RECORD_TYPES[recordType];
1879
+ if (!soapType) {
1880
+ return {
1881
+ success: false,
1882
+ error: `Unsupported SOAP record type: ${recordType}`
1883
+ };
1884
+ }
1885
+ const fieldXml = this.buildFieldXml(fields, soapType.namespace);
1886
+ const envelope = this.buildUpdateEnvelope(soapType, internalId, fieldXml);
1887
+ const normalizedId = this.accountId.toLowerCase().replace(/_/g, "-");
1888
+ const soapUrl = `https://${normalizedId}.suitetalk.api.netsuite.com/services/NetSuitePort_2024_1`;
1889
+ const response = await fetch(soapUrl, {
1890
+ method: "POST",
1891
+ headers: {
1892
+ "Content-Type": "text/xml; charset=utf-8",
1893
+ SOAPAction: "update"
1894
+ },
1895
+ body: envelope
1896
+ });
1897
+ const responseText = await response.text();
1898
+ if (!response.ok) {
1899
+ const errorMatch = responseText.match(/<faultstring>(.*?)<\/faultstring>/s);
1900
+ return {
1901
+ success: false,
1902
+ error: errorMatch?.[1] ?? `SOAP HTTP ${response.status}: ${response.statusText}`
1903
+ };
1904
+ }
1905
+ const successMatch = responseText.match(/isSuccess="true"/);
1906
+ if (successMatch) {
1907
+ return { success: true, internalId };
1908
+ }
1909
+ const detailMatch = responseText.match(/<platformCore:message>(.*?)<\/platformCore:message>/s);
806
1910
  return {
807
- message: String(e.detail ?? e.title ?? "Unknown error"),
808
- code: e["o:errorCode"],
809
- details: e
1911
+ success: false,
1912
+ internalId,
1913
+ error: detailMatch?.[1] ?? "SOAP update returned without success flag"
810
1914
  };
811
1915
  }
812
- if (e.message) {
1916
+ /**
1917
+ * Create a record via SOAP (full creation, not just field update).
1918
+ */
1919
+ async addRecord(recordType, fields) {
1920
+ const soapType = SOAP_RECORD_TYPES[recordType];
1921
+ if (!soapType) {
1922
+ return {
1923
+ success: false,
1924
+ error: `Unsupported SOAP record type: ${recordType}`
1925
+ };
1926
+ }
1927
+ const fieldXml = this.buildFieldXml(fields, soapType.namespace);
1928
+ const envelope = this.buildAddEnvelope(soapType, fieldXml);
1929
+ const normalizedId = this.accountId.toLowerCase().replace(/_/g, "-");
1930
+ const soapUrl = `https://${normalizedId}.suitetalk.api.netsuite.com/services/NetSuitePort_2024_1`;
1931
+ const response = await fetch(soapUrl, {
1932
+ method: "POST",
1933
+ headers: {
1934
+ "Content-Type": "text/xml; charset=utf-8",
1935
+ SOAPAction: "add"
1936
+ },
1937
+ body: envelope
1938
+ });
1939
+ const responseText = await response.text();
1940
+ if (!response.ok) {
1941
+ const errorMatch = responseText.match(/<faultstring>(.*?)<\/faultstring>/s);
1942
+ return {
1943
+ success: false,
1944
+ error: errorMatch?.[1] ?? `SOAP HTTP ${response.status}: ${response.statusText}`
1945
+ };
1946
+ }
1947
+ const successMatch = responseText.match(/isSuccess="true"/);
1948
+ const idMatch = responseText.match(/internalId="(\d+)"/);
1949
+ if (successMatch) {
1950
+ return { success: true, internalId: idMatch?.[1] };
1951
+ }
1952
+ const detailMatch = responseText.match(/<platformCore:message>(.*?)<\/platformCore:message>/s);
813
1953
  return {
814
- message: String(e.message),
815
- code: e.code
1954
+ success: false,
1955
+ error: detailMatch?.[1] ?? "SOAP add returned without success flag"
816
1956
  };
817
1957
  }
818
- return { message: JSON.stringify(error) };
819
- }
1958
+ // ─── Private helpers ──────────────────────────────────────────────────────
1959
+ buildFieldXml(fields, ns) {
1960
+ const prefix = ns;
1961
+ const parts = [];
1962
+ for (const [key, value] of Object.entries(fields)) {
1963
+ if (value === null || value === void 0) continue;
1964
+ if (typeof value === "object" && value !== null && "id" in value) {
1965
+ parts.push(`<${prefix}:${key} internalId="${value.id}"/>`);
1966
+ } else if (typeof value === "object" && value !== null && "items" in value) {
1967
+ const items = value.items;
1968
+ const listParts = [];
1969
+ for (const item of items) {
1970
+ Object.entries(item).map(([k, v]) => {
1971
+ if (typeof v === "object" && v !== null && "id" in v) {
1972
+ return `<${prefix}:${k} internalId="${v.id}"/>`;
1973
+ }
1974
+ return `<${prefix}:${k}>${String(v)}</${prefix}:${k}>`;
1975
+ }).join("\n ");
1976
+ listParts.push(`<core:recordRef internalId="${item.id ?? ""}"/>`);
1977
+ }
1978
+ parts.push(`<${prefix}:${key}List>
1979
+ ${listParts.join("\n ")}
1980
+ </${prefix}:${key}List>`);
1981
+ } else if (typeof value === "boolean") {
1982
+ parts.push(`<${prefix}:${key}>${value}</${prefix}:${key}>`);
1983
+ } else {
1984
+ parts.push(`<${prefix}:${key}>${String(value)}</${prefix}:${key}>`);
1985
+ }
1986
+ }
1987
+ return parts.join("\n ");
1988
+ }
1989
+ buildTokenPassport() {
1990
+ const nonce = crypto.randomBytes(16).toString("hex");
1991
+ const timestamp = Math.floor(Date.now() / 1e3).toString();
1992
+ const baseString = `${this.accountId}&${this.auth.consumerKey}&${this.auth.tokenKey}&${nonce}&${timestamp}`;
1993
+ const signingKey = `${this.auth.consumerSecret}&${this.auth.tokenSecret}`;
1994
+ const signature = crypto.createHmac("sha256", signingKey).update(baseString).digest("base64");
1995
+ return `
1996
+ <urn:tokenPassport>
1997
+ <core:account>${this.accountId}</core:account>
1998
+ <core:consumerKey>${this.auth.consumerKey}</core:consumerKey>
1999
+ <core:token>${this.auth.tokenKey}</core:token>
2000
+ <core:nonce>${nonce}</core:nonce>
2001
+ <core:timestamp>${timestamp}</core:timestamp>
2002
+ <core:signature algorithm="HMAC-SHA256">${signature}</core:signature>
2003
+ </urn:tokenPassport>`;
2004
+ }
2005
+ buildUpdateEnvelope(soapType, internalId, fieldXml) {
2006
+ const nsUri = NS_NAMESPACES[soapType.namespace];
2007
+ return `<?xml version="1.0" encoding="UTF-8"?>
2008
+ <soapenv:Envelope
2009
+ xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
2010
+ xmlns:urn="${NS_NAMESPACES.messages}"
2011
+ xmlns:core="${NS_NAMESPACES.core}"
2012
+ xmlns:${soapType.namespace}="${nsUri}"
2013
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
2014
+ <soapenv:Header>${this.buildTokenPassport()}
2015
+ </soapenv:Header>
2016
+ <soapenv:Body>
2017
+ <urn:update>
2018
+ <urn:record xsi:type="${soapType.namespace}:${soapType.type}" internalId="${internalId}">
2019
+ ${fieldXml}
2020
+ </urn:record>
2021
+ </urn:update>
2022
+ </soapenv:Body>
2023
+ </soapenv:Envelope>`;
2024
+ }
2025
+ buildAddEnvelope(soapType, fieldXml) {
2026
+ const nsUri = NS_NAMESPACES[soapType.namespace];
2027
+ return `<?xml version="1.0" encoding="UTF-8"?>
2028
+ <soapenv:Envelope
2029
+ xmlns:soapenv="http://schemas.xmlsoap.org/soap/envelope/"
2030
+ xmlns:urn="${NS_NAMESPACES.messages}"
2031
+ xmlns:core="${NS_NAMESPACES.core}"
2032
+ xmlns:${soapType.namespace}="${nsUri}"
2033
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
2034
+ <soapenv:Header>${this.buildTokenPassport()}
2035
+ </soapenv:Header>
2036
+ <soapenv:Body>
2037
+ <urn:add>
2038
+ <urn:record xsi:type="${soapType.namespace}:${soapType.type}">
2039
+ ${fieldXml}
2040
+ </urn:record>
2041
+ </urn:add>
2042
+ </soapenv:Body>
2043
+ </soapenv:Envelope>`;
2044
+ }
2045
+ };
820
2046
 
821
- // src/utils/url-builder.ts
822
- function normalizeAccountId(accountId) {
823
- return accountId.toLowerCase().replace(/_/g, "-");
824
- }
2047
+ // src/index.ts
2048
+ var import_response_cache = __toESM(require_response_cache());
2049
+ var import_rate_limiter = __toESM(require_rate_limiter());
2050
+ var import_validation = __toESM(require_validation());
2051
+ var import_date = __toESM(require_date());
2052
+ var import_error_parser = __toESM(require_error_parser());
2053
+ var import_url_builder = __toESM(require_url_builder());
2054
+ var export_NetSuiteClient = import_client.NetSuiteClient;
2055
+ var export_NetSuiteError = import_errors.NetSuiteError;
2056
+ var export_RateLimiter = import_rate_limiter.RateLimiter;
2057
+ var export_ResponseCache = import_response_cache.ResponseCache;
2058
+ var export_SuiteQLBuilder = import_query_builder.SuiteQLBuilder;
2059
+ var export_createCacheKey = import_response_cache.createCacheKey;
2060
+ var export_formatNetSuiteDate = import_date.formatNetSuiteDate;
2061
+ var export_normalizeAccountId = import_url_builder.normalizeAccountId;
2062
+ var export_parseNetSuiteDate = import_date.parseNetSuiteDate;
2063
+ var export_parseNetSuiteError = import_error_parser.parseNetSuiteError;
2064
+ var export_suiteql = import_query_builder.suiteql;
2065
+ var export_validateConfig = import_validation.validateConfig;
825
2066
 
826
- exports.NetSuiteClient = NetSuiteClient;
827
- exports.NetSuiteError = NetSuiteError;
828
- exports.RateLimiter = RateLimiter;
829
- exports.ResponseCache = ResponseCache;
830
- exports.SuiteQLBuilder = SuiteQLBuilder;
831
- exports.createCacheKey = createCacheKey;
832
- exports.formatNetSuiteDate = formatNetSuiteDate;
833
- exports.normalizeAccountId = normalizeAccountId;
834
- exports.parseNetSuiteDate = parseNetSuiteDate;
835
- exports.parseNetSuiteError = parseNetSuiteError;
836
- exports.suiteql = suiteql;
837
- exports.validateConfig = validateConfig;
2067
+ exports.NetSuiteClient = export_NetSuiteClient;
2068
+ exports.NetSuiteError = export_NetSuiteError;
2069
+ exports.RateLimiter = export_RateLimiter;
2070
+ exports.ResponseCache = export_ResponseCache;
2071
+ exports.SOAP_ONLY_FIELDS = SOAP_ONLY_FIELDS;
2072
+ exports.SoapFieldClient = SoapFieldClient;
2073
+ exports.SuiteQLBuilder = export_SuiteQLBuilder;
2074
+ exports.createCacheKey = export_createCacheKey;
2075
+ exports.extractSoapOnlyFields = extractSoapOnlyFields;
2076
+ exports.formatNetSuiteDate = export_formatNetSuiteDate;
2077
+ exports.normalizeAccountId = export_normalizeAccountId;
2078
+ exports.parseNetSuiteDate = export_parseNetSuiteDate;
2079
+ exports.parseNetSuiteError = export_parseNetSuiteError;
2080
+ exports.suiteql = export_suiteql;
2081
+ exports.validateConfig = export_validateConfig;
838
2082
  //# sourceMappingURL=index.js.map
839
2083
  //# sourceMappingURL=index.js.map