@beel_es/sdk 1.0.0 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (106) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +234 -74
  3. package/dist/index.d.mts +26774 -0
  4. package/dist/index.d.ts +26769 -21
  5. package/dist/index.js +1556 -50
  6. package/dist/index.js.map +1 -1
  7. package/dist/index.mjs +1497 -0
  8. package/dist/index.mjs.map +1 -0
  9. package/package.json +49 -19
  10. package/dist/client.d.ts +0 -54
  11. package/dist/client.d.ts.map +0 -1
  12. package/dist/client.js +0 -94
  13. package/dist/client.js.map +0 -1
  14. package/dist/generated/client/client.gen.d.ts +0 -3
  15. package/dist/generated/client/client.gen.d.ts.map +0 -1
  16. package/dist/generated/client/client.gen.js +0 -240
  17. package/dist/generated/client/client.gen.js.map +0 -1
  18. package/dist/generated/client/index.d.ts +0 -9
  19. package/dist/generated/client/index.d.ts.map +0 -1
  20. package/dist/generated/client/index.js +0 -18
  21. package/dist/generated/client/index.js.map +0 -1
  22. package/dist/generated/client/types.gen.d.ts +0 -118
  23. package/dist/generated/client/types.gen.d.ts.map +0 -1
  24. package/dist/generated/client/types.gen.js +0 -4
  25. package/dist/generated/client/types.gen.js.map +0 -1
  26. package/dist/generated/client/utils.gen.d.ts +0 -34
  27. package/dist/generated/client/utils.gen.d.ts.map +0 -1
  28. package/dist/generated/client/utils.gen.js +0 -242
  29. package/dist/generated/client/utils.gen.js.map +0 -1
  30. package/dist/generated/client.gen.d.ts +0 -13
  31. package/dist/generated/client.gen.d.ts.map +0 -1
  32. package/dist/generated/client.gen.js +0 -7
  33. package/dist/generated/client.gen.js.map +0 -1
  34. package/dist/generated/core/auth.gen.d.ts +0 -19
  35. package/dist/generated/core/auth.gen.d.ts.map +0 -1
  36. package/dist/generated/core/auth.gen.js +0 -19
  37. package/dist/generated/core/auth.gen.js.map +0 -1
  38. package/dist/generated/core/bodySerializer.gen.d.ts +0 -26
  39. package/dist/generated/core/bodySerializer.gen.d.ts.map +0 -1
  40. package/dist/generated/core/bodySerializer.gen.js +0 -61
  41. package/dist/generated/core/bodySerializer.gen.js.map +0 -1
  42. package/dist/generated/core/params.gen.d.ts +0 -44
  43. package/dist/generated/core/params.gen.d.ts.map +0 -1
  44. package/dist/generated/core/params.gen.js +0 -105
  45. package/dist/generated/core/params.gen.js.map +0 -1
  46. package/dist/generated/core/pathSerializer.gen.d.ts +0 -34
  47. package/dist/generated/core/pathSerializer.gen.d.ts.map +0 -1
  48. package/dist/generated/core/pathSerializer.gen.js +0 -116
  49. package/dist/generated/core/pathSerializer.gen.js.map +0 -1
  50. package/dist/generated/core/queryKeySerializer.gen.d.ts +0 -19
  51. package/dist/generated/core/queryKeySerializer.gen.d.ts.map +0 -1
  52. package/dist/generated/core/queryKeySerializer.gen.js +0 -99
  53. package/dist/generated/core/queryKeySerializer.gen.js.map +0 -1
  54. package/dist/generated/core/serverSentEvents.gen.d.ts +0 -72
  55. package/dist/generated/core/serverSentEvents.gen.d.ts.map +0 -1
  56. package/dist/generated/core/serverSentEvents.gen.js +0 -138
  57. package/dist/generated/core/serverSentEvents.gen.js.map +0 -1
  58. package/dist/generated/core/types.gen.d.ts +0 -79
  59. package/dist/generated/core/types.gen.d.ts.map +0 -1
  60. package/dist/generated/core/types.gen.js +0 -4
  61. package/dist/generated/core/types.gen.js.map +0 -1
  62. package/dist/generated/core/utils.gen.d.ts +0 -20
  63. package/dist/generated/core/utils.gen.d.ts.map +0 -1
  64. package/dist/generated/core/utils.gen.js +0 -94
  65. package/dist/generated/core/utils.gen.js.map +0 -1
  66. package/dist/generated/index.d.ts +0 -3
  67. package/dist/generated/index.d.ts.map +0 -1
  68. package/dist/generated/index.js +0 -84
  69. package/dist/generated/index.js.map +0 -1
  70. package/dist/generated/sdk.gen.d.ts +0 -966
  71. package/dist/generated/sdk.gen.d.ts.map +0 -1
  72. package/dist/generated/sdk.gen.js +0 -1490
  73. package/dist/generated/sdk.gen.js.map +0 -1
  74. package/dist/generated/types.gen.d.ts +0 -5646
  75. package/dist/generated/types.gen.d.ts.map +0 -1
  76. package/dist/generated/types.gen.js +0 -4
  77. package/dist/generated/types.gen.js.map +0 -1
  78. package/dist/index.d.ts.map +0 -1
  79. package/dist/resources/companies.d.ts +0 -75
  80. package/dist/resources/companies.d.ts.map +0 -1
  81. package/dist/resources/companies.js +0 -77
  82. package/dist/resources/companies.js.map +0 -1
  83. package/dist/resources/config.d.ts +0 -106
  84. package/dist/resources/config.d.ts.map +0 -1
  85. package/dist/resources/config.js +0 -86
  86. package/dist/resources/config.js.map +0 -1
  87. package/dist/resources/customers.d.ts +0 -172
  88. package/dist/resources/customers.d.ts.map +0 -1
  89. package/dist/resources/customers.js +0 -96
  90. package/dist/resources/customers.js.map +0 -1
  91. package/dist/resources/invoices.d.ts +0 -370
  92. package/dist/resources/invoices.d.ts.map +0 -1
  93. package/dist/resources/invoices.js +0 -174
  94. package/dist/resources/invoices.js.map +0 -1
  95. package/dist/resources/products.d.ts +0 -155
  96. package/dist/resources/products.d.ts.map +0 -1
  97. package/dist/resources/products.js +0 -96
  98. package/dist/resources/products.js.map +0 -1
  99. package/dist/resources/series.d.ts +0 -98
  100. package/dist/resources/series.d.ts.map +0 -1
  101. package/dist/resources/series.js +0 -83
  102. package/dist/resources/series.js.map +0 -1
  103. package/dist/webhooks/index.d.ts +0 -20
  104. package/dist/webhooks/index.d.ts.map +0 -1
  105. package/dist/webhooks/index.js +0 -70
  106. package/dist/webhooks/index.js.map +0 -1
package/dist/index.mjs ADDED
@@ -0,0 +1,1497 @@
1
+ // src/http/client.ts
2
+ import createClient from "openapi-fetch";
3
+
4
+ // src/http/middleware.ts
5
+ import { randomUUID } from "crypto";
6
+
7
+ // src/core/errors.ts
8
+ var BeeLApiError = class extends Error {
9
+ constructor(message, statusCode, code, details, requestId) {
10
+ super(message);
11
+ this.name = "BeeLApiError";
12
+ this.statusCode = statusCode;
13
+ this.code = code;
14
+ this.details = details;
15
+ this.requestId = requestId;
16
+ }
17
+ };
18
+ var BeeLRateLimitError = class extends BeeLApiError {
19
+ constructor(message, retryAfterSeconds, requestId) {
20
+ super(message, 429, "RATE_LIMIT_EXCEEDED", void 0, requestId);
21
+ this.name = "BeeLRateLimitError";
22
+ this.retryAfterSeconds = retryAfterSeconds;
23
+ }
24
+ };
25
+ var BeeLValidationError = class extends BeeLApiError {
26
+ constructor(message, details, requestId) {
27
+ super(message, 422, "UNPROCESSABLE_ENTITY", details, requestId);
28
+ this.name = "BeeLValidationError";
29
+ }
30
+ };
31
+ var BeeLAuthError = class extends BeeLApiError {
32
+ constructor(message, statusCode, requestId) {
33
+ super(
34
+ message,
35
+ statusCode,
36
+ statusCode === 401 ? "UNAUTHORIZED" : "FORBIDDEN",
37
+ void 0,
38
+ requestId
39
+ );
40
+ this.name = "BeeLAuthError";
41
+ }
42
+ };
43
+ var BeeLNotFoundError = class extends BeeLApiError {
44
+ constructor(message, requestId) {
45
+ super(message, 404, "NOT_FOUND", void 0, requestId);
46
+ this.name = "BeeLNotFoundError";
47
+ }
48
+ };
49
+ var BeeLConflictError = class extends BeeLApiError {
50
+ constructor(message, requestId) {
51
+ super(message, 409, "CONFLICT", void 0, requestId);
52
+ this.name = "BeeLConflictError";
53
+ }
54
+ };
55
+ function throwApiError(status, body) {
56
+ const parsed = body;
57
+ const errorData = parsed?.error ?? parsed;
58
+ const message = errorData?.message ?? `API error ${status}`;
59
+ const code = errorData?.code ?? "UNKNOWN";
60
+ const details = errorData?.details;
61
+ const requestId = parsed?.meta?.request_id;
62
+ switch (status) {
63
+ case 401:
64
+ case 403:
65
+ throw new BeeLAuthError(message, status, requestId);
66
+ case 404:
67
+ throw new BeeLNotFoundError(message, requestId);
68
+ case 409:
69
+ throw new BeeLConflictError(message, requestId);
70
+ case 422:
71
+ throw new BeeLValidationError(message, details, requestId);
72
+ case 429: {
73
+ const retryAfter = errorData?.retry_after ?? 60;
74
+ throw new BeeLRateLimitError(message, retryAfter, requestId);
75
+ }
76
+ default:
77
+ throw new BeeLApiError(message, status, code, details, requestId);
78
+ }
79
+ }
80
+
81
+ // src/http/middleware.ts
82
+ var requestMiddleware = {
83
+ async onRequest({ request }) {
84
+ const method = request.method;
85
+ if (["POST", "PUT", "PATCH"].includes(method)) {
86
+ const hasBody = request.headers.get("content-type")?.includes("application/json");
87
+ if (!hasBody) {
88
+ const clone = new Request(request, {
89
+ body: request.body ?? "{}",
90
+ headers: new Headers(request.headers)
91
+ });
92
+ clone.headers.set("Content-Type", "application/json");
93
+ if (method === "POST" && !clone.headers.has("Idempotency-Key")) {
94
+ clone.headers.set("Idempotency-Key", randomUUID());
95
+ }
96
+ return clone;
97
+ }
98
+ }
99
+ if (method === "POST" && !request.headers.has("Idempotency-Key")) {
100
+ request.headers.set("Idempotency-Key", randomUUID());
101
+ }
102
+ return request;
103
+ }
104
+ };
105
+ var errorMiddleware = {
106
+ async onResponse({ response }) {
107
+ if (!response.ok) {
108
+ const body = await response.json().catch(() => null);
109
+ throwApiError(response.status, body);
110
+ }
111
+ return response;
112
+ }
113
+ };
114
+ function createRetryMiddleware(options) {
115
+ return {
116
+ async onError({ error, request }) {
117
+ if (!(error instanceof BeeLApiError)) return;
118
+ if (!(error instanceof BeeLRateLimitError) && error.statusCode < 500) return;
119
+ for (let attempt = 0; attempt < options.maxRetries; attempt++) {
120
+ const delay = error instanceof BeeLRateLimitError ? error.retryAfterSeconds * 1e3 : Math.min(
121
+ options.initialDelayMs * Math.pow(2, attempt) + Math.random() * options.initialDelayMs,
122
+ options.maxDelayMs
123
+ );
124
+ await new Promise((r) => setTimeout(r, delay));
125
+ try {
126
+ if (request.method === "POST") {
127
+ request.headers.set("Idempotency-Key", randomUUID());
128
+ }
129
+ const response = await fetch(request.clone());
130
+ if (response.ok) return response;
131
+ const body = await response.json().catch(() => null);
132
+ throwApiError(response.status, body);
133
+ } catch (retryError) {
134
+ if (!(retryError instanceof BeeLApiError)) throw retryError;
135
+ if (!(retryError instanceof BeeLRateLimitError) && retryError.statusCode < 500) throw retryError;
136
+ if (attempt === options.maxRetries - 1) throw retryError;
137
+ }
138
+ }
139
+ }
140
+ };
141
+ }
142
+
143
+ // src/http/client.ts
144
+ function createBeeLClient(config) {
145
+ const client = createClient({
146
+ baseUrl: config.baseUrl ?? "https://app.beel.es/api",
147
+ headers: {
148
+ Authorization: `Bearer ${config.apiKey}`
149
+ }
150
+ });
151
+ client.use(requestMiddleware);
152
+ client.use(errorMiddleware);
153
+ client.use(
154
+ createRetryMiddleware({
155
+ maxRetries: config.maxRetries ?? 3,
156
+ initialDelayMs: config.retryDelayMs ?? 500,
157
+ maxDelayMs: config.maxRetryDelayMs ?? 3e4
158
+ })
159
+ );
160
+ return client;
161
+ }
162
+
163
+ // src/resources/invoices.ts
164
+ var InvoicesResource = class {
165
+ constructor(client) {
166
+ this.client = client;
167
+ }
168
+ /**
169
+ * List invoices with optional filters and pagination.
170
+ *
171
+ * @example
172
+ * const { invoices, pagination } = await beel.invoices.list({ status: 'ISSUED', limit: 20 });
173
+ */
174
+ async list(params) {
175
+ const { data } = await this.client.GET("/v1/invoices", { params: { query: params } });
176
+ return data.data;
177
+ }
178
+ /**
179
+ * Create a new invoice. An idempotency key is automatically added.
180
+ *
181
+ * @example
182
+ * const invoice = await beel.invoices.create({
183
+ * type: 'STANDARD',
184
+ * recipient: { customer_id: 'uuid' },
185
+ * lines: [{ description: 'Service', quantity: 1, unit_price: 100, discount_percentage: 0 }],
186
+ * });
187
+ */
188
+ async create(body) {
189
+ const { data } = await this.client.POST("/v1/invoices", { body });
190
+ return data.data;
191
+ }
192
+ /** Get an invoice by ID. */
193
+ async get(id) {
194
+ const { data } = await this.client.GET("/v1/invoices/{invoice_id}", { params: { path: { invoice_id: id } } });
195
+ return data.data;
196
+ }
197
+ /** Update a draft invoice. Only draft invoices can be updated. */
198
+ async update(id, body) {
199
+ const { data } = await this.client.PUT("/v1/invoices/{invoice_id}", { params: { path: { invoice_id: id } }, body });
200
+ return data.data;
201
+ }
202
+ /** Delete a draft invoice. Only draft invoices can be deleted. */
203
+ async delete(id) {
204
+ await this.client.DELETE("/v1/invoices/{invoice_id}", { params: { path: { invoice_id: id } } });
205
+ }
206
+ /** Duplicate an invoice, optionally into a different series. */
207
+ async duplicate(id, options) {
208
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/duplicate", { params: { path: { invoice_id: id } }, body: options });
209
+ return data.data;
210
+ }
211
+ /**
212
+ * Issue a draft invoice. Assigns an invoice number and triggers VeriFactu submission.
213
+ * @param options.wait_for_pdf - If true, waits for PDF generation before returning.
214
+ */
215
+ async issue(id, options) {
216
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/issue", { params: { path: { invoice_id: id }, query: options } });
217
+ return data.data;
218
+ }
219
+ /**
220
+ * Mark an invoice as paid.
221
+ * @param options.payment_date - Payment date (defaults to today).
222
+ * @param options.payment_method - Payment method details.
223
+ */
224
+ async markPaid(id, options) {
225
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/mark-paid", { params: { path: { invoice_id: id } }, body: options });
226
+ return data.data;
227
+ }
228
+ /** Mark an invoice as sent (e.g. delivered by other means). */
229
+ async markSent(id, options) {
230
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/mark-sent", { params: { path: { invoice_id: id } }, body: options });
231
+ return data.data;
232
+ }
233
+ /** Revert a paid/sent invoice back to issued status. */
234
+ async revertToIssued(id) {
235
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/revert-to-issued", { params: { path: { invoice_id: id } } });
236
+ return data.data;
237
+ }
238
+ /**
239
+ * Void an issued invoice. Requires a reason (min 10 chars).
240
+ *
241
+ * @example
242
+ * await beel.invoices.void('id', { reason: 'Duplicate invoice sent in error' });
243
+ */
244
+ async void(id, params) {
245
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/void", { params: { path: { invoice_id: id } }, body: params });
246
+ return data.data;
247
+ }
248
+ /** Create a corrective invoice that references the original. */
249
+ async createCorrective(id, body) {
250
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/corrective", { params: { path: { invoice_id: id } }, body });
251
+ return data.data;
252
+ }
253
+ /** Schedule a draft invoice to be issued on a future date. */
254
+ async schedule(id, params) {
255
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/schedule", { params: { path: { invoice_id: id } }, body: params });
256
+ return data.data;
257
+ }
258
+ /** Cancel a scheduled invoice, returning it to draft. */
259
+ async unschedule(id) {
260
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/unschedule", { params: { path: { invoice_id: id } } });
261
+ return data.data;
262
+ }
263
+ /** Change the scheduled date of a scheduled invoice. */
264
+ async reschedule(id, params) {
265
+ const { data } = await this.client.PATCH("/v1/invoices/{invoice_id}/reschedule", { params: { path: { invoice_id: id } }, body: params });
266
+ return data.data;
267
+ }
268
+ /**
269
+ * Get a pre-signed URL to download the invoice PDF.
270
+ * The URL expires in 5 minutes. Use `beel.downloadPdf(id)` for a simpler Buffer download.
271
+ */
272
+ async getPdf(id) {
273
+ const { data } = await this.client.GET("/v1/invoices/{invoice_id}/pdf", { params: { path: { invoice_id: id } } });
274
+ return data.data;
275
+ }
276
+ /** Send an invoice by email. Uses the customer's email by default. */
277
+ async sendEmail(id, options) {
278
+ const { data } = await this.client.POST("/v1/invoices/{invoice_id}/send", { params: { path: { invoice_id: id } }, body: options });
279
+ return data.data;
280
+ }
281
+ };
282
+
283
+ // src/resources/customers.ts
284
+ var CustomersResource = class {
285
+ constructor(client) {
286
+ this.client = client;
287
+ }
288
+ /**
289
+ * List customers with optional filters and pagination.
290
+ *
291
+ * @example
292
+ * const { customers, pagination } = await beel.customers.list({ search: 'Acme', limit: 10 });
293
+ */
294
+ async list(params) {
295
+ const { data } = await this.client.GET("/v1/customers", { params: { query: params } });
296
+ return data.data;
297
+ }
298
+ /**
299
+ * Create a new customer.
300
+ *
301
+ * @example
302
+ * const customer = await beel.customers.create({
303
+ * legal_name: 'Acme SL',
304
+ * nif: 'B12345678',
305
+ * address: { street: 'Calle Mayor', number: '1', postal_code: '28001', city: 'Madrid', province: 'Madrid', country: 'Spain', country_code: 'ES' },
306
+ * });
307
+ */
308
+ async create(body) {
309
+ const { data } = await this.client.POST("/v1/customers", { body });
310
+ return data.data;
311
+ }
312
+ /** Get a customer by ID. */
313
+ async get(id) {
314
+ const { data } = await this.client.GET("/v1/customers/{customer_id}", { params: { path: { customer_id: id } } });
315
+ return data.data;
316
+ }
317
+ /** Update a customer. Only provided fields are changed. */
318
+ async update(id, body) {
319
+ const { data } = await this.client.PUT("/v1/customers/{customer_id}", { params: { path: { customer_id: id } }, body });
320
+ return data.data;
321
+ }
322
+ /** Deactivate (soft-delete) a customer. */
323
+ async deactivate(id) {
324
+ await this.client.DELETE("/v1/customers/{customer_id}", { params: { path: { customer_id: id } } });
325
+ }
326
+ };
327
+
328
+ // src/resources/products.ts
329
+ var ProductsResource = class {
330
+ constructor(client) {
331
+ this.client = client;
332
+ }
333
+ /**
334
+ * List products with optional filters and pagination.
335
+ *
336
+ * @example
337
+ * const { products, pagination } = await beel.products.list({ category: 'SERVICE' });
338
+ */
339
+ async list(params) {
340
+ const { data } = await this.client.GET("/v1/products", { params: { query: params } });
341
+ return data.data;
342
+ }
343
+ /**
344
+ * Create a new product or service.
345
+ *
346
+ * @example
347
+ * const product = await beel.products.create({
348
+ * name: 'Consulting',
349
+ * code: 'CONS-001',
350
+ * category: 'SERVICE',
351
+ * default_price: 100,
352
+ * main_tax: { type: 'IVA', percentage: 21 },
353
+ * });
354
+ */
355
+ async create(body) {
356
+ const { data } = await this.client.POST("/v1/products", { body });
357
+ return data.data;
358
+ }
359
+ /** Get a product by ID. */
360
+ async get(id) {
361
+ const { data } = await this.client.GET("/v1/products/{product_id}", { params: { path: { product_id: id } } });
362
+ return data.data;
363
+ }
364
+ /** Update a product. Only provided fields are changed. */
365
+ async update(id, body) {
366
+ const { data } = await this.client.PUT("/v1/products/{product_id}", { params: { path: { product_id: id } }, body });
367
+ return data.data;
368
+ }
369
+ /** Delete a product permanently. */
370
+ async delete(id) {
371
+ await this.client.DELETE("/v1/products/{product_id}", { params: { path: { product_id: id } } });
372
+ }
373
+ /**
374
+ * Search products by name or code. Returns up to `limit` results.
375
+ *
376
+ * @example
377
+ * const results = await beel.products.search('consulting', 5);
378
+ */
379
+ async search(q, limit) {
380
+ const { data } = await this.client.GET("/v1/products/search", { params: { query: { q, limit } } });
381
+ return data.data;
382
+ }
383
+ };
384
+
385
+ // src/resources/configuration.ts
386
+ var ConfigurationResource = class {
387
+ constructor(client) {
388
+ this.client = client;
389
+ }
390
+ /** Get the current tax configuration (default VAT, IRPF, etc.). */
391
+ async getTaxConfig() {
392
+ const { data } = await this.client.GET("/v1/configuration/taxes");
393
+ return data.data;
394
+ }
395
+ /** Update tax configuration. */
396
+ async updateTaxConfig(body) {
397
+ const { data } = await this.client.PUT("/v1/configuration/taxes", { body });
398
+ return data.data;
399
+ }
400
+ /** Get available tax types (IVA/IGIC rates, IRPF types, equivalence surcharges). */
401
+ async getTaxTypes() {
402
+ const { data } = await this.client.GET("/v1/configuration/tax-types");
403
+ return data.data;
404
+ }
405
+ /** Get invoice customization options (logo, colors, footer text, etc.). */
406
+ async getInvoiceCustomizationOptions() {
407
+ const { data } = await this.client.GET("/v1/configuration/invoice-customization-options");
408
+ return data.data;
409
+ }
410
+ /** Update the user's preferred language (es, en, ca). */
411
+ async updateLanguage(language) {
412
+ const { data } = await this.client.PUT("/v1/configuration/language", { body: { language } });
413
+ return data.data;
414
+ }
415
+ /** Get VeriFactu configuration (enabled, certificate status, etc.). */
416
+ async getVerifactu() {
417
+ const { data } = await this.client.GET("/v1/configuration/verifactu");
418
+ return data.data;
419
+ }
420
+ /** Update VeriFactu configuration. */
421
+ async updateVerifactu(body) {
422
+ const { data } = await this.client.PUT("/v1/configuration/verifactu", { body });
423
+ return data.data;
424
+ }
425
+ };
426
+
427
+ // src/resources/series.ts
428
+ var SeriesResource = class {
429
+ constructor(client) {
430
+ this.client = client;
431
+ }
432
+ /**
433
+ * List all invoice series. Optionally filter by active status.
434
+ *
435
+ * @example
436
+ * const series = await beel.series.list();
437
+ * const activeSeries = await beel.series.list(true);
438
+ */
439
+ async list(active) {
440
+ const { data } = await this.client.GET("/v1/configuration/series", {
441
+ params: { query: active !== void 0 ? { active } : void 0 }
442
+ });
443
+ return data.data;
444
+ }
445
+ /** Create a new invoice series (e.g. "A-2026", "RECT"). */
446
+ async create(body) {
447
+ const { data } = await this.client.POST("/v1/configuration/series", { body });
448
+ return data.data;
449
+ }
450
+ /** Update a series (name, description, etc.). */
451
+ async update(id, body) {
452
+ const { data } = await this.client.PUT("/v1/configuration/series/{series_id}", {
453
+ params: { path: { series_id: id } },
454
+ body
455
+ });
456
+ return data.data;
457
+ }
458
+ /** Delete an invoice series. Only empty series can be deleted. */
459
+ async delete(id) {
460
+ await this.client.DELETE("/v1/configuration/series/{series_id}", {
461
+ params: { path: { series_id: id } }
462
+ });
463
+ }
464
+ /** Set a series as the default for new invoices. */
465
+ async setDefault(id) {
466
+ const { data } = await this.client.POST("/v1/configuration/series/{series_id}/default", {
467
+ params: { path: { series_id: id } }
468
+ });
469
+ return data.data;
470
+ }
471
+ };
472
+
473
+ // src/resources/nif.ts
474
+ var NifResource = class {
475
+ constructor(client) {
476
+ this.client = client;
477
+ }
478
+ /**
479
+ * Validate a Spanish NIF/CIF against the AEAT tax registry.
480
+ *
481
+ * @example
482
+ * const result = await beel.nif.validate('B12345678');
483
+ * console.log(result.valid, result.name);
484
+ */
485
+ async validate(nif) {
486
+ const { data } = await this.client.POST("/v1/nif/validate", { body: { nif } });
487
+ return data.data;
488
+ }
489
+ };
490
+
491
+ // src/resources/accounts.ts
492
+ var AccountsResource = class {
493
+ constructor(client) {
494
+ this.client = client;
495
+ }
496
+ /** List accounts reachable with this API key (cursor-paginated). */
497
+ async list(params) {
498
+ const { data } = await this.client.GET("/v1/accounts", { params: { query: params } });
499
+ return data.data;
500
+ }
501
+ /** Provision a new managed account. */
502
+ async provision(body) {
503
+ const { data } = await this.client.POST("/v1/accounts", { body });
504
+ return data.data;
505
+ }
506
+ /** Get a managed account by ID. */
507
+ async get(accountId) {
508
+ const { data } = await this.client.GET("/v1/accounts/{account_id}", {
509
+ params: { path: { account_id: accountId } }
510
+ });
511
+ return data.data;
512
+ }
513
+ /** Alias of `beel.account(accountId)` — returns an account-scoped facade. */
514
+ scope(accountId) {
515
+ return new AccountScope(this.client, accountId);
516
+ }
517
+ };
518
+ var AccountScope = class {
519
+ constructor(client, accountId) {
520
+ this.client = client;
521
+ this.accountId = accountId;
522
+ this.members = new AccountMembersResource(client, accountId);
523
+ this.invitations = new AccountInvitationsResource(client, accountId);
524
+ this.webhooks = new AccountWebhooksResource(client, accountId);
525
+ this.companies = new AccountCompaniesResource(client, accountId);
526
+ }
527
+ path() {
528
+ return { account_id: this.accountId };
529
+ }
530
+ /** Get the account summary. */
531
+ async get() {
532
+ const { data } = await this.client.GET("/v1/accounts/{account_id}", { params: { path: this.path() } });
533
+ return data.data;
534
+ }
535
+ /** Provisioning usage counters (accounts, NIFs) for billing purposes. */
536
+ async usage() {
537
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/usage", { params: { path: this.path() } });
538
+ return data.data;
539
+ }
540
+ /** Change the manager's access level over this account. */
541
+ async changeAccessLevel(body) {
542
+ await this.client.PATCH("/v1/accounts/{account_id}/access-level", {
543
+ params: { path: this.path() },
544
+ body
545
+ });
546
+ }
547
+ /** End the management relationship with this account. */
548
+ async endManagement() {
549
+ await this.client.DELETE("/v1/accounts/{account_id}/management", { params: { path: this.path() } });
550
+ }
551
+ /** Create a claim token so the end user can take ownership of the account. */
552
+ async createClaimToken(body) {
553
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/claim-tokens", {
554
+ params: { path: this.path() },
555
+ body: body ?? {}
556
+ });
557
+ return data.data;
558
+ }
559
+ /** Transfer account ownership to an existing member. */
560
+ async setOwner(body) {
561
+ await this.client.PUT("/v1/accounts/{account_id}/owner", {
562
+ params: { path: this.path() },
563
+ body
564
+ });
565
+ }
566
+ };
567
+ var AccountMembersResource = class {
568
+ constructor(client, accountId) {
569
+ this.client = client;
570
+ this.accountId = accountId;
571
+ }
572
+ async list() {
573
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/members", {
574
+ params: { path: { account_id: this.accountId } }
575
+ });
576
+ return data.data.members;
577
+ }
578
+ async get(memberId) {
579
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/members/{member_id}", {
580
+ params: { path: { account_id: this.accountId, member_id: memberId } }
581
+ });
582
+ return data.data;
583
+ }
584
+ /** Update a member's account role. */
585
+ async update(memberId, body) {
586
+ const { data } = await this.client.PATCH("/v1/accounts/{account_id}/members/{member_id}", {
587
+ params: { path: { account_id: this.accountId, member_id: memberId } },
588
+ body
589
+ });
590
+ return data.data;
591
+ }
592
+ /** Remove a member from the account. */
593
+ async remove(memberId) {
594
+ await this.client.DELETE("/v1/accounts/{account_id}/members/{member_id}", {
595
+ params: { path: { account_id: this.accountId, member_id: memberId } }
596
+ });
597
+ }
598
+ /** List a member's per-company grants. */
599
+ async listGrants(memberId) {
600
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/members/{member_id}/grants", {
601
+ params: { path: { account_id: this.accountId, member_id: memberId } }
602
+ });
603
+ return data.data;
604
+ }
605
+ /** Grant (or replace) a member's permissions over one company. */
606
+ async putGrant(memberId, companyId, body) {
607
+ const { data } = await this.client.PUT("/v1/accounts/{account_id}/members/{member_id}/grants/{company_id}", {
608
+ params: { path: { account_id: this.accountId, member_id: memberId, company_id: companyId } },
609
+ body
610
+ });
611
+ return data.data;
612
+ }
613
+ /** Revoke a member's grant over one company. */
614
+ async removeGrant(memberId, companyId) {
615
+ await this.client.DELETE("/v1/accounts/{account_id}/members/{member_id}/grants/{company_id}", {
616
+ params: { path: { account_id: this.accountId, member_id: memberId, company_id: companyId } }
617
+ });
618
+ }
619
+ };
620
+ var AccountInvitationsResource = class {
621
+ constructor(client, accountId) {
622
+ this.client = client;
623
+ this.accountId = accountId;
624
+ }
625
+ async list() {
626
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/invitations", {
627
+ params: { path: { account_id: this.accountId } }
628
+ });
629
+ return data.data;
630
+ }
631
+ async create(body) {
632
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/invitations", {
633
+ params: { path: { account_id: this.accountId } },
634
+ body
635
+ });
636
+ return data.data;
637
+ }
638
+ async get(invitationId) {
639
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/invitations/{invitation_id}", {
640
+ params: { path: { account_id: this.accountId, invitation_id: invitationId } }
641
+ });
642
+ return data.data;
643
+ }
644
+ async revoke(invitationId) {
645
+ await this.client.DELETE("/v1/accounts/{account_id}/invitations/{invitation_id}", {
646
+ params: { path: { account_id: this.accountId, invitation_id: invitationId } }
647
+ });
648
+ }
649
+ };
650
+ var AccountWebhooksResource = class {
651
+ constructor(client, accountId) {
652
+ this.client = client;
653
+ this.accountId = accountId;
654
+ }
655
+ async list(params) {
656
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/webhooks", {
657
+ params: { path: { account_id: this.accountId }, query: params }
658
+ });
659
+ return data.data;
660
+ }
661
+ async create(body) {
662
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/webhooks", {
663
+ params: { path: { account_id: this.accountId } },
664
+ body
665
+ });
666
+ return data.data;
667
+ }
668
+ async get(webhookId) {
669
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/webhooks/{webhook_id}", {
670
+ params: { path: { account_id: this.accountId, webhook_id: webhookId } }
671
+ });
672
+ return data.data;
673
+ }
674
+ async update(webhookId, body) {
675
+ const { data } = await this.client.PATCH("/v1/accounts/{account_id}/webhooks/{webhook_id}", {
676
+ params: { path: { account_id: this.accountId, webhook_id: webhookId } },
677
+ body
678
+ });
679
+ return data.data;
680
+ }
681
+ async delete(webhookId) {
682
+ await this.client.DELETE("/v1/accounts/{account_id}/webhooks/{webhook_id}", {
683
+ params: { path: { account_id: this.accountId, webhook_id: webhookId } }
684
+ });
685
+ }
686
+ /** Send a test event to the webhook endpoint. */
687
+ async test(webhookId) {
688
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/webhooks/{webhook_id}/test", {
689
+ params: { path: { account_id: this.accountId, webhook_id: webhookId } }
690
+ });
691
+ return data.data;
692
+ }
693
+ /** Rotate the webhook signing secret. */
694
+ async rotateSecret(webhookId) {
695
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/webhooks/{webhook_id}/secret", {
696
+ params: { path: { account_id: this.accountId, webhook_id: webhookId } }
697
+ });
698
+ return data.data;
699
+ }
700
+ async listDeliveries(webhookId, params) {
701
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/webhooks/{webhook_id}/deliveries", {
702
+ params: { path: { account_id: this.accountId, webhook_id: webhookId }, query: params }
703
+ });
704
+ return data.data;
705
+ }
706
+ async retryDelivery(webhookId, deliveryId) {
707
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/webhooks/{webhook_id}/deliveries/{delivery_id}/retry", {
708
+ params: { path: { account_id: this.accountId, webhook_id: webhookId, delivery_id: deliveryId } }
709
+ });
710
+ return data.data;
711
+ }
712
+ };
713
+ var AccountCompaniesResource = class {
714
+ constructor(client, accountId) {
715
+ this.client = client;
716
+ this.accountId = accountId;
717
+ }
718
+ async list(params) {
719
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/companies", {
720
+ params: { path: { account_id: this.accountId }, query: params }
721
+ });
722
+ return { companies: data.data ?? [], pagination: data.pagination };
723
+ }
724
+ /** Register a new company (NIF) under the account. */
725
+ async create(body) {
726
+ const { data } = await this.client.POST("/v1/accounts/{account_id}/companies", {
727
+ params: { path: { account_id: this.accountId } },
728
+ body
729
+ });
730
+ return data.data;
731
+ }
732
+ /** Aggregated per-company stats for the account. */
733
+ async stats() {
734
+ const { data } = await this.client.GET("/v1/accounts/{account_id}/companies/stats", {
735
+ params: { path: { account_id: this.accountId } }
736
+ });
737
+ return data.data;
738
+ }
739
+ };
740
+
741
+ // src/resources/company.ts
742
+ var CompanyScope = class {
743
+ constructor(client, companyId) {
744
+ this.client = client;
745
+ this.companyId = companyId;
746
+ this.invoices = new CompanyInvoicesResource(client, companyId);
747
+ this.customers = new CompanyCustomersResource(client, companyId);
748
+ this.products = new CompanyProductsResource(client, companyId);
749
+ this.series = new CompanySeriesResource(client, companyId);
750
+ this.recurringInvoices = new CompanyRecurringInvoicesResource(client, companyId);
751
+ }
752
+ path() {
753
+ return { company_id: this.companyId };
754
+ }
755
+ /** Get the company. */
756
+ async get(params) {
757
+ const { data } = await this.client.GET("/v1/companies/{company_id}", {
758
+ params: { path: this.path(), query: params }
759
+ });
760
+ return data.data;
761
+ }
762
+ /** Update company data. */
763
+ async update(body) {
764
+ const { data } = await this.client.PATCH("/v1/companies/{company_id}", {
765
+ params: { path: this.path() },
766
+ body
767
+ });
768
+ return data.data;
769
+ }
770
+ /** Delete the company. */
771
+ async delete() {
772
+ await this.client.DELETE("/v1/companies/{company_id}", { params: { path: this.path() } });
773
+ }
774
+ /** Fiscal summary (VAT/IRPF aggregates) for the company. */
775
+ async fiscalSummary(params) {
776
+ const { data } = await this.client.GET("/v1/companies/{company_id}/fiscal-summary", {
777
+ params: { path: this.path(), query: params }
778
+ });
779
+ return data.data;
780
+ }
781
+ /** Whether the company can already issue invoices, and what is missing if not. */
782
+ async issuingReadiness() {
783
+ const { data } = await this.client.GET("/v1/companies/{company_id}/issuing-readiness", {
784
+ params: { path: this.path() }
785
+ });
786
+ return data.data;
787
+ }
788
+ };
789
+ var CompanyInvoicesResource = class {
790
+ constructor(client, companyId) {
791
+ this.client = client;
792
+ this.companyId = companyId;
793
+ }
794
+ path(rest) {
795
+ return { company_id: this.companyId, ...rest };
796
+ }
797
+ async list(params) {
798
+ const { data } = await this.client.GET("/v1/companies/{company_id}/invoices", {
799
+ params: { path: this.path(), query: params }
800
+ });
801
+ return data.data;
802
+ }
803
+ async create(body, params) {
804
+ const { data } = await this.client.POST("/v1/companies/{company_id}/invoices", {
805
+ params: { path: this.path(), query: params },
806
+ body
807
+ });
808
+ return data.data;
809
+ }
810
+ async get(invoiceId) {
811
+ const { data } = await this.client.GET("/v1/companies/{company_id}/invoices/{invoice_id}", {
812
+ params: { path: this.path({ invoice_id: invoiceId }) }
813
+ });
814
+ return data.data;
815
+ }
816
+ /** Update a draft invoice. */
817
+ async update(invoiceId, body) {
818
+ const { data } = await this.client.PATCH("/v1/companies/{company_id}/invoices/{invoice_id}", {
819
+ params: { path: this.path({ invoice_id: invoiceId }) },
820
+ body
821
+ });
822
+ return data.data;
823
+ }
824
+ /** Delete a draft invoice. */
825
+ async delete(invoiceId) {
826
+ await this.client.DELETE("/v1/companies/{company_id}/invoices/{invoice_id}", {
827
+ params: { path: this.path({ invoice_id: invoiceId }) }
828
+ });
829
+ }
830
+ /** Issue a draft invoice (assigns number, submits to VeriFactu when configured). */
831
+ async issue(invoiceId, params) {
832
+ const { data } = await this.client.POST("/v1/companies/{company_id}/invoices/{invoice_id}/issue", {
833
+ params: { path: this.path({ invoice_id: invoiceId }), query: params }
834
+ });
835
+ return data.data;
836
+ }
837
+ /** Void an issued invoice. */
838
+ async void(invoiceId, body) {
839
+ const { data } = await this.client.POST("/v1/companies/{company_id}/invoices/{invoice_id}/void", {
840
+ params: { path: this.path({ invoice_id: invoiceId }) },
841
+ body
842
+ });
843
+ return data.data;
844
+ }
845
+ /** Create a corrective (rectificativa) for an issued invoice. */
846
+ async createCorrective(invoiceId, body) {
847
+ const { data } = await this.client.POST("/v1/companies/{company_id}/invoices/{invoice_id}/corrective", {
848
+ params: { path: this.path({ invoice_id: invoiceId }) },
849
+ body
850
+ });
851
+ return data.data;
852
+ }
853
+ /** Convert a proforma into an invoice. */
854
+ async convertToInvoice(invoiceId, body) {
855
+ const { data } = await this.client.POST("/v1/companies/{company_id}/invoices/{invoice_id}/convert-to-invoice", {
856
+ params: { path: this.path({ invoice_id: invoiceId }) },
857
+ body
858
+ });
859
+ return data.data;
860
+ }
861
+ /** Update payment status (e.g. mark as paid). */
862
+ async setStatus(invoiceId, body) {
863
+ const { data } = await this.client.PUT("/v1/companies/{company_id}/invoices/{invoice_id}/status", {
864
+ params: { path: this.path({ invoice_id: invoiceId }) },
865
+ body
866
+ });
867
+ return data.data;
868
+ }
869
+ /** Get PDF metadata and download URL. */
870
+ async getPdf(invoiceId) {
871
+ const { data } = await this.client.GET("/v1/companies/{company_id}/invoices/{invoice_id}/pdf", {
872
+ params: { path: this.path({ invoice_id: invoiceId }) }
873
+ });
874
+ return data.data;
875
+ }
876
+ /** Send the invoice by email to the customer. */
877
+ async send(invoiceId, body) {
878
+ const { data } = await this.client.POST("/v1/companies/{company_id}/invoices/{invoice_id}/send", {
879
+ params: { path: this.path({ invoice_id: invoiceId }) },
880
+ body
881
+ });
882
+ return data.data;
883
+ }
884
+ };
885
+ var CompanyCustomersResource = class {
886
+ constructor(client, companyId) {
887
+ this.client = client;
888
+ this.companyId = companyId;
889
+ }
890
+ async list(params) {
891
+ const { data } = await this.client.GET("/v1/companies/{company_id}/customers", {
892
+ params: { path: { company_id: this.companyId }, query: params }
893
+ });
894
+ return data.data;
895
+ }
896
+ async create(body) {
897
+ const { data } = await this.client.POST("/v1/companies/{company_id}/customers", {
898
+ params: { path: { company_id: this.companyId } },
899
+ body
900
+ });
901
+ return data.data;
902
+ }
903
+ async createBulk(body) {
904
+ const { data } = await this.client.POST("/v1/companies/{company_id}/customers/bulk", {
905
+ params: { path: { company_id: this.companyId } },
906
+ body
907
+ });
908
+ return data.data;
909
+ }
910
+ async get(customerId) {
911
+ const { data } = await this.client.GET("/v1/companies/{company_id}/customers/{customer_id}", {
912
+ params: { path: { company_id: this.companyId, customer_id: customerId } }
913
+ });
914
+ return data.data;
915
+ }
916
+ async update(customerId, body) {
917
+ const { data } = await this.client.PATCH("/v1/companies/{company_id}/customers/{customer_id}", {
918
+ params: { path: { company_id: this.companyId, customer_id: customerId } },
919
+ body
920
+ });
921
+ return data.data;
922
+ }
923
+ async delete(customerId) {
924
+ await this.client.DELETE("/v1/companies/{company_id}/customers/{customer_id}", {
925
+ params: { path: { company_id: this.companyId, customer_id: customerId } }
926
+ });
927
+ }
928
+ };
929
+ var CompanyProductsResource = class {
930
+ constructor(client, companyId) {
931
+ this.client = client;
932
+ this.companyId = companyId;
933
+ }
934
+ async list(params) {
935
+ const { data } = await this.client.GET("/v1/companies/{company_id}/products", {
936
+ params: { path: { company_id: this.companyId }, query: params }
937
+ });
938
+ return data.data;
939
+ }
940
+ async create(body) {
941
+ const { data } = await this.client.POST("/v1/companies/{company_id}/products", {
942
+ params: { path: { company_id: this.companyId } },
943
+ body
944
+ });
945
+ return data.data;
946
+ }
947
+ async get(productId) {
948
+ const { data } = await this.client.GET("/v1/companies/{company_id}/products/{product_id}", {
949
+ params: { path: { company_id: this.companyId, product_id: productId } }
950
+ });
951
+ return data.data;
952
+ }
953
+ async update(productId, body) {
954
+ const { data } = await this.client.PATCH("/v1/companies/{company_id}/products/{product_id}", {
955
+ params: { path: { company_id: this.companyId, product_id: productId } },
956
+ body
957
+ });
958
+ return data.data;
959
+ }
960
+ async delete(productId) {
961
+ await this.client.DELETE("/v1/companies/{company_id}/products/{product_id}", {
962
+ params: { path: { company_id: this.companyId, product_id: productId } }
963
+ });
964
+ }
965
+ };
966
+ var CompanySeriesResource = class {
967
+ constructor(client, companyId) {
968
+ this.client = client;
969
+ this.companyId = companyId;
970
+ }
971
+ async list(params) {
972
+ const { data } = await this.client.GET("/v1/companies/{company_id}/series", {
973
+ params: { path: { company_id: this.companyId }, query: params }
974
+ });
975
+ return data.data;
976
+ }
977
+ async create(body) {
978
+ const { data } = await this.client.POST("/v1/companies/{company_id}/series", {
979
+ params: { path: { company_id: this.companyId } },
980
+ body
981
+ });
982
+ return data.data;
983
+ }
984
+ async update(seriesId, body) {
985
+ const { data } = await this.client.PATCH("/v1/companies/{company_id}/series/{series_id}", {
986
+ params: { path: { company_id: this.companyId, series_id: seriesId } },
987
+ body
988
+ });
989
+ return data.data;
990
+ }
991
+ async delete(seriesId) {
992
+ await this.client.DELETE("/v1/companies/{company_id}/series/{series_id}", {
993
+ params: { path: { company_id: this.companyId, series_id: seriesId } }
994
+ });
995
+ }
996
+ /** Current default series per invoice type. */
997
+ async getDefaults() {
998
+ const { data } = await this.client.GET("/v1/companies/{company_id}/series/defaults", {
999
+ params: { path: { company_id: this.companyId } }
1000
+ });
1001
+ return data.data;
1002
+ }
1003
+ /** Ensure the three typed default series exist (idempotent seeding). */
1004
+ async ensureDefaults() {
1005
+ const { data } = await this.client.PUT("/v1/companies/{company_id}/series/defaults", {
1006
+ params: { path: { company_id: this.companyId } }
1007
+ });
1008
+ return data.data;
1009
+ }
1010
+ /** Mark a series as the default for its invoice type. */
1011
+ async setDefault(seriesId) {
1012
+ const { data } = await this.client.PUT("/v1/companies/{company_id}/series/{series_id}/default", {
1013
+ params: { path: { company_id: this.companyId, series_id: seriesId } }
1014
+ });
1015
+ return data.data;
1016
+ }
1017
+ };
1018
+ var CompanyRecurringInvoicesResource = class {
1019
+ constructor(client, companyId) {
1020
+ this.client = client;
1021
+ this.companyId = companyId;
1022
+ }
1023
+ path(rest) {
1024
+ return { company_id: this.companyId, ...rest };
1025
+ }
1026
+ async list(params) {
1027
+ const { data } = await this.client.GET("/v1/companies/{company_id}/recurring-invoices", {
1028
+ params: { path: this.path(), query: params }
1029
+ });
1030
+ return data.data;
1031
+ }
1032
+ async create(body) {
1033
+ const { data } = await this.client.POST("/v1/companies/{company_id}/recurring-invoices", {
1034
+ params: { path: this.path() },
1035
+ body
1036
+ });
1037
+ return data.data;
1038
+ }
1039
+ async get(recurringInvoiceId) {
1040
+ const { data } = await this.client.GET("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}", {
1041
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) }
1042
+ });
1043
+ return data.data;
1044
+ }
1045
+ async update(recurringInvoiceId, body) {
1046
+ const { data } = await this.client.PATCH("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}", {
1047
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) },
1048
+ body
1049
+ });
1050
+ return data.data;
1051
+ }
1052
+ async delete(recurringInvoiceId) {
1053
+ await this.client.DELETE("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}", {
1054
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) }
1055
+ });
1056
+ }
1057
+ /** Pause or resume the schedule. */
1058
+ async setStatus(recurringInvoiceId, body) {
1059
+ const { data } = await this.client.PUT("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}/status", {
1060
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) },
1061
+ body
1062
+ });
1063
+ return data.data;
1064
+ }
1065
+ /** Skip the next scheduled occurrence. */
1066
+ async skip(recurringInvoiceId) {
1067
+ const { data } = await this.client.POST("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}/skip", {
1068
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) }
1069
+ });
1070
+ return data.data;
1071
+ }
1072
+ /** Generate the next invoice now instead of waiting for the schedule. */
1073
+ async generateNow(recurringInvoiceId) {
1074
+ const { data } = await this.client.POST("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}/generate", {
1075
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) }
1076
+ });
1077
+ return data.data;
1078
+ }
1079
+ async nextOccurrence(recurringInvoiceId) {
1080
+ const { data } = await this.client.GET("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}/next-occurrence", {
1081
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }) }
1082
+ });
1083
+ return data.data;
1084
+ }
1085
+ async history(recurringInvoiceId, params) {
1086
+ const { data } = await this.client.GET("/v1/companies/{company_id}/recurring-invoices/{recurring_invoice_id}/history", {
1087
+ params: { path: this.path({ recurring_invoice_id: recurringInvoiceId }), query: params }
1088
+ });
1089
+ return data.data;
1090
+ }
1091
+ };
1092
+
1093
+ // src/client.ts
1094
+ var BeeL = class {
1095
+ constructor(config) {
1096
+ const client = createBeeLClient(config);
1097
+ this._client = client;
1098
+ this.invoices = new InvoicesResource(client);
1099
+ this.customers = new CustomersResource(client);
1100
+ this.products = new ProductsResource(client);
1101
+ this.configuration = new ConfigurationResource(client);
1102
+ this.series = new SeriesResource(client);
1103
+ this.nif = new NifResource(client);
1104
+ this.accounts = new AccountsResource(client);
1105
+ }
1106
+ /**
1107
+ * Returns a facade scoped to one company (NIF) — the explicit multi-NIF surface.
1108
+ * All operations address the company in the path, no session focus needed.
1109
+ *
1110
+ * @example
1111
+ * ```typescript
1112
+ * const company = beel.company('company-uuid');
1113
+ * const { invoices } = await company.invoices.list({ status: 'ISSUED' });
1114
+ * ```
1115
+ */
1116
+ company(companyId) {
1117
+ return new CompanyScope(this._client, companyId);
1118
+ }
1119
+ /**
1120
+ * Returns a facade scoped to one managed account — members, invitations,
1121
+ * account webhooks, companies, usage. Symmetric with {@link company}.
1122
+ *
1123
+ * @example
1124
+ * ```typescript
1125
+ * const account = beel.account('account-uuid');
1126
+ * const members = await account.members.list();
1127
+ * ```
1128
+ */
1129
+ account(accountId) {
1130
+ return new AccountScope(this._client, accountId);
1131
+ }
1132
+ /**
1133
+ * Download an invoice PDF as a Buffer.
1134
+ *
1135
+ * @deprecated Relies on the deprecated session-focus PDF endpoint. Use
1136
+ * `beel.company(companyId).invoices.getPdf(invoiceId)` and fetch `download_url` instead.
1137
+ *
1138
+ * @example
1139
+ * ```typescript
1140
+ * const { buffer, fileName } = await beel.downloadPdf('invoice-uuid');
1141
+ * fs.writeFileSync(fileName, buffer);
1142
+ * ```
1143
+ */
1144
+ async downloadPdf(invoiceId) {
1145
+ const pdf = await this.invoices.getPdf(invoiceId);
1146
+ const response = await fetch(pdf.download_url);
1147
+ if (!response.ok) throw new Error(`Failed to download PDF: ${response.status}`);
1148
+ const arrayBuffer = await response.arrayBuffer();
1149
+ return { buffer: Buffer.from(arrayBuffer), fileName: pdf.file_name };
1150
+ }
1151
+ };
1152
+
1153
+ // src/webhooks/verifier.ts
1154
+ import { createHmac, timingSafeEqual } from "crypto";
1155
+ var WebhookVerifier = class {
1156
+ /**
1157
+ * Creates a new WebhookVerifier
1158
+ *
1159
+ * @param secret - Your webhook secret from BeeL dashboard
1160
+ * @param toleranceSeconds - Maximum age of webhook events (default: 300 = 5 minutes)
1161
+ */
1162
+ constructor(secret, toleranceSeconds = 300) {
1163
+ if (!secret || secret.trim().length === 0) {
1164
+ throw new Error("Webhook secret is required");
1165
+ }
1166
+ this.secret = secret;
1167
+ this.toleranceSeconds = toleranceSeconds;
1168
+ }
1169
+ /**
1170
+ * Verify a webhook signature and return the parsed event
1171
+ *
1172
+ * @param rawBody - Raw request body (string or Buffer, before JSON parsing)
1173
+ * @param signatureHeader - Value of the `BeeL-Signature` header
1174
+ * @returns Parsed webhook event
1175
+ * @throws {WebhookVerificationError} If signature is invalid or event is too old
1176
+ *
1177
+ * @example Basic usage
1178
+ * ```typescript
1179
+ * const verifier = new WebhookVerifier('your_secret');
1180
+ * const event = verifier.verify(rawBody, signature);
1181
+ *
1182
+ * if (event.type === 'verifactu.status.updated') {
1183
+ * console.log('Invoice:', event.data.invoice_number);
1184
+ * console.log('Status:', event.data.new_status);
1185
+ * }
1186
+ * ```
1187
+ */
1188
+ verify(rawBody, signatureHeader) {
1189
+ if (!signatureHeader) {
1190
+ throw new WebhookVerificationError("Missing BeeL-Signature header");
1191
+ }
1192
+ const { timestamp, signature } = this.parseSignatureHeader(signatureHeader);
1193
+ const now = Math.floor(Date.now() / 1e3);
1194
+ const age = Math.abs(now - timestamp);
1195
+ if (age > this.toleranceSeconds) {
1196
+ throw new WebhookVerificationError(
1197
+ `Webhook timestamp too old (${age}s ago, max ${this.toleranceSeconds}s allowed)`
1198
+ );
1199
+ }
1200
+ const bodyString = Buffer.isBuffer(rawBody) ? rawBody.toString("utf8") : rawBody;
1201
+ const expectedSignature = this.computeSignature(timestamp, bodyString);
1202
+ if (!this.secureCompare(signature, expectedSignature)) {
1203
+ throw new WebhookVerificationError("Invalid webhook signature");
1204
+ }
1205
+ try {
1206
+ return JSON.parse(bodyString);
1207
+ } catch (error) {
1208
+ throw new WebhookVerificationError("Invalid JSON in webhook body");
1209
+ }
1210
+ }
1211
+ /**
1212
+ * Parse the BeeL-Signature header
1213
+ *
1214
+ * Format: `t=1741362026,v1=3c4f7a2e...`
1215
+ */
1216
+ parseSignatureHeader(header) {
1217
+ const parts = header.split(",");
1218
+ let timestamp;
1219
+ let signature;
1220
+ for (const part of parts) {
1221
+ const [key, value] = part.split("=", 2);
1222
+ if (key === "t") {
1223
+ timestamp = parseInt(value, 10);
1224
+ } else if (key === "v1") {
1225
+ signature = value;
1226
+ }
1227
+ }
1228
+ if (!timestamp || !signature) {
1229
+ throw new WebhookVerificationError(
1230
+ "Invalid signature header format (expected: t=timestamp,v1=signature)"
1231
+ );
1232
+ }
1233
+ if (isNaN(timestamp)) {
1234
+ throw new WebhookVerificationError("Invalid timestamp in signature header");
1235
+ }
1236
+ return { timestamp, signature };
1237
+ }
1238
+ /**
1239
+ * Compute HMAC-SHA256 signature
1240
+ *
1241
+ * Algorithm:
1242
+ * 1. Build signed payload: `{timestamp}.{raw_body}`
1243
+ * 2. Compute: HMAC-SHA256(secret, signed_payload)
1244
+ * 3. Return hex digest
1245
+ */
1246
+ computeSignature(timestamp, body) {
1247
+ const signedPayload = `${timestamp}.${body}`;
1248
+ return createHmac("sha256", this.secret).update(signedPayload, "utf8").digest("hex");
1249
+ }
1250
+ /**
1251
+ * Constant-time string comparison to prevent timing attacks
1252
+ */
1253
+ secureCompare(a, b) {
1254
+ if (a.length !== b.length) {
1255
+ return false;
1256
+ }
1257
+ const bufferA = Buffer.from(a, "utf8");
1258
+ const bufferB = Buffer.from(b, "utf8");
1259
+ return timingSafeEqual(bufferA, bufferB);
1260
+ }
1261
+ };
1262
+ var WebhookVerificationError = class extends Error {
1263
+ constructor(message) {
1264
+ super(message);
1265
+ this.name = "WebhookVerificationError";
1266
+ }
1267
+ };
1268
+
1269
+ // src/generated-webhooks/models/AccountClaimedEvent.ts
1270
+ var AccountClaimedEvent;
1271
+ ((AccountClaimedEvent2) => {
1272
+ let type;
1273
+ ((type2) => {
1274
+ type2["ACCOUNT_CLAIMED"] = "account.claimed";
1275
+ })(type = AccountClaimedEvent2.type || (AccountClaimedEvent2.type = {}));
1276
+ })(AccountClaimedEvent || (AccountClaimedEvent = {}));
1277
+
1278
+ // src/generated-webhooks/models/CompanyCreatedEvent.ts
1279
+ var CompanyCreatedEvent;
1280
+ ((CompanyCreatedEvent2) => {
1281
+ let type;
1282
+ ((type2) => {
1283
+ type2["COMPANY_CREATED"] = "company.created";
1284
+ })(type = CompanyCreatedEvent2.type || (CompanyCreatedEvent2.type = {}));
1285
+ })(CompanyCreatedEvent || (CompanyCreatedEvent = {}));
1286
+
1287
+ // src/generated-webhooks/models/InvoiceEmailSentEvent.ts
1288
+ var InvoiceEmailSentEvent;
1289
+ ((InvoiceEmailSentEvent2) => {
1290
+ let type;
1291
+ ((type2) => {
1292
+ type2["INVOICE_EMAIL_SENT"] = "invoice.email.sent";
1293
+ })(type = InvoiceEmailSentEvent2.type || (InvoiceEmailSentEvent2.type = {}));
1294
+ })(InvoiceEmailSentEvent || (InvoiceEmailSentEvent = {}));
1295
+
1296
+ // src/generated-webhooks/models/InvoiceIssuedEvent.ts
1297
+ var InvoiceIssuedEvent;
1298
+ ((InvoiceIssuedEvent2) => {
1299
+ let type;
1300
+ ((type2) => {
1301
+ type2["INVOICE_ISSUED"] = "invoice.issued";
1302
+ })(type = InvoiceIssuedEvent2.type || (InvoiceIssuedEvent2.type = {}));
1303
+ })(InvoiceIssuedEvent || (InvoiceIssuedEvent = {}));
1304
+
1305
+ // src/generated-webhooks/models/InvoiceVoidedEvent.ts
1306
+ var InvoiceVoidedEvent;
1307
+ ((InvoiceVoidedEvent2) => {
1308
+ let type;
1309
+ ((type2) => {
1310
+ type2["INVOICE_VOIDED"] = "invoice.voided";
1311
+ })(type = InvoiceVoidedEvent2.type || (InvoiceVoidedEvent2.type = {}));
1312
+ })(InvoiceVoidedEvent || (InvoiceVoidedEvent = {}));
1313
+
1314
+ // src/generated-webhooks/models/RecurringInvoicePausedEvent.ts
1315
+ var RecurringInvoicePausedEvent;
1316
+ ((RecurringInvoicePausedEvent2) => {
1317
+ let type;
1318
+ ((type2) => {
1319
+ type2["RECURRING_INVOICE_PAUSED"] = "recurring_invoice.paused";
1320
+ })(type = RecurringInvoicePausedEvent2.type || (RecurringInvoicePausedEvent2.type = {}));
1321
+ })(RecurringInvoicePausedEvent || (RecurringInvoicePausedEvent = {}));
1322
+
1323
+ // src/generated-webhooks/models/RepresentationSignedEvent.ts
1324
+ var RepresentationSignedEvent;
1325
+ ((RepresentationSignedEvent2) => {
1326
+ let type;
1327
+ ((type2) => {
1328
+ type2["REPRESENTATION_SIGNED"] = "representation.signed";
1329
+ })(type = RepresentationSignedEvent2.type || (RepresentationSignedEvent2.type = {}));
1330
+ })(RepresentationSignedEvent || (RepresentationSignedEvent = {}));
1331
+
1332
+ // src/generated-webhooks/models/VeriFactuStatusUpdatedEvent.ts
1333
+ var VeriFactuStatusUpdatedEvent;
1334
+ ((VeriFactuStatusUpdatedEvent2) => {
1335
+ let type;
1336
+ ((type2) => {
1337
+ type2["VERIFACTU_STATUS_UPDATED"] = "verifactu.status.updated";
1338
+ })(type = VeriFactuStatusUpdatedEvent2.type || (VeriFactuStatusUpdatedEvent2.type = {}));
1339
+ })(VeriFactuStatusUpdatedEvent || (VeriFactuStatusUpdatedEvent = {}));
1340
+
1341
+ // src/generated-webhooks/models/VeriFactuSubmissionStatus.ts
1342
+ var VeriFactuSubmissionStatus = /* @__PURE__ */ ((VeriFactuSubmissionStatus2) => {
1343
+ VeriFactuSubmissionStatus2["PENDING"] = "PENDING";
1344
+ VeriFactuSubmissionStatus2["ACCEPTED"] = "ACCEPTED";
1345
+ VeriFactuSubmissionStatus2["VOIDED"] = "VOIDED";
1346
+ VeriFactuSubmissionStatus2["REJECTED"] = "REJECTED";
1347
+ return VeriFactuSubmissionStatus2;
1348
+ })(VeriFactuSubmissionStatus || {});
1349
+
1350
+ // src/generated-webhooks/models/WebhookEventType.ts
1351
+ var WebhookEventType = /* @__PURE__ */ ((WebhookEventType2) => {
1352
+ WebhookEventType2["VERIFACTU_STATUS_UPDATED"] = "verifactu.status.updated";
1353
+ WebhookEventType2["INVOICE_ISSUED"] = "invoice.issued";
1354
+ WebhookEventType2["INVOICE_EMAIL_SENT"] = "invoice.email.sent";
1355
+ WebhookEventType2["INVOICE_VOIDED"] = "invoice.voided";
1356
+ WebhookEventType2["RECURRING_INVOICE_PAUSED"] = "recurring_invoice.paused";
1357
+ WebhookEventType2["ACCOUNT_CLAIMED"] = "account.claimed";
1358
+ WebhookEventType2["COMPANY_CREATED"] = "company.created";
1359
+ WebhookEventType2["REPRESENTATION_SIGNED"] = "representation.signed";
1360
+ return WebhookEventType2;
1361
+ })(WebhookEventType || {});
1362
+
1363
+ // src/builders/customer-builder.ts
1364
+ var CustomerBuilder = class _CustomerBuilder {
1365
+ constructor() {
1366
+ }
1367
+ static create() {
1368
+ return new _CustomerBuilder();
1369
+ }
1370
+ name(name) {
1371
+ this._name = name;
1372
+ return this;
1373
+ }
1374
+ nif(nif) {
1375
+ this._nif = nif;
1376
+ return this;
1377
+ }
1378
+ email(email) {
1379
+ this._email = email;
1380
+ return this;
1381
+ }
1382
+ phone(phone) {
1383
+ this._phone = phone;
1384
+ return this;
1385
+ }
1386
+ address(street, number, postalCode, city, province, country, countryCode = "ES") {
1387
+ this._address = { street, number, postal_code: postalCode, city, province, country, country_code: countryCode };
1388
+ return this;
1389
+ }
1390
+ notes(notes) {
1391
+ this._notes = notes;
1392
+ return this;
1393
+ }
1394
+ build() {
1395
+ if (!this._name || this._name.trim().length === 0) throw new Error("Legal name is required");
1396
+ if (!this._nif || this._nif.trim().length === 0) throw new Error("NIF/CIF is required");
1397
+ if (!this._address) throw new Error("Address is required");
1398
+ return {
1399
+ legal_name: this._name,
1400
+ nif: this._nif,
1401
+ email: this._email,
1402
+ phone: this._phone,
1403
+ address: this._address,
1404
+ notes: this._notes
1405
+ };
1406
+ }
1407
+ };
1408
+
1409
+ // src/builders/invoice-builder.ts
1410
+ var InvoiceBuilder = class _InvoiceBuilder {
1411
+ constructor() {
1412
+ this._type = "STANDARD";
1413
+ this._lines = [];
1414
+ }
1415
+ static create() {
1416
+ return new _InvoiceBuilder();
1417
+ }
1418
+ type(type) {
1419
+ this._type = type;
1420
+ return this;
1421
+ }
1422
+ forCustomer(customerId) {
1423
+ this._customerId = customerId;
1424
+ return this;
1425
+ }
1426
+ operationDate(date) {
1427
+ this._operationDate = date instanceof Date ? date.toISOString().split("T")[0] : date;
1428
+ return this;
1429
+ }
1430
+ dueDate(date) {
1431
+ this._dueDate = date instanceof Date ? date.toISOString().split("T")[0] : date;
1432
+ return this;
1433
+ }
1434
+ addLine(description, quantity, unitPrice, discountPercentage = 0) {
1435
+ this._lines.push({ line_type: "NORMAL", description, quantity, unit_price: unitPrice, discount_percentage: discountPercentage });
1436
+ return this;
1437
+ }
1438
+ addLineObject(line) {
1439
+ this._lines.push(line);
1440
+ return this;
1441
+ }
1442
+ notes(notes) {
1443
+ this._notes = notes;
1444
+ return this;
1445
+ }
1446
+ series(id) {
1447
+ this._seriesId = id;
1448
+ return this;
1449
+ }
1450
+ metadata(data) {
1451
+ this._metadata = data;
1452
+ return this;
1453
+ }
1454
+ build() {
1455
+ if (!this._customerId) throw new Error("Customer ID is required");
1456
+ if (this._lines.length === 0) throw new Error("At least one invoice line is required");
1457
+ const recipient = { customer_id: this._customerId };
1458
+ return {
1459
+ type: this._type,
1460
+ operation_date: this._operationDate,
1461
+ due_date: this._dueDate,
1462
+ recipient,
1463
+ lines: this._lines,
1464
+ notes: this._notes,
1465
+ series_id: this._seriesId,
1466
+ metadata: this._metadata
1467
+ };
1468
+ }
1469
+ };
1470
+ export {
1471
+ AccountCompaniesResource,
1472
+ AccountInvitationsResource,
1473
+ AccountMembersResource,
1474
+ AccountScope,
1475
+ AccountWebhooksResource,
1476
+ AccountsResource,
1477
+ BeeL,
1478
+ BeeLApiError,
1479
+ BeeLAuthError,
1480
+ BeeLConflictError,
1481
+ BeeLNotFoundError,
1482
+ BeeLRateLimitError,
1483
+ BeeLValidationError,
1484
+ CompanyCustomersResource,
1485
+ CompanyInvoicesResource,
1486
+ CompanyProductsResource,
1487
+ CompanyRecurringInvoicesResource,
1488
+ CompanyScope,
1489
+ CompanySeriesResource,
1490
+ CustomerBuilder,
1491
+ InvoiceBuilder,
1492
+ VeriFactuSubmissionStatus,
1493
+ WebhookEventType,
1494
+ WebhookVerificationError,
1495
+ WebhookVerifier
1496
+ };
1497
+ //# sourceMappingURL=index.mjs.map