@profplum700/etsy-v3-api-client 2.4.1 → 2.4.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.cjs CHANGED
@@ -1435,6 +1435,24 @@ class EtsyClient {
1435
1435
  sleep(ms) {
1436
1436
  return new Promise(resolve => setTimeout(resolve, ms));
1437
1437
  }
1438
+ buildFormBody(params) {
1439
+ const body = new URLSearchParams();
1440
+ for (const [key, value] of Object.entries(params)) {
1441
+ if (value === undefined || value === null)
1442
+ continue;
1443
+ if (Array.isArray(value)) {
1444
+ for (const item of value) {
1445
+ if (item === undefined || item === null)
1446
+ continue;
1447
+ body.append(key, String(item));
1448
+ }
1449
+ }
1450
+ else {
1451
+ body.append(key, String(value));
1452
+ }
1453
+ }
1454
+ return body;
1455
+ }
1438
1456
  getApiKey() {
1439
1457
  if (this.sharedSecret) {
1440
1458
  return `${this.keystring}:${this.sharedSecret}`;
@@ -1494,19 +1512,37 @@ class EtsyClient {
1494
1512
  searchParams.set('sort_order', params.sort_order);
1495
1513
  if (params.includes)
1496
1514
  searchParams.set('includes', params.includes.join(','));
1515
+ if (params.legacy !== undefined) {
1516
+ searchParams.set('legacy', params.legacy.toString());
1517
+ }
1497
1518
  const response = await this.makeRequest(`/shops/${targetShopId}/listings?${searchParams.toString()}`);
1498
1519
  return response.results;
1499
1520
  }
1500
- async getListing(listingId, includes) {
1501
- const params = includes ? `?includes=${includes.join(',')}` : '';
1502
- return this.makeRequest(`/listings/${listingId}${params}`);
1521
+ async getListing(listingId, params) {
1522
+ const resolvedParams = Array.isArray(params)
1523
+ ? { includes: params }
1524
+ : params;
1525
+ const searchParams = new URLSearchParams();
1526
+ if (resolvedParams?.includes) {
1527
+ searchParams.set('includes', resolvedParams.includes.join(','));
1528
+ }
1529
+ if (resolvedParams?.language) {
1530
+ searchParams.set('language', resolvedParams.language);
1531
+ }
1532
+ if (resolvedParams?.legacy !== undefined) {
1533
+ searchParams.set('legacy', resolvedParams.legacy.toString());
1534
+ }
1535
+ if (resolvedParams?.allow_suggested_title !== undefined) {
1536
+ searchParams.set('allow_suggested_title', resolvedParams.allow_suggested_title.toString());
1537
+ }
1538
+ const query = searchParams.toString();
1539
+ const suffix = query ? `?${query}` : '';
1540
+ return this.makeRequest(`/listings/${listingId}${suffix}`);
1503
1541
  }
1504
1542
  async findAllListingsActive(params = {}) {
1505
1543
  const searchParams = new URLSearchParams();
1506
1544
  if (params.keywords)
1507
1545
  searchParams.set('keywords', params.keywords);
1508
- if (params.category)
1509
- searchParams.set('category', params.category);
1510
1546
  if (params.limit !== undefined)
1511
1547
  searchParams.set('limit', params.limit.toString());
1512
1548
  if (params.offset !== undefined)
@@ -1519,12 +1555,14 @@ class EtsyClient {
1519
1555
  searchParams.set('min_price', params.min_price.toString());
1520
1556
  if (params.max_price !== undefined)
1521
1557
  searchParams.set('max_price', params.max_price.toString());
1522
- if (params.tags)
1523
- searchParams.set('tags', params.tags.join(','));
1524
- if (params.location)
1525
- searchParams.set('location', params.location);
1558
+ if (params.taxonomy_id !== undefined) {
1559
+ searchParams.set('taxonomy_id', params.taxonomy_id.toString());
1560
+ }
1526
1561
  if (params.shop_location)
1527
1562
  searchParams.set('shop_location', params.shop_location);
1563
+ if (params.legacy !== undefined) {
1564
+ searchParams.set('legacy', params.legacy.toString());
1565
+ }
1528
1566
  const response = await this.makeRequest(`/listings/active?${searchParams.toString()}`);
1529
1567
  return response.results;
1530
1568
  }
@@ -1532,15 +1570,58 @@ class EtsyClient {
1532
1570
  const response = await this.makeRequest(`/listings/${listingId}/images`);
1533
1571
  return response.results;
1534
1572
  }
1535
- async getListingInventory(listingId) {
1536
- return this.makeRequest(`/listings/${listingId}/inventory`);
1573
+ async getListingInventory(listingId, params = {}) {
1574
+ const searchParams = new URLSearchParams();
1575
+ if (params.show_deleted !== undefined) {
1576
+ searchParams.set('show_deleted', params.show_deleted.toString());
1577
+ }
1578
+ if (params.includes) {
1579
+ searchParams.set('includes', params.includes);
1580
+ }
1581
+ if (params.legacy !== undefined) {
1582
+ searchParams.set('legacy', params.legacy.toString());
1583
+ }
1584
+ const query = searchParams.toString();
1585
+ const suffix = query ? `?${query}` : '';
1586
+ return this.makeRequest(`/listings/${listingId}/inventory${suffix}`);
1587
+ }
1588
+ async getReviewsByListing(listingId, params = {}) {
1589
+ const searchParams = new URLSearchParams();
1590
+ if (params.limit !== undefined)
1591
+ searchParams.set('limit', params.limit.toString());
1592
+ if (params.offset !== undefined)
1593
+ searchParams.set('offset', params.offset.toString());
1594
+ if (params.min_created !== undefined) {
1595
+ searchParams.set('min_created', params.min_created.toString());
1596
+ }
1597
+ if (params.max_created !== undefined) {
1598
+ searchParams.set('max_created', params.max_created.toString());
1599
+ }
1600
+ const response = await this.makeRequest(`/listings/${listingId}/reviews?${searchParams.toString()}`);
1601
+ return response.results;
1602
+ }
1603
+ async getReviewsByShop(shopId, params = {}) {
1604
+ const searchParams = new URLSearchParams();
1605
+ if (params.limit !== undefined)
1606
+ searchParams.set('limit', params.limit.toString());
1607
+ if (params.offset !== undefined)
1608
+ searchParams.set('offset', params.offset.toString());
1609
+ if (params.min_created !== undefined) {
1610
+ searchParams.set('min_created', params.min_created.toString());
1611
+ }
1612
+ if (params.max_created !== undefined) {
1613
+ searchParams.set('max_created', params.max_created.toString());
1614
+ }
1615
+ const response = await this.makeRequest(`/shops/${shopId}/reviews?${searchParams.toString()}`);
1616
+ return response.results;
1537
1617
  }
1538
1618
  async getSellerTaxonomyNodes() {
1539
1619
  const response = await this.makeRequest('/seller-taxonomy/nodes');
1540
1620
  return response.results;
1541
1621
  }
1542
1622
  async getUserShops() {
1543
- const response = await this.makeRequest('/users/me/shops');
1623
+ const user = await this.getUser();
1624
+ const response = await this.makeRequest(`/users/${user.user_id}/shops`);
1544
1625
  return response.results || [];
1545
1626
  }
1546
1627
  async updateShop(shopId, params, options) {
@@ -1557,21 +1638,27 @@ class EtsyClient {
1557
1638
  }
1558
1639
  }
1559
1640
  }
1641
+ const body = this.buildFormBody(params);
1560
1642
  return this.makeRequest(`/shops/${shopId}`, {
1561
1643
  method: 'PUT',
1562
- body: JSON.stringify(params)
1644
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1645
+ body: body.toString()
1563
1646
  }, false);
1564
1647
  }
1565
1648
  async createShopSection(shopId, params) {
1649
+ const body = this.buildFormBody(params);
1566
1650
  return this.makeRequest(`/shops/${shopId}/sections`, {
1567
1651
  method: 'POST',
1568
- body: JSON.stringify(params)
1652
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1653
+ body: body.toString()
1569
1654
  }, false);
1570
1655
  }
1571
1656
  async updateShopSection(shopId, sectionId, params) {
1657
+ const body = this.buildFormBody(params);
1572
1658
  return this.makeRequest(`/shops/${shopId}/sections/${sectionId}`, {
1573
1659
  method: 'PUT',
1574
- body: JSON.stringify(params)
1660
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1661
+ body: body.toString()
1575
1662
  }, false);
1576
1663
  }
1577
1664
  async deleteShopSection(shopId, sectionId) {
@@ -1591,9 +1678,13 @@ class EtsyClient {
1591
1678
  }
1592
1679
  }
1593
1680
  }
1594
- return this.makeRequest(`/shops/${shopId}/listings`, {
1681
+ const legacy = options?.legacy;
1682
+ const query = legacy !== undefined ? `?legacy=${legacy}` : '';
1683
+ const body = this.buildFormBody(params);
1684
+ return this.makeRequest(`/shops/${shopId}/listings${query}`, {
1595
1685
  method: 'POST',
1596
- body: JSON.stringify(params)
1686
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1687
+ body: body.toString()
1597
1688
  }, false);
1598
1689
  }
1599
1690
  async updateListing(shopId, listingId, params, options) {
@@ -1610,16 +1701,22 @@ class EtsyClient {
1610
1701
  }
1611
1702
  }
1612
1703
  }
1613
- return this.makeRequest(`/shops/${shopId}/listings/${listingId}`, {
1704
+ const legacy = options?.legacy;
1705
+ const query = legacy !== undefined ? `?legacy=${legacy}` : '';
1706
+ const body = this.buildFormBody(params);
1707
+ return this.makeRequest(`/shops/${shopId}/listings/${listingId}${query}`, {
1614
1708
  method: 'PATCH',
1615
- body: JSON.stringify(params)
1709
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1710
+ body: body.toString()
1616
1711
  }, false);
1617
1712
  }
1618
1713
  async deleteListing(listingId) {
1619
1714
  await this.makeRequest(`/listings/${listingId}`, { method: 'DELETE' }, false);
1620
1715
  }
1621
- async updateListingInventory(listingId, params) {
1622
- return this.makeRequest(`/listings/${listingId}/inventory`, {
1716
+ async updateListingInventory(listingId, params, options) {
1717
+ const legacy = options?.legacy;
1718
+ const query = legacy !== undefined ? `?legacy=${legacy}` : '';
1719
+ return this.makeRequest(`/listings/${listingId}/inventory${query}`, {
1623
1720
  method: 'PUT',
1624
1721
  body: JSON.stringify(params)
1625
1722
  }, false);
@@ -1652,8 +1749,8 @@ class EtsyClient {
1652
1749
  }
1653
1750
  return response.json();
1654
1751
  }
1655
- async getListingImage(shopId, listingId, imageId) {
1656
- return this.makeRequest(`/shops/${shopId}/listings/${listingId}/images/${imageId}`);
1752
+ async getListingImage(listingId, imageId) {
1753
+ return this.makeRequest(`/listings/${listingId}/images/${imageId}`);
1657
1754
  }
1658
1755
  async deleteListingImage(shopId, listingId, imageId) {
1659
1756
  await this.makeRequest(`/shops/${shopId}/listings/${listingId}/images/${imageId}`, { method: 'DELETE' }, false);
@@ -1700,20 +1797,40 @@ class EtsyClient {
1700
1797
  searchParams.set('was_shipped', params.was_shipped.toString());
1701
1798
  if (params?.was_delivered !== undefined)
1702
1799
  searchParams.set('was_delivered', params.was_delivered.toString());
1800
+ if (params?.was_canceled !== undefined)
1801
+ searchParams.set('was_canceled', params.was_canceled.toString());
1802
+ if (params?.legacy !== undefined)
1803
+ searchParams.set('legacy', params.legacy.toString());
1703
1804
  const response = await this.makeRequest(`/shops/${shopId}/receipts?${searchParams.toString()}`);
1704
1805
  return response.results;
1705
1806
  }
1706
- async getShopReceipt(shopId, receiptId) {
1707
- return this.makeRequest(`/shops/${shopId}/receipts/${receiptId}`);
1708
- }
1709
- async updateShopReceipt(shopId, receiptId, params) {
1710
- return this.makeRequest(`/shops/${shopId}/receipts/${receiptId}`, {
1807
+ async getShopReceipt(shopId, receiptId, params = {}) {
1808
+ const searchParams = new URLSearchParams();
1809
+ if (params.legacy !== undefined) {
1810
+ searchParams.set('legacy', params.legacy.toString());
1811
+ }
1812
+ const query = searchParams.toString();
1813
+ const suffix = query ? `?${query}` : '';
1814
+ return this.makeRequest(`/shops/${shopId}/receipts/${receiptId}${suffix}`);
1815
+ }
1816
+ async updateShopReceipt(shopId, receiptId, params, options) {
1817
+ const legacy = options?.legacy;
1818
+ const query = legacy !== undefined ? `?legacy=${legacy}` : '';
1819
+ const body = this.buildFormBody(params);
1820
+ return this.makeRequest(`/shops/${shopId}/receipts/${receiptId}${query}`, {
1711
1821
  method: 'PUT',
1712
- body: JSON.stringify(params)
1822
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1823
+ body: body.toString()
1713
1824
  }, false);
1714
1825
  }
1715
- async getShopReceiptTransactions(shopId, receiptId) {
1716
- const response = await this.makeRequest(`/shops/${shopId}/receipts/${receiptId}/transactions`);
1826
+ async getShopReceiptTransactions(shopId, receiptId, params = {}) {
1827
+ const searchParams = new URLSearchParams();
1828
+ if (params.legacy !== undefined) {
1829
+ searchParams.set('legacy', params.legacy.toString());
1830
+ }
1831
+ const query = searchParams.toString();
1832
+ const suffix = query ? `?${query}` : '';
1833
+ const response = await this.makeRequest(`/shops/${shopId}/receipts/${receiptId}/transactions${suffix}`);
1717
1834
  return response.results;
1718
1835
  }
1719
1836
  async getShopTransaction(shopId, transactionId) {
@@ -1724,37 +1841,54 @@ class EtsyClient {
1724
1841
  return response.results;
1725
1842
  }
1726
1843
  async createShopShippingProfile(shopId, params) {
1844
+ const body = this.buildFormBody(params);
1727
1845
  return this.makeRequest(`/shops/${shopId}/shipping-profiles`, {
1728
1846
  method: 'POST',
1729
- body: JSON.stringify(params)
1847
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1848
+ body: body.toString()
1730
1849
  }, false);
1731
1850
  }
1732
1851
  async getShopShippingProfile(shopId, profileId) {
1733
1852
  return this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}`);
1734
1853
  }
1735
1854
  async updateShopShippingProfile(shopId, profileId, params) {
1855
+ const body = this.buildFormBody(params);
1736
1856
  return this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}`, {
1737
1857
  method: 'PUT',
1738
- body: JSON.stringify(params)
1858
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1859
+ body: body.toString()
1739
1860
  }, false);
1740
1861
  }
1741
1862
  async deleteShopShippingProfile(shopId, profileId) {
1742
1863
  await this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}`, { method: 'DELETE' }, false);
1743
1864
  }
1744
- async getShopShippingProfileDestinations(shopId, profileId) {
1745
- const response = await this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}/destinations`);
1865
+ async getShopShippingProfileDestinations(shopId, profileId, params = {}) {
1866
+ const searchParams = new URLSearchParams();
1867
+ if (params.limit !== undefined) {
1868
+ searchParams.set('limit', params.limit.toString());
1869
+ }
1870
+ if (params.offset !== undefined) {
1871
+ searchParams.set('offset', params.offset.toString());
1872
+ }
1873
+ const query = searchParams.toString();
1874
+ const suffix = query ? `?${query}` : '';
1875
+ const response = await this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}/destinations${suffix}`);
1746
1876
  return response.results;
1747
1877
  }
1748
1878
  async createShopShippingProfileDestination(shopId, profileId, params) {
1879
+ const body = this.buildFormBody(params);
1749
1880
  return this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}/destinations`, {
1750
1881
  method: 'POST',
1751
- body: JSON.stringify(params)
1882
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1883
+ body: body.toString()
1752
1884
  }, false);
1753
1885
  }
1754
1886
  async updateShopShippingProfileDestination(shopId, profileId, destinationId, params) {
1887
+ const body = this.buildFormBody(params);
1755
1888
  return this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}/destinations/${destinationId}`, {
1756
1889
  method: 'PUT',
1757
- body: JSON.stringify(params)
1890
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1891
+ body: body.toString()
1758
1892
  }, false);
1759
1893
  }
1760
1894
  async deleteShopShippingProfileDestination(shopId, profileId, destinationId) {
@@ -1764,16 +1898,16 @@ class EtsyClient {
1764
1898
  const response = await this.makeRequest(`/shops/${shopId}/shipping-profiles/${profileId}/upgrades`);
1765
1899
  return response.results;
1766
1900
  }
1767
- async createReceiptShipment(shopId, receiptId, params) {
1768
- return this.makeRequest(`/shops/${shopId}/receipts/${receiptId}/tracking`, {
1901
+ async createReceiptShipment(shopId, receiptId, params, options) {
1902
+ const legacy = options?.legacy;
1903
+ const query = legacy !== undefined ? `?legacy=${legacy}` : '';
1904
+ const body = this.buildFormBody(params);
1905
+ return this.makeRequest(`/shops/${shopId}/receipts/${receiptId}/tracking${query}`, {
1769
1906
  method: 'POST',
1770
- body: JSON.stringify(params)
1907
+ headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
1908
+ body: body.toString()
1771
1909
  }, false);
1772
1910
  }
1773
- async getShopReceiptShipments(shopId, receiptId) {
1774
- const response = await this.makeRequest(`/shops/${shopId}/receipts/${receiptId}/shipments`);
1775
- return response.results;
1776
- }
1777
1911
  async getShopPaymentAccountLedgerEntries(shopId, params) {
1778
1912
  const searchParams = new URLSearchParams();
1779
1913
  searchParams.set('min_created', params.min_created.toString());
@@ -1788,8 +1922,18 @@ class EtsyClient {
1788
1922
  async getShopPaymentAccountLedgerEntry(shopId, entryId) {
1789
1923
  return this.makeRequest(`/shops/${shopId}/payment-account/ledger-entries/${entryId}`);
1790
1924
  }
1925
+ async getPayments(shopId, paymentIds) {
1926
+ const searchParams = new URLSearchParams();
1927
+ searchParams.set('payment_ids', paymentIds.join(','));
1928
+ const response = await this.makeRequest(`/shops/${shopId}/payments?${searchParams.toString()}`);
1929
+ return response.results;
1930
+ }
1791
1931
  async getShopPayment(shopId, paymentId) {
1792
- return this.makeRequest(`/shops/${shopId}/payment-account/payments/${paymentId}`);
1932
+ const payments = await this.getPayments(shopId, [Number(paymentId)]);
1933
+ if (payments.length === 0) {
1934
+ throw new EtsyApiError('Payment not found', 404);
1935
+ }
1936
+ return payments[0];
1793
1937
  }
1794
1938
  async getBuyerTaxonomyNodes() {
1795
1939
  const response = await this.makeRequest('/buyer-taxonomy/nodes');
@@ -1806,8 +1950,8 @@ class EtsyClient {
1806
1950
  async updateListingProperty(params) {
1807
1951
  const { shopId, listingId, propertyId, valueIds, values, scaleId } = params;
1808
1952
  const body = new URLSearchParams();
1809
- valueIds.forEach(id => body.append('value_ids[]', id.toString()));
1810
- values.forEach(val => body.append('values[]', val));
1953
+ valueIds.forEach(id => body.append('value_ids', id.toString()));
1954
+ values.forEach(val => body.append('values', val));
1811
1955
  if (scaleId !== undefined) {
1812
1956
  body.append('scale_id', scaleId.toString());
1813
1957
  }
@@ -2184,12 +2328,23 @@ class GlobalRequestQueue {
2184
2328
  let result;
2185
2329
  if (item.timeout) {
2186
2330
  const remainingTimeout = item.timeout - elapsed;
2331
+ let timeoutId;
2187
2332
  const timeoutPromise = new Promise((_, reject) => {
2188
- setTimeout(() => {
2333
+ timeoutId = setTimeout(() => {
2189
2334
  reject(new Error(`Request timeout after ${item.timeout}ms (exceeded during execution)`));
2190
2335
  }, remainingTimeout);
2336
+ if (timeoutId && typeof timeoutId.unref === 'function') {
2337
+ timeoutId.unref();
2338
+ }
2191
2339
  });
2192
- result = await Promise.race([item.request(), timeoutPromise]);
2340
+ try {
2341
+ result = await Promise.race([item.request(), timeoutPromise]);
2342
+ }
2343
+ finally {
2344
+ if (timeoutId) {
2345
+ clearTimeout(timeoutId);
2346
+ }
2347
+ }
2193
2348
  }
2194
2349
  else {
2195
2350
  result = await item.request();