@mcurros2/microm 1.1.168-0 → 1.1.170-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.
package/dist/index.js CHANGED
@@ -1345,6 +1345,8 @@ parcelRegister("dU7Zq", function(module, exports) {
1345
1345
 
1346
1346
  $parcel$export(module.exports, "MicroMClient", function () { return $16abd72d1aa9b62d$export$6118e57c65bf19ee; });
1347
1347
 
1348
+ var $lTNXP = parcelRequire("lTNXP");
1349
+
1348
1350
  var $cfO6r = parcelRequire("cfO6r");
1349
1351
 
1350
1352
  var $hDJ3w = parcelRequire("hDJ3w");
@@ -1397,6 +1399,7 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1397
1399
  getAPPID() {
1398
1400
  return this.#APP_ID;
1399
1401
  }
1402
+ //*** Record access
1400
1403
  startRecordPaths() {
1401
1404
  this.#RECORD_PATHS = true;
1402
1405
  }
@@ -1441,6 +1444,9 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1441
1444
  };
1442
1445
  }
1443
1446
  }
1447
+ async #saveRecordedAccessData(data) {
1448
+ await this.#DATA_STORAGE.saveData(this.#APP_ID, (0, $brSbF.RECORDED_ACCESS_DATA_STORAGE_KEY), data);
1449
+ }
1444
1450
  async #saveAllRecordedAccess() {
1445
1451
  if (this.#RECORD_PATHS) {
1446
1452
  const result = (0, $brSbF.generateCSharpGetRoutePaths)(this.#RECORDED_PATHS);
@@ -1448,39 +1454,73 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1448
1454
  console.log(result);
1449
1455
  }
1450
1456
  }
1451
- async localLogoff() {
1452
- await this.#removeToken();
1453
- await this.#deleteEnabledMenus();
1457
+ //*** OIDC flows
1458
+ async oidcLoginAndRedirect(options) {
1459
+ const authorizeUrl = await this.#startOidcLogin(options);
1460
+ window.location.href = authorizeUrl;
1454
1461
  }
1455
- async logoff() {
1456
- const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'Login request timed out');
1462
+ async #startOidcLogin(options) {
1463
+ const { targetLinkUri: targetLinkUri, extraParams: extraParams } = options;
1464
+ const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'OIDC PAR request timed out');
1457
1465
  try {
1458
- await this.#removeToken();
1459
- await this.#deleteEnabledMenus();
1460
- if (this.#RECORD_PATHS) this.#saveAllRecordedAccess();
1461
- const response = await fetch(`${this.#API_URL}/${this.#APP_ID}/auth/logoff`, {
1466
+ const localDeviceId = await this.#getLocalDeviceId();
1467
+ // Prepare OIDC client PAR request parameters
1468
+ // required OIDC parameters are server-managed
1469
+ const params = new URLSearchParams();
1470
+ if (targetLinkUri) params.set('target_link_uri', targetLinkUri);
1471
+ params.set('local_device_id', localDeviceId);
1472
+ params.set('client_id', this.#APP_ID);
1473
+ if (extraParams) {
1474
+ for (const [k, v] of Object.entries(extraParams))if (v != null) {
1475
+ // Avoid overriding security-related parameters that are server-managed.
1476
+ if ((0, $lTNXP.isIn)(k, 'response_type', 'scope', 'state', 'nonce', 'code_challenge', 'code_challenge_method', 'client_id', 'request_uri', 'redirect_uri')) {
1477
+ console.warn(`Ignoring OIDC extraParam '${k}' because it is server-managed.`);
1478
+ continue;
1479
+ }
1480
+ params.set(k, v);
1481
+ }
1482
+ }
1483
+ const parUrl = `${this.#API_URL}/${this.#APP_ID}/oidc-client/par`;
1484
+ const response = await fetch(parUrl, {
1462
1485
  method: 'POST',
1463
1486
  headers: {
1464
- "Content-Type": "application/json; charset=utf-8",
1465
- "Authorization": `Bearer ${this.#TOKEN?.access_token || ''}`
1487
+ "Content-Type": "application/x-www-form-urlencoded"
1466
1488
  },
1467
1489
  mode: this.#REQUEST_MODE,
1468
1490
  cache: 'no-store',
1469
1491
  credentials: 'include',
1470
1492
  referrerPolicy: 'strict-origin-when-cross-origin',
1471
1493
  signal: loginTimeout.signal,
1472
- body: JSON.stringify({})
1494
+ body: params.toString()
1473
1495
  });
1474
- if (!response.ok) throw {
1475
- status: response.status,
1476
- statusMessage: response.statusText,
1477
- message: response.statusText,
1478
- url: response.url
1496
+ if (!response.ok) {
1497
+ const text = await response.text().catch(()=>'');
1498
+ throw {
1499
+ status: response.status,
1500
+ statusMessage: response.statusText,
1501
+ message: text || response.statusText,
1502
+ url: response.url
1503
+ };
1504
+ }
1505
+ const data = await response.json();
1506
+ if (!data.authorize_url) throw {
1507
+ status: 500,
1508
+ statusMessage: 'invalid_par_response',
1509
+ message: data.error_description || data.error || 'PAR response missing authorize_url',
1510
+ url: parUrl
1479
1511
  };
1512
+ return data.authorize_url;
1480
1513
  } finally{
1481
1514
  loginTimeout.clear();
1482
1515
  }
1483
1516
  }
1517
+ //*** Local login/logout
1518
+ get LOGGED_IN_USER() {
1519
+ return this.#TOKEN?.claims;
1520
+ }
1521
+ async getRememberUser() {
1522
+ return await this.#DATA_STORAGE.readData(this.#APP_ID, $16abd72d1aa9b62d$var$REMEMBER_USER_DATA_KEY);
1523
+ }
1484
1524
  async isLoggedIn() {
1485
1525
  const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'Login request timed out');
1486
1526
  try {
@@ -1515,27 +1555,6 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1515
1555
  }
1516
1556
  return !!this.#TOKEN?.access_token && new Date() < new Date(this.#TOKEN.expiration);
1517
1557
  }
1518
- get LOGGED_IN_USER() {
1519
- return this.#TOKEN?.claims;
1520
- }
1521
- async updateClientClaims(claims) {
1522
- if (this.#TOKEN) {
1523
- this.#TOKEN.claims = claims;
1524
- await this.#setToken(this.#TOKEN);
1525
- }
1526
- }
1527
- async #getLocalDeviceId() {
1528
- const local_device = await this.#DATA_STORAGE.readData(this.#APP_ID, $16abd72d1aa9b62d$var$LOCAL_DEVICE_ID_KEY);
1529
- if (local_device !== null) {
1530
- this.#LOCAL_DEVICE_ID = local_device;
1531
- return local_device;
1532
- }
1533
- // Generate a new local device ID if it doesn't exist
1534
- const randomId = "10000000-1000-4000-8000-100000000000".replace(/[018]/g, (c)=>(+c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> +c / 4).toString(16));
1535
- await this.#DATA_STORAGE.saveData(this.#APP_ID, $16abd72d1aa9b62d$var$LOCAL_DEVICE_ID_KEY, randomId);
1536
- this.#LOCAL_DEVICE_ID = randomId;
1537
- return randomId;
1538
- }
1539
1558
  async login(username, password, rememberme) {
1540
1559
  //Intentionally not accounting for tokenRefreshInProgress (see refresh logic)
1541
1560
  const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'Login request timed out');
@@ -1598,6 +1617,45 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1598
1617
  loginTimeout.clear();
1599
1618
  }
1600
1619
  }
1620
+ async localLogoff() {
1621
+ await this.#removeToken();
1622
+ await this.#deleteEnabledMenus();
1623
+ }
1624
+ async logoff() {
1625
+ const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'Login request timed out');
1626
+ try {
1627
+ await this.#removeToken();
1628
+ await this.#deleteEnabledMenus();
1629
+ if (this.#RECORD_PATHS) await this.#saveAllRecordedAccess();
1630
+ const response = await fetch(`${this.#API_URL}/${this.#APP_ID}/auth/logoff`, {
1631
+ method: 'POST',
1632
+ headers: {
1633
+ "Content-Type": "application/json; charset=utf-8",
1634
+ "Authorization": `Bearer ${this.#TOKEN?.access_token || ''}`
1635
+ },
1636
+ mode: this.#REQUEST_MODE,
1637
+ cache: 'no-store',
1638
+ credentials: 'include',
1639
+ referrerPolicy: 'strict-origin-when-cross-origin',
1640
+ signal: loginTimeout.signal,
1641
+ body: JSON.stringify({})
1642
+ });
1643
+ if (!response.ok) throw {
1644
+ status: response.status,
1645
+ statusMessage: response.statusText,
1646
+ message: response.statusText,
1647
+ url: response.url
1648
+ };
1649
+ } finally{
1650
+ loginTimeout.clear();
1651
+ }
1652
+ }
1653
+ async updateClientClaims(claims) {
1654
+ if (this.#TOKEN) {
1655
+ this.#TOKEN.claims = claims;
1656
+ await this.#setToken(this.#TOKEN);
1657
+ }
1658
+ }
1601
1659
  async recoveryemail(username) {
1602
1660
  const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT * 4, 'Login request timed out');
1603
1661
  try {
@@ -1660,6 +1718,99 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1660
1718
  loginTimeout.clear();
1661
1719
  }
1662
1720
  }
1721
+ async #getLocalDeviceId() {
1722
+ const local_device = await this.#DATA_STORAGE.readData(this.#APP_ID, $16abd72d1aa9b62d$var$LOCAL_DEVICE_ID_KEY);
1723
+ if (local_device !== null) {
1724
+ this.#LOCAL_DEVICE_ID = local_device;
1725
+ return local_device;
1726
+ }
1727
+ // Generate a new local device ID if it doesn't exist
1728
+ const randomId = "10000000-1000-4000-8000-100000000000".replace(/[018]/g, (c)=>(+c ^ crypto.getRandomValues(new Uint8Array(1))[0] & 15 >> +c / 4).toString(16));
1729
+ await this.#DATA_STORAGE.saveData(this.#APP_ID, $16abd72d1aa9b62d$var$LOCAL_DEVICE_ID_KEY, randomId);
1730
+ this.#LOCAL_DEVICE_ID = randomId;
1731
+ return randomId;
1732
+ }
1733
+ async #loadToken() {
1734
+ if (!this.#TOKEN) this.#TOKEN = await this.#TOKEN_STORAGE.readToken(this.#APP_ID);
1735
+ }
1736
+ async #setToken(token) {
1737
+ await this.#TOKEN_STORAGE.saveToken(this.#APP_ID, token);
1738
+ this.#TOKEN = token;
1739
+ }
1740
+ async #removeToken() {
1741
+ await this.#TOKEN_STORAGE.deleteToken(this.#APP_ID);
1742
+ this.#TOKEN = null;
1743
+ }
1744
+ async #checkAndRefreshToken() {
1745
+ await this.#loadToken();
1746
+ await this.#readTimeZoneOffset();
1747
+ if (!this.#TOKEN) return;
1748
+ const renewalAheadPeriod = 60000;
1749
+ const now = new Date();
1750
+ const expiration = new Date(this.#TOKEN.expiration);
1751
+ if (now > new Date(expiration.getTime() - renewalAheadPeriod)) await this.#refreshToken();
1752
+ }
1753
+ async #refreshToken() {
1754
+ // Check if a token refresh is already in progress.
1755
+ // If so, return that promise instead of starting a new request.
1756
+ if (this.#tokenRefreshInProgress) {
1757
+ console.warn('Token refresh already in progress');
1758
+ return this.#tokenRefreshInProgress;
1759
+ }
1760
+ const _performTokenRefresh = async ()=>{
1761
+ const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'Login request timed out');
1762
+ try {
1763
+ if (!this.#TOKEN) throw new Error('Token not found');
1764
+ //console.log('Refreshing token');
1765
+ const old_token = this.#TOKEN;
1766
+ const response = await fetch(`${this.#API_URL}/${this.#APP_ID}/auth/refresh`, {
1767
+ method: 'POST',
1768
+ headers: {
1769
+ "Content-Type": "application/json; charset=utf-8"
1770
+ },
1771
+ mode: this.#REQUEST_MODE,
1772
+ cache: 'no-store',
1773
+ credentials: 'include',
1774
+ referrerPolicy: 'strict-origin-when-cross-origin',
1775
+ signal: loginTimeout.signal,
1776
+ body: JSON.stringify({
1777
+ Bearer: this.#TOKEN.access_token,
1778
+ RefreshToken: this.#TOKEN.refresh_token
1779
+ })
1780
+ });
1781
+ if (!response.ok) throw {
1782
+ status: response?.status,
1783
+ statusMessage: response?.statusText,
1784
+ message: response?.statusText,
1785
+ url: response?.url
1786
+ };
1787
+ const data = await response.json();
1788
+ if (data && data.access_token) {
1789
+ const new_token = new (0, $78KzE.MicroMToken)(data.access_token, data.expires_in, data['refresh-token'], data.token_type, this.#TOKEN.claims);
1790
+ if (old_token !== this.#TOKEN) throw new Error("Current token was changed while refreshing.");
1791
+ await this.#setToken(new_token);
1792
+ //console.log('Token refreshed', new_token);
1793
+ return;
1794
+ } else //console.log('Unexpected result', data);
1795
+ throw {
1796
+ statusMessage: 'Unexpected result',
1797
+ url: response.url
1798
+ };
1799
+ } catch (error) {
1800
+ //console.log('RefreshToken', error);
1801
+ throw error;
1802
+ } finally{
1803
+ this.#tokenRefreshInProgress = null; // Clear the ongoing refresh promise once done.
1804
+ loginTimeout.clear();
1805
+ }
1806
+ };
1807
+ this.#tokenRefreshInProgress = _performTokenRefresh();
1808
+ return this.#tokenRefreshInProgress;
1809
+ }
1810
+ //*** Timezone offset
1811
+ get TIMEZONE_OFFSET() {
1812
+ return this.#TIMEZONE_OFFSET;
1813
+ }
1663
1814
  async #saveTimeZoneOffset(data) {
1664
1815
  await this.#DATA_STORAGE.saveData(this.#APP_ID, $16abd72d1aa9b62d$var$TIMEZONE_OFFSET_DATA_KEY, data);
1665
1816
  }
@@ -1684,8 +1835,13 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1684
1835
  await this.#saveTimeZoneOffset(offset);
1685
1836
  return result;
1686
1837
  }
1687
- get TIMEZONE_OFFSET() {
1688
- return this.#TIMEZONE_OFFSET;
1838
+ //*** Enabled menus
1839
+ async getMenus() {
1840
+ if (this.#ENABLED_MENUS.size === 0) {
1841
+ const data = await this.#readEnabledMenus();
1842
+ this.#ENABLED_MENUS = data ? new Set(data) : new Set();
1843
+ }
1844
+ return this.#ENABLED_MENUS;
1689
1845
  }
1690
1846
  async #getAPIEnabledMenus(username, abort_signal = null) {
1691
1847
  if (!this.#TOKEN) return;
@@ -1702,12 +1858,45 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1702
1858
  await this.#saveEnabledMenus(menu_items);
1703
1859
  this.#ENABLED_MENUS = new Set(menu_items);
1704
1860
  }
1705
- async getMenus() {
1706
- if (this.#ENABLED_MENUS.size === 0) {
1707
- const data = await this.#readEnabledMenus();
1708
- this.#ENABLED_MENUS = data ? new Set(data) : new Set();
1709
- }
1710
- return this.#ENABLED_MENUS;
1861
+ async #saveEnabledMenus(data) {
1862
+ await this.#DATA_STORAGE.saveData(this.#APP_ID, $16abd72d1aa9b62d$var$ENABLED_MENUS_DATA_KEY, data);
1863
+ }
1864
+ async #readEnabledMenus() {
1865
+ return await this.#DATA_STORAGE.readData(this.#APP_ID, $16abd72d1aa9b62d$var$ENABLED_MENUS_DATA_KEY);
1866
+ }
1867
+ async #deleteEnabledMenus() {
1868
+ await this.#DATA_STORAGE.deleteData(this.#APP_ID, $16abd72d1aa9b62d$var$ENABLED_MENUS_DATA_KEY);
1869
+ }
1870
+ //*** File upload/download
1871
+ getDocumentURL(fileGuid) {
1872
+ return fileGuid ? `${this.#API_URL}/${this.#APP_ID}/serve/${fileGuid}` : '';
1873
+ }
1874
+ getThumbnailURL(fileGuid, max_size = 150, quality = 75) {
1875
+ return fileGuid ? `${this.#API_URL}/${this.#APP_ID}/thumbnail/${fileGuid}/${max_size}/${quality}` : '';
1876
+ }
1877
+ async upload(file, fileprocess_id, abort_signal = null, max_size = 150, quality = 75, onProgress = ()=>{}) {
1878
+ return this.#uploadFile(file, fileprocess_id, abort_signal, max_size, quality, onProgress);
1879
+ }
1880
+ async downloadBlob(fileUrl, abort_signal = null) {
1881
+ await this.#checkAndRefreshToken();
1882
+ if (!this.#TOKEN) throw {
1883
+ status: 401,
1884
+ statusMessage: `Can't execute request: Not logged in`
1885
+ };
1886
+ const response = await fetch(fileUrl, {
1887
+ headers: {
1888
+ ...this.#TOKEN ? {
1889
+ "Authorization": `Bearer ${this.#TOKEN.access_token}`
1890
+ } : {}
1891
+ },
1892
+ mode: this.#REQUEST_MODE,
1893
+ cache: 'no-store',
1894
+ credentials: 'include',
1895
+ referrerPolicy: 'strict-origin-when-cross-origin',
1896
+ signal: abort_signal
1897
+ });
1898
+ if (!response.ok) throw new Error(`Network error: ${response.status} - ${response.statusText}`);
1899
+ return await response.blob();
1711
1900
  }
1712
1901
  async #uploadFile(file, fileprocess_id, abort_signal = null, max_size = 150, quality = 75, onProgress = ()=>{}) {
1713
1902
  await this.#checkAndRefreshToken();
@@ -1768,223 +1957,7 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
1768
1957
  xhr.send(file);
1769
1958
  });
1770
1959
  }
1771
- async #refreshToken() {
1772
- // Check if a token refresh is already in progress.
1773
- // If so, return that promise instead of starting a new request.
1774
- if (this.#tokenRefreshInProgress) {
1775
- console.warn('Token refresh already in progress');
1776
- return this.#tokenRefreshInProgress;
1777
- }
1778
- const _performTokenRefresh = async ()=>{
1779
- const loginTimeout = new (0, $dF8o7.TimeoutSignal)(this.#LOGIN_TIMEOUT, 'Login request timed out');
1780
- try {
1781
- if (!this.#TOKEN) throw new Error('Token not found');
1782
- //console.log('Refreshing token');
1783
- const old_token = this.#TOKEN;
1784
- const response = await fetch(`${this.#API_URL}/${this.#APP_ID}/auth/refresh`, {
1785
- method: 'POST',
1786
- headers: {
1787
- "Content-Type": "application/json; charset=utf-8"
1788
- },
1789
- mode: this.#REQUEST_MODE,
1790
- cache: 'no-store',
1791
- credentials: 'include',
1792
- referrerPolicy: 'strict-origin-when-cross-origin',
1793
- signal: loginTimeout.signal,
1794
- body: JSON.stringify({
1795
- Bearer: this.#TOKEN.access_token,
1796
- RefreshToken: this.#TOKEN.refresh_token
1797
- })
1798
- });
1799
- if (!response.ok) throw {
1800
- status: response?.status,
1801
- statusMessage: response?.statusText,
1802
- message: response?.statusText,
1803
- url: response?.url
1804
- };
1805
- const data = await response.json();
1806
- if (data && data.access_token) {
1807
- const new_token = new (0, $78KzE.MicroMToken)(data.access_token, data.expires_in, data['refresh-token'], data.token_type, this.#TOKEN.claims);
1808
- if (old_token !== this.#TOKEN) throw new Error("Current token was changed while refreshing.");
1809
- await this.#setToken(new_token);
1810
- //console.log('Token refreshed', new_token);
1811
- return;
1812
- } else //console.log('Unexpected result', data);
1813
- throw {
1814
- statusMessage: 'Unexpected result',
1815
- url: response.url
1816
- };
1817
- } catch (error) {
1818
- //console.log('RefreshToken', error);
1819
- throw error;
1820
- } finally{
1821
- this.#tokenRefreshInProgress = null; // Clear the ongoing refresh promise once done.
1822
- loginTimeout.clear();
1823
- }
1824
- };
1825
- this.#tokenRefreshInProgress = _performTokenRefresh();
1826
- return this.#tokenRefreshInProgress;
1827
- }
1828
- async getRememberUser() {
1829
- return await this.#DATA_STORAGE.readData(this.#APP_ID, $16abd72d1aa9b62d$var$REMEMBER_USER_DATA_KEY);
1830
- }
1831
- async #saveRecordedAccessData(data) {
1832
- await this.#DATA_STORAGE.saveData(this.#APP_ID, (0, $brSbF.RECORDED_ACCESS_DATA_STORAGE_KEY), data);
1833
- }
1834
- async #saveEnabledMenus(data) {
1835
- await this.#DATA_STORAGE.saveData(this.#APP_ID, $16abd72d1aa9b62d$var$ENABLED_MENUS_DATA_KEY, data);
1836
- }
1837
- async #readEnabledMenus() {
1838
- return await this.#DATA_STORAGE.readData(this.#APP_ID, $16abd72d1aa9b62d$var$ENABLED_MENUS_DATA_KEY);
1839
- }
1840
- async #deleteEnabledMenus() {
1841
- await this.#DATA_STORAGE.deleteData(this.#APP_ID, $16abd72d1aa9b62d$var$ENABLED_MENUS_DATA_KEY);
1842
- }
1843
- async #loadToken() {
1844
- if (!this.#TOKEN) this.#TOKEN = await this.#TOKEN_STORAGE.readToken(this.#APP_ID);
1845
- }
1846
- async #setToken(token) {
1847
- await this.#TOKEN_STORAGE.saveToken(this.#APP_ID, token);
1848
- this.#TOKEN = token;
1849
- }
1850
- async #removeToken() {
1851
- await this.#TOKEN_STORAGE.deleteToken(this.#APP_ID);
1852
- this.#TOKEN = null;
1853
- }
1854
- async #checkAndRefreshToken() {
1855
- await this.#loadToken();
1856
- await this.#readTimeZoneOffset();
1857
- if (!this.#TOKEN) return;
1858
- const renewalAheadPeriod = 60000;
1859
- const now = new Date();
1860
- const expiration = new Date(this.#TOKEN.expiration);
1861
- if (now > new Date(expiration.getTime() - renewalAheadPeriod)) await this.#refreshToken();
1862
- }
1863
- async #submitToAPI(entity_name, parent_keys, values, recordsSelection, action, abort_signal = null, additional_route = null) {
1864
- const extra_route = additional_route !== null ? `/${additional_route}` : '';
1865
- const route = `${this.#API_URL}/${this.#APP_ID}/ent/${entity_name}/${action}${extra_route}`;
1866
- try {
1867
- await this.#checkAndRefreshToken();
1868
- if (!this.#TOKEN) throw {
1869
- status: 401,
1870
- statusMessage: `Can't execute request: Not logged in`,
1871
- url: route
1872
- };
1873
- const body = JSON.stringify({
1874
- ParentKeys: parent_keys,
1875
- Values: values,
1876
- RecordsSelection: recordsSelection
1877
- }, (0, $hDJ3w.JSONDateWithTimezoneReplacer));
1878
- const res = await fetch(route, {
1879
- method: 'POST',
1880
- headers: {
1881
- "Content-Type": "application/json; charset=utf-8",
1882
- "Authorization": `Bearer ${this.#TOKEN.access_token}`
1883
- },
1884
- mode: this.#REQUEST_MODE,
1885
- cache: 'no-store',
1886
- credentials: 'include',
1887
- referrerPolicy: 'strict-origin-when-cross-origin',
1888
- signal: abort_signal,
1889
- body: body
1890
- });
1891
- if (!res.ok) throw {
1892
- status: res?.status,
1893
- statusMessage: res?.statusText,
1894
- message: res?.statusText,
1895
- url: res?.url
1896
- };
1897
- const data = await res.json();
1898
- return data;
1899
- } catch (error) {
1900
- abort_signal = null;
1901
- if (this.#REDIRECT_ON_401) {
1902
- if (error.status === 401) {
1903
- console.warn(`${route} 401, redirecting to login page: ${this.#REDIRECT_ON_401}`);
1904
- await this.localLogoff();
1905
- window.location.href = this.#REDIRECT_ON_401;
1906
- }
1907
- } else throw error;
1908
- throw error;
1909
- }
1910
- }
1911
- async #submitToPublicAPI(entity_name, parent_keys, values, recordsSelection, action, abort_signal = null, additional_route = null) {
1912
- const extra_route = additional_route !== null ? `/${additional_route}` : '';
1913
- const route = `${this.#API_URL}/${this.#APP_ID}/public/${entity_name}/${action}${extra_route}`;
1914
- const body = JSON.stringify({
1915
- ParentKeys: parent_keys,
1916
- Values: values,
1917
- RecordsSelection: recordsSelection
1918
- }, (0, $hDJ3w.JSONDateWithTimezoneReplacer));
1919
- const res = await fetch(route, {
1920
- method: 'POST',
1921
- headers: {
1922
- "Content-Type": "application/json; charset=utf-8"
1923
- },
1924
- mode: this.#REQUEST_MODE,
1925
- cache: 'no-store',
1926
- credentials: 'include',
1927
- referrerPolicy: 'strict-origin-when-cross-origin',
1928
- signal: abort_signal,
1929
- body: body
1930
- });
1931
- if (!res.ok) throw {
1932
- status: res?.status,
1933
- statusMessage: res?.statusText,
1934
- message: res?.statusText,
1935
- url: res?.url
1936
- };
1937
- const data = await res.json();
1938
- abort_signal = null;
1939
- return data;
1940
- }
1941
- async downloadBlob(fileUrl, abort_signal = null) {
1942
- await this.#checkAndRefreshToken();
1943
- if (!this.#TOKEN) throw {
1944
- status: 401,
1945
- statusMessage: `Can't execute request: Not logged in`
1946
- };
1947
- const response = await fetch(fileUrl, {
1948
- headers: {
1949
- ...this.#TOKEN ? {
1950
- "Authorization": `Bearer ${this.#TOKEN.access_token}`
1951
- } : {}
1952
- },
1953
- mode: this.#REQUEST_MODE,
1954
- cache: 'no-store',
1955
- credentials: 'include',
1956
- referrerPolicy: 'strict-origin-when-cross-origin',
1957
- signal: abort_signal
1958
- });
1959
- if (!response.ok) throw new Error(`Network error: ${response.status} - ${response.statusText}`);
1960
- return await response.blob();
1961
- }
1962
- #isPublicAPI(entity_name, action, proc_name, action_name) {
1963
- const endpoint = this.#publicEndpoints[entity_name];
1964
- if (endpoint) switch(action){
1965
- case "get":
1966
- return (endpoint.AllowedAccess & 8) !== 0;
1967
- case "insert":
1968
- return (endpoint.AllowedAccess & 1) !== 0;
1969
- case "update":
1970
- return (endpoint.AllowedAccess & 2) !== 0;
1971
- case "delete":
1972
- return (endpoint.AllowedAccess & 4) !== 0;
1973
- case "lookup":
1974
- return (endpoint.AllowedAccess & 16) !== 0;
1975
- case "action":
1976
- return endpoint.AllowedActions && action_name && endpoint.AllowedActions.has(action_name) || false;
1977
- case "view":
1978
- return endpoint.AllowedProcs && proc_name && endpoint.AllowedProcs.has(proc_name) || false;
1979
- case "proc":
1980
- return endpoint.AllowedProcs && proc_name && endpoint.AllowedProcs.has(proc_name) || false;
1981
- case "process":
1982
- return endpoint.AllowedProcs && proc_name && endpoint.AllowedProcs.has(proc_name) || false;
1983
- default:
1984
- return false;
1985
- }
1986
- return false;
1987
- }
1960
+ //*** Entities API
1988
1961
  async get(entity_name, parent_keys, values, abort_signal = null) {
1989
1962
  this.#recordAccess({
1990
1963
  entityName: entity_name,
@@ -2090,14 +2063,108 @@ class $16abd72d1aa9b62d$export$6118e57c65bf19ee {
2090
2063
  });
2091
2064
  return this.#submitToAPI(entity_name, parent_keys, values, [], "import", abort_signal, import_procname);
2092
2065
  }
2093
- async upload(file, fileprocess_id, abort_signal = null, max_size = 150, quality = 75, onProgress = ()=>{}) {
2094
- return this.#uploadFile(file, fileprocess_id, abort_signal, max_size, quality, onProgress);
2066
+ async #submitToAPI(entity_name, parent_keys, values, recordsSelection, action, abort_signal = null, additional_route = null) {
2067
+ const extra_route = additional_route !== null ? `/${additional_route}` : '';
2068
+ const route = `${this.#API_URL}/${this.#APP_ID}/ent/${entity_name}/${action}${extra_route}`;
2069
+ try {
2070
+ await this.#checkAndRefreshToken();
2071
+ if (!this.#TOKEN) throw {
2072
+ status: 401,
2073
+ statusMessage: `Can't execute request: Not logged in`,
2074
+ url: route
2075
+ };
2076
+ const body = JSON.stringify({
2077
+ ParentKeys: parent_keys,
2078
+ Values: values,
2079
+ RecordsSelection: recordsSelection
2080
+ }, (0, $hDJ3w.JSONDateWithTimezoneReplacer));
2081
+ const res = await fetch(route, {
2082
+ method: 'POST',
2083
+ headers: {
2084
+ "Content-Type": "application/json; charset=utf-8",
2085
+ "Authorization": `Bearer ${this.#TOKEN.access_token}`
2086
+ },
2087
+ mode: this.#REQUEST_MODE,
2088
+ cache: 'no-store',
2089
+ credentials: 'include',
2090
+ referrerPolicy: 'strict-origin-when-cross-origin',
2091
+ signal: abort_signal,
2092
+ body: body
2093
+ });
2094
+ if (!res.ok) throw {
2095
+ status: res?.status,
2096
+ statusMessage: res?.statusText,
2097
+ message: res?.statusText,
2098
+ url: res?.url
2099
+ };
2100
+ const data = await res.json();
2101
+ return data;
2102
+ } catch (error) {
2103
+ if (this.#REDIRECT_ON_401 && error.status === 401) {
2104
+ console.warn(`${route} 401, redirecting to login page: ${this.#REDIRECT_ON_401}`);
2105
+ await this.localLogoff();
2106
+ window.location.href = this.#REDIRECT_ON_401;
2107
+ // return intentionally omitted
2108
+ }
2109
+ // MMC: this line should never execute if the redirect happens.
2110
+ // In case the browser, webview or environment for any reason fails to redirect, we still throw the error to the caller.
2111
+ throw error;
2112
+ }
2095
2113
  }
2096
- getDocumentURL(fileGuid) {
2097
- return fileGuid ? `${this.#API_URL}/${this.#APP_ID}/serve/${fileGuid}` : '';
2114
+ async #submitToPublicAPI(entity_name, parent_keys, values, recordsSelection, action, abort_signal = null, additional_route = null) {
2115
+ const extra_route = additional_route !== null ? `/${additional_route}` : '';
2116
+ const route = `${this.#API_URL}/${this.#APP_ID}/public/${entity_name}/${action}${extra_route}`;
2117
+ const body = JSON.stringify({
2118
+ ParentKeys: parent_keys,
2119
+ Values: values,
2120
+ RecordsSelection: recordsSelection
2121
+ }, (0, $hDJ3w.JSONDateWithTimezoneReplacer));
2122
+ const res = await fetch(route, {
2123
+ method: 'POST',
2124
+ headers: {
2125
+ "Content-Type": "application/json; charset=utf-8"
2126
+ },
2127
+ mode: this.#REQUEST_MODE,
2128
+ cache: 'no-store',
2129
+ credentials: 'include',
2130
+ referrerPolicy: 'strict-origin-when-cross-origin',
2131
+ signal: abort_signal,
2132
+ body: body
2133
+ });
2134
+ if (!res.ok) throw {
2135
+ status: res?.status,
2136
+ statusMessage: res?.statusText,
2137
+ message: res?.statusText,
2138
+ url: res?.url
2139
+ };
2140
+ const data = await res.json();
2141
+ return data;
2098
2142
  }
2099
- getThumbnailURL(fileGuid, max_size = 150, quality = 75) {
2100
- return fileGuid ? `${this.#API_URL}/${this.#APP_ID}/thumbnail/${fileGuid}/${max_size}/${quality}` : '';
2143
+ #isPublicAPI(entity_name, action, proc_name, action_name) {
2144
+ const endpoint = this.#publicEndpoints[entity_name];
2145
+ if (endpoint) switch(action){
2146
+ case "get":
2147
+ return (endpoint.AllowedAccess & 8) !== 0;
2148
+ case "insert":
2149
+ return (endpoint.AllowedAccess & 1) !== 0;
2150
+ case "update":
2151
+ return (endpoint.AllowedAccess & 2) !== 0;
2152
+ case "delete":
2153
+ return (endpoint.AllowedAccess & 4) !== 0;
2154
+ case "lookup":
2155
+ return (endpoint.AllowedAccess & 16) !== 0;
2156
+ case "action":
2157
+ return endpoint.AllowedActions && action_name && endpoint.AllowedActions.has(action_name) || false;
2158
+ case "view":
2159
+ return endpoint.AllowedProcs && proc_name && endpoint.AllowedProcs.has(proc_name) || false;
2160
+ case "proc":
2161
+ return endpoint.AllowedProcs && proc_name && endpoint.AllowedProcs.has(proc_name) || false;
2162
+ case "process":
2163
+ return endpoint.AllowedProcs && proc_name && endpoint.AllowedProcs.has(proc_name) || false;
2164
+ default:
2165
+ return false;
2166
+ }
2167
+ return false;
2101
2168
  }
2102
2169
  }
2103
2170
 
@@ -35804,7 +35871,7 @@ function $404ec2751816fed2$export$a6c7ac8248d6e38a(props) {
35804
35871
  return /*#__PURE__*/ (0, $b4te3$reactjsxruntime.jsx)((0, $b4te3$mantinecore.Anchor), {
35805
35872
  href: to,
35806
35873
  onClick: (e)=>{
35807
- e.preventDefault;
35874
+ e.preventDefault();
35808
35875
  navigate(to);
35809
35876
  },
35810
35877
  children: children