@chift/chift-nodejs 1.0.1 → 1.0.2

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/CHANGELOG.md CHANGED
@@ -1,9 +1,16 @@
1
1
  # Changelog
2
2
 
3
3
  ## 1.0.0 - 2023-09-14
4
- * First release with scopes of the 5 unified APIs (Accounting, POS, eCommerce, Invoicing & Payment) of Chift and the management of consumers, connections & webhooks.
5
- * Review of tests and CI-pipeline
4
+
5
+ - First release with scopes of the 5 unified APIs (Accounting, POS, eCommerce, Invoicing & Payment) of Chift and the management of consumers, connections & webhooks.
6
+ - Review of tests and CI-pipeline
6
7
 
7
8
  ## 1.0.1 - 2023-09-21
8
- * Update accounting model
9
- * add getOutstandings route
9
+
10
+ - Update accounting model
11
+ - add getOutstandings route
12
+
13
+ ## 1.0.2 - 2023-10-02
14
+
15
+ - add createFinancialEntry params
16
+ - add createJournalEntry route
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@chift/chift-nodejs",
3
- "version": "1.0.1",
3
+ "version": "1.0.2",
4
4
  "description": "The Chift NodeJS library provides convenient access to the Chift API from applications written in the NodeJS language (Javascript/Typescript).",
5
5
  "main": "dist/src/index.js",
6
6
  "types": "dist/src/index.d.ts",
@@ -358,14 +358,25 @@ const accountingFactory = {
358
358
  };
359
359
  },
360
360
  createFinancialEntry(
361
- financial_entry: components['schemas']['FinancialEntryItemIn']
361
+ financial_entry: components['schemas']['FinancialEntryItemIn'],
362
+ params: operations['accounting_create_financial_entry']['parameters']['query']
362
363
  ): RequestData<components['schemas']['FinancialEntryItemOut']> {
363
364
  return {
365
+ params,
364
366
  method: 'post',
365
367
  url: '/consumers/{consumer_id}/accounting/financial-entry',
366
368
  body: financial_entry,
367
369
  };
368
370
  },
371
+ createJournalEntry(
372
+ journal_entry: components['schemas']['JournalEntryIn']
373
+ ): RequestData<components['schemas']['JournalEntryMultiAnalyticPlan']> {
374
+ return {
375
+ method: 'post',
376
+ url: '/consumers/{consumer_id}/accounting/journal/entries',
377
+ body: journal_entry,
378
+ };
379
+ },
369
380
  };
370
381
 
371
382
  export { accountingFactory };
@@ -64,6 +64,10 @@ export interface paths {
64
64
  */
65
65
  get: operations['integrations_get_integrations'];
66
66
  };
67
+ '/integrations/{integrationid}/{image_type}.json': {
68
+ /** Returns a logo/icon of an integration (as base64) */
69
+ get: operations['integrations_get_integration_logo_json'];
70
+ };
67
71
  '/webhooks/list': {
68
72
  /**
69
73
  * Get list of possible webhooks
@@ -1946,7 +1950,7 @@ export interface components {
1946
1950
  account_number: string;
1947
1951
  /**
1948
1952
  * Partner Id
1949
- * @description Must be filled in it is a 'customer_account' or 'supplier_account' line type.
1953
+ * @description Must be filled in it is a 'customer_account', 'supplier_account' or 'employee_account' line type.
1950
1954
  */
1951
1955
  partner_id?: string;
1952
1956
  /**
@@ -1964,7 +1968,7 @@ export interface components {
1964
1968
  account_number: string;
1965
1969
  /**
1966
1970
  * Partner Id
1967
- * @description Must be filled in it is a 'customer_account' or 'supplier_account' line type.
1971
+ * @description Must be filled in it is a 'customer_account', 'supplier_account' or 'employee_account' line type.
1968
1972
  */
1969
1973
  partner_id?: string;
1970
1974
  /**
@@ -2078,6 +2082,12 @@ export interface components {
2078
2082
  /** Url */
2079
2083
  url: string;
2080
2084
  };
2085
+ /**
2086
+ * ImageType
2087
+ * @description An enumeration.
2088
+ * @enum {unknown}
2089
+ */
2090
+ ImageType: 'icon' | 'logo';
2081
2091
  /** IntegrationItem */
2082
2092
  IntegrationItem: {
2083
2093
  /** Integrationid */
@@ -2086,6 +2096,10 @@ export interface components {
2086
2096
  name: string;
2087
2097
  status: components['schemas']['app__routers__integrations__Status'];
2088
2098
  api: components['schemas']['Api'];
2099
+ /** Logo Url */
2100
+ logo_url: string;
2101
+ /** Icon Url */
2102
+ icon_url: string;
2089
2103
  /**
2090
2104
  * Credentials
2091
2105
  * @description List of credentials that must be specified to create a connection. Can be used if you want to pass credentials on connection creation. Not compatible with oAuth2 routes.
@@ -3115,6 +3129,13 @@ export interface components {
3115
3129
  /** Url */
3116
3130
  url: string;
3117
3131
  };
3132
+ /** LogoImage */
3133
+ LogoImage: {
3134
+ /** Integrationid */
3135
+ integrationid: string;
3136
+ /** Data */
3137
+ data: string;
3138
+ };
3118
3139
  /** MappingItem */
3119
3140
  MappingItem: {
3120
3141
  /** Source Id */
@@ -5817,6 +5838,35 @@ export interface operations {
5817
5838
  };
5818
5839
  };
5819
5840
  };
5841
+ /** Returns a logo/icon of an integration (as base64) */
5842
+ integrations_get_integration_logo_json: {
5843
+ parameters: {
5844
+ path: {
5845
+ integrationid: number;
5846
+ image_type: components['schemas']['ImageType'];
5847
+ };
5848
+ };
5849
+ responses: {
5850
+ /** @description Successful Response */
5851
+ 200: {
5852
+ content: {
5853
+ 'application/json': components['schemas']['LogoImage'];
5854
+ };
5855
+ };
5856
+ /** @description Not Found */
5857
+ 404: {
5858
+ content: {
5859
+ 'application/json': components['schemas']['ChiftError'];
5860
+ };
5861
+ };
5862
+ /** @description Validation Error */
5863
+ 422: {
5864
+ content: {
5865
+ 'application/json': components['schemas']['HTTPValidationError'];
5866
+ };
5867
+ };
5868
+ };
5869
+ };
5820
5870
  /**
5821
5871
  * Get list of possible webhooks
5822
5872
  * @description Returns a list of webhook that are available for your account
@@ -7944,6 +7994,10 @@ export interface operations {
7944
7994
  */
7945
7995
  accounting_create_financial_entry: {
7946
7996
  parameters: {
7997
+ query?: {
7998
+ /** @description Counterpart account number of the bank/cash journal. This will be retrieved from the accounting settings if left empty. */
7999
+ financial_counterpart_account?: string;
8000
+ };
7947
8001
  path: {
7948
8002
  consumer_id: string;
7949
8003
  };
@@ -40,6 +40,19 @@ test('getJournals', async () => {
40
40
  expect(journals[0]).toHaveProperty('journal_type', expect.any(String));
41
41
  });
42
42
 
43
+ let vatCodes: components['schemas']['app__routers__accounting__VatCode'][];
44
+ test('getVatCodes', async () => {
45
+ vatCodes = await consumer.accounting.getVatCodes();
46
+ expect(vatCodes).toBeInstanceOf(Array);
47
+ expect(vatCodes.length).toBeGreaterThan(0);
48
+ expect(vatCodes[0]).toHaveProperty('id', expect.any(String));
49
+ expect(vatCodes[0]).toHaveProperty('code');
50
+ expect(vatCodes[0]).toHaveProperty('label', expect.any(String));
51
+ expect(vatCodes[0]).toHaveProperty('scope', expect.any(String));
52
+ expect(vatCodes[0]).toHaveProperty('rate', expect.any(Number));
53
+ expect(vatCodes[0]).toHaveProperty('type', expect.any(String));
54
+ });
55
+
43
56
  test('createClient', async () => {
44
57
  const body: components['schemas']['ClientItemIn'] = {
45
58
  external_reference: 'sdk test',
@@ -164,6 +177,16 @@ test('updateSupplier', async () => {
164
177
  });
165
178
 
166
179
  test('createInvoice', async () => {
180
+ const journal = journals.find((journal) => journal.journal_type === 'customer_invoice');
181
+ if (!journal) {
182
+ throw new Error('No journal with type "customer_invoice" found to create invoice');
183
+ }
184
+
185
+ const vatCode = vatCodes.find((vatCode) => vatCode.type === 'sale' && vatCode.rate === 21);
186
+ if (!vatCode?.id) {
187
+ throw new Error('No vat code with type "sale" and rate 21 found to create invoice');
188
+ }
189
+
167
190
  const body: components['schemas']['InvoiceItemInMonoAnalyticPlan'] = {
168
191
  invoice_type: 'customer_invoice',
169
192
  invoice_date: '2022-12-01',
@@ -173,7 +196,7 @@ test('createInvoice', async () => {
173
196
  tax_amount: 21,
174
197
  total: 121,
175
198
  partner_id: clients[0]?.id as string,
176
- journal_id: journals[0].id,
199
+ journal_id: journal.id,
177
200
  lines: [
178
201
  {
179
202
  description: 'Test',
@@ -184,7 +207,7 @@ test('createInvoice', async () => {
184
207
  tax_amount: 21,
185
208
  total: 121,
186
209
  account_number: '700000',
187
- tax_code: '1',
210
+ tax_code: vatCode.id,
188
211
  },
189
212
  ],
190
213
  };
@@ -243,6 +266,18 @@ test('getInvoice', async () => {
243
266
  });
244
267
 
245
268
  test('createInvoiceWithMultiplePlans', async () => {
269
+ const journal = journals.find((journal) => journal.journal_type === 'customer_invoice');
270
+ if (!journal) {
271
+ throw new Error(
272
+ 'No journal with type customer_invoice found to create Invoice With Multiple Plans'
273
+ );
274
+ }
275
+
276
+ const vatCode = vatCodes.find((vatCode) => vatCode.type === 'sale' && vatCode.rate === 21);
277
+ if (!vatCode?.id) {
278
+ throw new Error('No vat code with type "sale" and rate 21 found to create invoice');
279
+ }
280
+
246
281
  const body: components['schemas']['InvoiceItemInMonoAnalyticPlan'] = {
247
282
  invoice_type: 'customer_invoice',
248
283
  invoice_date: '2022-12-01',
@@ -252,7 +287,7 @@ test('createInvoiceWithMultiplePlans', async () => {
252
287
  tax_amount: 21,
253
288
  total: 121,
254
289
  partner_id: clients[0]?.id as string,
255
- journal_id: journals[0].id,
290
+ journal_id: journal.id,
256
291
  lines: [
257
292
  {
258
293
  description: 'Test',
@@ -263,7 +298,7 @@ test('createInvoiceWithMultiplePlans', async () => {
263
298
  tax_amount: 21,
264
299
  total: 121,
265
300
  account_number: '700000',
266
- tax_code: '1',
301
+ tax_code: vatCode.id,
267
302
  },
268
303
  ],
269
304
  };
@@ -374,6 +409,35 @@ test('getAnalyticLinesOfAccount', async () => {
374
409
  }
375
410
  });
376
411
 
412
+ test('createJournalEntry', async () => {
413
+ const journal = journals.find((journal) => journal.journal_type === 'customer_invoice');
414
+ if (!journal) {
415
+ throw new Error('No journal with type "customer_invoice" found to create journal entry');
416
+ }
417
+ const journalEntry = await consumer.accounting.createJournalEntry({
418
+ journal_id: journal.id,
419
+ name: Date.now().toString(),
420
+ date: '2022-01-01',
421
+ items: [
422
+ {
423
+ account_number: clients[0].account_number,
424
+ credit: 0,
425
+ debit: 10,
426
+ partner_id: clients[0].id,
427
+ currency: 'EUR',
428
+ },
429
+ {
430
+ account_number: '700000',
431
+ credit: 10,
432
+ debit: 0,
433
+ currency: 'EUR',
434
+ },
435
+ ],
436
+ });
437
+ expect(journalEntry).toBeTruthy();
438
+ expect(journalEntry).toHaveProperty('journal_id', journal.id);
439
+ });
440
+
377
441
  test('getJournalEntries', async () => {
378
442
  const journalEntries = await consumer.accounting.getJournalEntries({
379
443
  unposted_allowed: true,
@@ -399,18 +463,6 @@ test('getPaymentsByInvoiceId', async () => {
399
463
  expect(payments).toBeInstanceOf(Array);
400
464
  });
401
465
 
402
- test('getVatCodes', async () => {
403
- const vatCodes = await consumer.accounting.getVatCodes();
404
- expect(vatCodes).toBeInstanceOf(Array);
405
- expect(vatCodes.length).toBeGreaterThan(0);
406
- expect(vatCodes[0]).toHaveProperty('id', expect.any(String));
407
- expect(vatCodes[0]).toHaveProperty('code');
408
- expect(vatCodes[0]).toHaveProperty('label', expect.any(String));
409
- expect(vatCodes[0]).toHaveProperty('scope', expect.any(String));
410
- expect(vatCodes[0]).toHaveProperty('rate', expect.any(Number));
411
- expect(vatCodes[0]).toHaveProperty('type', expect.any(String));
412
- });
413
-
414
466
  let miscOperations: components['schemas']['MiscellaneousOperationOut'][];
415
467
  test('getMiscOperations', async () => {
416
468
  miscOperations = await consumer.accounting.getMiscOperations();
@@ -485,13 +537,48 @@ test('getBalanceOfAccounts', async () => {
485
537
  test('getEmployees', async () => {
486
538
  const employees = await consumer.accounting.getEmployees();
487
539
  expect(employees).toBeTruthy();
488
- expect(employees.items).toBeInstanceOf(Array);
489
540
  });
490
541
 
491
542
  test('getOutstandings', async () => {
492
- const outstandings = await consumer.accounting.getOutstandings({
493
- type: 'client',
543
+ expect.assertions(1);
544
+ try {
545
+ const outstandings = await consumer.accounting.getOutstandings({
546
+ type: 'client',
547
+ unposted_allowed: true,
548
+ });
549
+ expect(outstandings).toBeTruthy();
550
+ expect(outstandings.items).toBeInstanceOf(Array);
551
+ } catch (e: any) {
552
+ if (e?.error?.error_code) {
553
+ expect(e.error.error_code).toMatch('ERROR_API_RESOURCE_NOT_FOUND');
554
+ return;
555
+ }
556
+
557
+ throw e;
558
+ }
559
+ });
560
+
561
+ test('createFinancialEntry', async () => {
562
+ const journal = journals.find((journal) => journal.journal_type === 'financial_operation');
563
+ if (!journal) {
564
+ throw new Error(
565
+ 'No journal with type "financial_operation" found to create financial entry'
566
+ );
567
+ }
568
+
569
+ const financialEntry = await consumer.accounting.createFinancialEntry({
570
+ date: '2022-01-01',
571
+ journal_id: journal.id,
572
+ currency: 'EUR',
573
+ items: [
574
+ {
575
+ type: 'customer_account',
576
+ account_number: clients[0].account_number,
577
+ partner_id: clients[0].id,
578
+ amount: 10,
579
+ },
580
+ ],
494
581
  });
495
- expect(outstandings).toBeTruthy();
496
- expect(outstandings.items).toBeInstanceOf(Array);
582
+ expect(financialEntry).toBeTruthy();
583
+ expect(financialEntry).toHaveProperty('journal_id', journal.id);
497
584
  });
@@ -51,7 +51,9 @@ test('getConsumers', async () => {
51
51
  test('getConsumersByName', async () => {
52
52
  const consumersWithName = await client.Consumers.getConsumersByName(consumerName);
53
53
  expect(consumersWithName).toBeInstanceOf(Array);
54
- expect(consumersWithName[0]).toHaveProperty('name', consumerName);
54
+ expect(consumersWithName.some((consumer: any) => consumer.name.includes(consumerName))).toBe(
55
+ true
56
+ );
55
57
  });
56
58
 
57
59
  test('getConsumerById', async () => {