@medplum/core 0.9.13 → 0.9.16

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/cjs/index.js CHANGED
@@ -820,155 +820,6 @@
820
820
  return decodePayload(payload);
821
821
  }
822
822
 
823
- const OK_ID = 'ok';
824
- const CREATED_ID = 'created';
825
- const GONE_ID = 'gone';
826
- const NOT_MODIFIED_ID = 'not-modified';
827
- const NOT_FOUND_ID = 'not-found';
828
- const ACCESS_DENIED = 'access-denied';
829
- const allOk = {
830
- resourceType: 'OperationOutcome',
831
- id: OK_ID,
832
- issue: [
833
- {
834
- severity: 'information',
835
- code: 'information',
836
- details: {
837
- text: 'All OK',
838
- },
839
- },
840
- ],
841
- };
842
- const created = {
843
- resourceType: 'OperationOutcome',
844
- id: CREATED_ID,
845
- issue: [
846
- {
847
- severity: 'information',
848
- code: 'information',
849
- details: {
850
- text: 'Created',
851
- },
852
- },
853
- ],
854
- };
855
- const notModified = {
856
- resourceType: 'OperationOutcome',
857
- id: NOT_MODIFIED_ID,
858
- issue: [
859
- {
860
- severity: 'information',
861
- code: 'information',
862
- details: {
863
- text: 'Not Modified',
864
- },
865
- },
866
- ],
867
- };
868
- const notFound = {
869
- resourceType: 'OperationOutcome',
870
- id: NOT_FOUND_ID,
871
- issue: [
872
- {
873
- severity: 'error',
874
- code: 'not-found',
875
- details: {
876
- text: 'Not found',
877
- },
878
- },
879
- ],
880
- };
881
- const gone = {
882
- resourceType: 'OperationOutcome',
883
- id: GONE_ID,
884
- issue: [
885
- {
886
- severity: 'error',
887
- code: 'gone',
888
- details: {
889
- text: 'Gone',
890
- },
891
- },
892
- ],
893
- };
894
- const accessDenied = {
895
- resourceType: 'OperationOutcome',
896
- id: ACCESS_DENIED,
897
- issue: [
898
- {
899
- severity: 'error',
900
- code: 'access-denied',
901
- details: {
902
- text: 'Access Denied',
903
- },
904
- },
905
- ],
906
- };
907
- function badRequest(details, expression) {
908
- return {
909
- resourceType: 'OperationOutcome',
910
- issue: [
911
- {
912
- severity: 'error',
913
- code: 'invalid',
914
- details: {
915
- text: details,
916
- },
917
- expression: expression ? [expression] : undefined,
918
- },
919
- ],
920
- };
921
- }
922
- function isOk(outcome) {
923
- return outcome.id === OK_ID || outcome.id === CREATED_ID || outcome.id === NOT_MODIFIED_ID;
924
- }
925
- function isNotFound(outcome) {
926
- return outcome.id === NOT_FOUND_ID;
927
- }
928
- function isGone(outcome) {
929
- return outcome.id === GONE_ID;
930
- }
931
- function getStatus(outcome) {
932
- if (outcome.id === OK_ID) {
933
- return 200;
934
- }
935
- else if (outcome.id === CREATED_ID) {
936
- return 201;
937
- }
938
- else if (outcome.id === NOT_MODIFIED_ID) {
939
- return 304;
940
- }
941
- else if (outcome.id === ACCESS_DENIED) {
942
- return 403;
943
- }
944
- else if (outcome.id === NOT_FOUND_ID) {
945
- return 404;
946
- }
947
- else if (outcome.id === GONE_ID) {
948
- return 410;
949
- }
950
- else {
951
- return 400;
952
- }
953
- }
954
- /**
955
- * Asserts that the operation completed successfully and that the resource is defined.
956
- * @param outcome The operation outcome.
957
- * @param resource The resource that may or may not have been returned.
958
- */
959
- function assertOk(outcome, resource) {
960
- if (!isOk(outcome) || resource === undefined) {
961
- throw new OperationOutcomeError(outcome);
962
- }
963
- }
964
- class OperationOutcomeError extends Error {
965
- constructor(outcome) {
966
- var _a, _b;
967
- super((_b = (_a = outcome === null || outcome === void 0 ? void 0 : outcome.issue) === null || _a === void 0 ? void 0 : _a[0].details) === null || _b === void 0 ? void 0 : _b.text);
968
- this.outcome = outcome;
969
- }
970
- }
971
-
972
823
  var _ReadablePromise_suspender, _ReadablePromise_status, _ReadablePromise_response, _ReadablePromise_error, _a;
973
824
  /**
974
825
  * The ReadablePromise class wraps a request promise suitable for React Suspense.
@@ -1333,10 +1184,11 @@
1333
1184
 
1334
1185
  // PKCE auth ased on:
1335
1186
  // https://aws.amazon.com/blogs/security/how-to-add-authentication-single-page-web-application-with-amazon-cognito-oauth2-implementation/
1336
- var _MedplumClient_instances, _MedplumClient_fetch, _MedplumClient_createPdf, _MedplumClient_storage, _MedplumClient_schema, _MedplumClient_requestCache, _MedplumClient_baseUrl, _MedplumClient_clientId, _MedplumClient_authorizeUrl, _MedplumClient_tokenUrl, _MedplumClient_logoutUrl, _MedplumClient_onUnauthenticated, _MedplumClient_accessToken, _MedplumClient_refreshToken, _MedplumClient_refreshPromise, _MedplumClient_profilePromise, _MedplumClient_profile, _MedplumClient_config, _MedplumClient_addLogin, _MedplumClient_refreshProfile, _MedplumClient_request, _MedplumClient_addFetchOptionsDefaults, _MedplumClient_setRequestContentType, _MedplumClient_setRequestBody, _MedplumClient_handleUnauthenticated, _MedplumClient_startPkce, _MedplumClient_requestAuthorization, _MedplumClient_refresh, _MedplumClient_fetchTokens, _MedplumClient_verifyTokens, _MedplumClient_setupStorageListener;
1187
+ var _MedplumClient_instances, _MedplumClient_fetch, _MedplumClient_createPdf, _MedplumClient_storage, _MedplumClient_schema, _MedplumClient_requestCache, _MedplumClient_cacheTime, _MedplumClient_baseUrl, _MedplumClient_clientId, _MedplumClient_authorizeUrl, _MedplumClient_tokenUrl, _MedplumClient_logoutUrl, _MedplumClient_onUnauthenticated, _MedplumClient_accessToken, _MedplumClient_refreshToken, _MedplumClient_refreshPromise, _MedplumClient_profilePromise, _MedplumClient_profile, _MedplumClient_config, _MedplumClient_addLogin, _MedplumClient_refreshProfile, _MedplumClient_getCacheEntry, _MedplumClient_setCacheEntry, _MedplumClient_request, _MedplumClient_addFetchOptionsDefaults, _MedplumClient_setRequestContentType, _MedplumClient_setRequestBody, _MedplumClient_handleUnauthenticated, _MedplumClient_startPkce, _MedplumClient_requestAuthorization, _MedplumClient_refresh, _MedplumClient_fetchTokens, _MedplumClient_verifyTokens, _MedplumClient_setupStorageListener;
1337
1188
  const DEFAULT_BASE_URL = 'https://api.medplum.com/';
1338
1189
  const DEFAULT_SCOPE = 'launch/patient openid fhirUser offline_access user/*.*';
1339
1190
  const DEFAULT_RESOURCE_CACHE_SIZE = 1000;
1191
+ const DEFAULT_CACHE_TIME = 10000; // 10 seconds
1340
1192
  const JSON_CONTENT_TYPE = 'application/json';
1341
1193
  const FHIR_CONTENT_TYPE = 'application/fhir+json';
1342
1194
  const PATCH_CONTENT_TYPE = 'application/json-patch+json';
@@ -1389,7 +1241,7 @@
1389
1241
  */
1390
1242
  class MedplumClient extends EventTarget {
1391
1243
  constructor(options) {
1392
- var _a;
1244
+ var _a, _b;
1393
1245
  super();
1394
1246
  _MedplumClient_instances.add(this);
1395
1247
  _MedplumClient_fetch.set(this, void 0);
@@ -1397,6 +1249,7 @@
1397
1249
  _MedplumClient_storage.set(this, void 0);
1398
1250
  _MedplumClient_schema.set(this, void 0);
1399
1251
  _MedplumClient_requestCache.set(this, void 0);
1252
+ _MedplumClient_cacheTime.set(this, void 0);
1400
1253
  _MedplumClient_baseUrl.set(this, void 0);
1401
1254
  _MedplumClient_clientId.set(this, void 0);
1402
1255
  _MedplumClient_authorizeUrl.set(this, void 0);
@@ -1422,6 +1275,7 @@
1422
1275
  __classPrivateFieldSet(this, _MedplumClient_storage, new ClientStorage(), "f");
1423
1276
  __classPrivateFieldSet(this, _MedplumClient_schema, createSchema(), "f");
1424
1277
  __classPrivateFieldSet(this, _MedplumClient_requestCache, new LRUCache((_a = options === null || options === void 0 ? void 0 : options.resourceCacheSize) !== null && _a !== void 0 ? _a : DEFAULT_RESOURCE_CACHE_SIZE), "f");
1278
+ __classPrivateFieldSet(this, _MedplumClient_cacheTime, (_b = options === null || options === void 0 ? void 0 : options.cacheTime) !== null && _b !== void 0 ? _b : DEFAULT_CACHE_TIME, "f");
1425
1279
  __classPrivateFieldSet(this, _MedplumClient_baseUrl, (options === null || options === void 0 ? void 0 : options.baseUrl) || DEFAULT_BASE_URL, "f");
1426
1280
  __classPrivateFieldSet(this, _MedplumClient_clientId, (options === null || options === void 0 ? void 0 : options.clientId) || '', "f");
1427
1281
  __classPrivateFieldSet(this, _MedplumClient_authorizeUrl, (options === null || options === void 0 ? void 0 : options.authorizeUrl) || __classPrivateFieldGet(this, _MedplumClient_baseUrl, "f") + 'oauth2/authorize', "f");
@@ -1490,14 +1344,12 @@
1490
1344
  */
1491
1345
  get(url, options = {}) {
1492
1346
  url = url.toString();
1493
- if (!(options === null || options === void 0 ? void 0 : options.cache)) {
1494
- const cached = __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").get(url);
1495
- if (cached) {
1496
- return cached;
1497
- }
1347
+ const cached = __classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_getCacheEntry).call(this, url, options);
1348
+ if (cached) {
1349
+ return cached.value;
1498
1350
  }
1499
1351
  const promise = new ReadablePromise(__classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_request).call(this, 'GET', url, options));
1500
- __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").set(url, promise);
1352
+ __classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_setCacheEntry).call(this, url, promise);
1501
1353
  return promise;
1502
1354
  }
1503
1355
  /**
@@ -1737,14 +1589,12 @@
1737
1589
  url.searchParams.set('_count', '1');
1738
1590
  url.searchParams.sort();
1739
1591
  const cacheKey = url.toString() + '-searchOne';
1740
- if (!(options === null || options === void 0 ? void 0 : options.cache)) {
1741
- const cached = __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").get(cacheKey);
1742
- if (cached) {
1743
- return cached;
1744
- }
1592
+ const cached = __classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_getCacheEntry).call(this, cacheKey, options);
1593
+ if (cached) {
1594
+ return cached.value;
1745
1595
  }
1746
1596
  const promise = new ReadablePromise(this.search(resourceType, url.searchParams, options).then((b) => { var _a, _b; return (_b = (_a = b.entry) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.resource; }));
1747
- __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").set(cacheKey, promise);
1597
+ __classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_setCacheEntry).call(this, cacheKey, promise);
1748
1598
  return promise;
1749
1599
  }
1750
1600
  /**
@@ -1769,14 +1619,12 @@
1769
1619
  searchResources(resourceType, query, options = {}) {
1770
1620
  const url = this.fhirSearchUrl(resourceType, query);
1771
1621
  const cacheKey = url.toString() + '-searchResources';
1772
- if (!(options === null || options === void 0 ? void 0 : options.cache)) {
1773
- const cached = __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").get(cacheKey);
1774
- if (cached) {
1775
- return cached;
1776
- }
1622
+ const cached = __classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_getCacheEntry).call(this, cacheKey, options);
1623
+ if (cached) {
1624
+ return cached.value;
1777
1625
  }
1778
1626
  const promise = new ReadablePromise(this.search(resourceType, query, options).then((b) => { var _a, _b; return (_b = (_a = b.entry) === null || _a === void 0 ? void 0 : _a.map((e) => e.resource)) !== null && _b !== void 0 ? _b : []; }));
1779
- __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").set(cacheKey, promise);
1627
+ __classPrivateFieldGet(this, _MedplumClient_instances, "m", _MedplumClient_setCacheEntry).call(this, cacheKey, promise);
1780
1628
  return promise;
1781
1629
  }
1782
1630
  /**
@@ -1799,7 +1647,8 @@
1799
1647
  * @returns The resource if it is available in the cache; undefined otherwise.
1800
1648
  */
1801
1649
  getCached(resourceType, id) {
1802
- const cached = __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").get(this.fhirUrl(resourceType, id).toString());
1650
+ var _a;
1651
+ const cached = (_a = __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").get(this.fhirUrl(resourceType, id).toString())) === null || _a === void 0 ? void 0 : _a.value;
1803
1652
  return cached && !cached.isPending() ? cached.read() : undefined;
1804
1653
  }
1805
1654
  /**
@@ -2363,7 +2212,7 @@
2363
2212
  });
2364
2213
  }
2365
2214
  }
2366
- _MedplumClient_fetch = new WeakMap(), _MedplumClient_createPdf = new WeakMap(), _MedplumClient_storage = new WeakMap(), _MedplumClient_schema = new WeakMap(), _MedplumClient_requestCache = new WeakMap(), _MedplumClient_baseUrl = new WeakMap(), _MedplumClient_clientId = new WeakMap(), _MedplumClient_authorizeUrl = new WeakMap(), _MedplumClient_tokenUrl = new WeakMap(), _MedplumClient_logoutUrl = new WeakMap(), _MedplumClient_onUnauthenticated = new WeakMap(), _MedplumClient_accessToken = new WeakMap(), _MedplumClient_refreshToken = new WeakMap(), _MedplumClient_refreshPromise = new WeakMap(), _MedplumClient_profilePromise = new WeakMap(), _MedplumClient_profile = new WeakMap(), _MedplumClient_config = new WeakMap(), _MedplumClient_instances = new WeakSet(), _MedplumClient_addLogin = function _MedplumClient_addLogin(newLogin) {
2215
+ _MedplumClient_fetch = new WeakMap(), _MedplumClient_createPdf = new WeakMap(), _MedplumClient_storage = new WeakMap(), _MedplumClient_schema = new WeakMap(), _MedplumClient_requestCache = new WeakMap(), _MedplumClient_cacheTime = new WeakMap(), _MedplumClient_baseUrl = new WeakMap(), _MedplumClient_clientId = new WeakMap(), _MedplumClient_authorizeUrl = new WeakMap(), _MedplumClient_tokenUrl = new WeakMap(), _MedplumClient_logoutUrl = new WeakMap(), _MedplumClient_onUnauthenticated = new WeakMap(), _MedplumClient_accessToken = new WeakMap(), _MedplumClient_refreshToken = new WeakMap(), _MedplumClient_refreshPromise = new WeakMap(), _MedplumClient_profilePromise = new WeakMap(), _MedplumClient_profile = new WeakMap(), _MedplumClient_config = new WeakMap(), _MedplumClient_instances = new WeakSet(), _MedplumClient_addLogin = function _MedplumClient_addLogin(newLogin) {
2367
2216
  const logins = this.getLogins().filter((login) => { var _a, _b; return ((_a = login.profile) === null || _a === void 0 ? void 0 : _a.reference) !== ((_b = newLogin.profile) === null || _b === void 0 ? void 0 : _b.reference); });
2368
2217
  logins.push(newLogin);
2369
2218
  __classPrivateFieldGet(this, _MedplumClient_storage, "f").setObject('logins', logins);
@@ -2382,6 +2231,19 @@
2382
2231
  }), "f");
2383
2232
  return __classPrivateFieldGet(this, _MedplumClient_profilePromise, "f");
2384
2233
  });
2234
+ }, _MedplumClient_getCacheEntry = function _MedplumClient_getCacheEntry(key, options) {
2235
+ if (__classPrivateFieldGet(this, _MedplumClient_cacheTime, "f") <= 0 || (options === null || options === void 0 ? void 0 : options.cache) === 'no-cache' || (options === null || options === void 0 ? void 0 : options.cache) === 'reload') {
2236
+ return undefined;
2237
+ }
2238
+ const entry = __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").get(key);
2239
+ if (!entry || entry.requestTime + __classPrivateFieldGet(this, _MedplumClient_cacheTime, "f") < Date.now()) {
2240
+ return undefined;
2241
+ }
2242
+ return entry;
2243
+ }, _MedplumClient_setCacheEntry = function _MedplumClient_setCacheEntry(key, value) {
2244
+ if (__classPrivateFieldGet(this, _MedplumClient_cacheTime, "f") > 0) {
2245
+ __classPrivateFieldGet(this, _MedplumClient_requestCache, "f").set(key, { requestTime: Date.now(), value });
2246
+ }
2385
2247
  }, _MedplumClient_request = function _MedplumClient_request(method, url, options = {}) {
2386
2248
  return __awaiter(this, void 0, void 0, function* () {
2387
2249
  if (__classPrivateFieldGet(this, _MedplumClient_refreshPromise, "f")) {
@@ -2402,8 +2264,8 @@
2402
2264
  return undefined;
2403
2265
  }
2404
2266
  const obj = yield response.json();
2405
- if ((obj === null || obj === void 0 ? void 0 : obj.resourceType) === 'OperationOutcome' && !isOk(obj)) {
2406
- return Promise.reject(obj);
2267
+ if (response.status >= 400) {
2268
+ throw obj;
2407
2269
  }
2408
2270
  return obj;
2409
2271
  });
@@ -5192,6 +5054,155 @@
5192
5054
  }
5193
5055
  }
5194
5056
 
5057
+ const OK_ID = 'ok';
5058
+ const CREATED_ID = 'created';
5059
+ const GONE_ID = 'gone';
5060
+ const NOT_MODIFIED_ID = 'not-modified';
5061
+ const NOT_FOUND_ID = 'not-found';
5062
+ const ACCESS_DENIED = 'access-denied';
5063
+ const allOk = {
5064
+ resourceType: 'OperationOutcome',
5065
+ id: OK_ID,
5066
+ issue: [
5067
+ {
5068
+ severity: 'information',
5069
+ code: 'information',
5070
+ details: {
5071
+ text: 'All OK',
5072
+ },
5073
+ },
5074
+ ],
5075
+ };
5076
+ const created = {
5077
+ resourceType: 'OperationOutcome',
5078
+ id: CREATED_ID,
5079
+ issue: [
5080
+ {
5081
+ severity: 'information',
5082
+ code: 'information',
5083
+ details: {
5084
+ text: 'Created',
5085
+ },
5086
+ },
5087
+ ],
5088
+ };
5089
+ const notModified = {
5090
+ resourceType: 'OperationOutcome',
5091
+ id: NOT_MODIFIED_ID,
5092
+ issue: [
5093
+ {
5094
+ severity: 'information',
5095
+ code: 'information',
5096
+ details: {
5097
+ text: 'Not Modified',
5098
+ },
5099
+ },
5100
+ ],
5101
+ };
5102
+ const notFound = {
5103
+ resourceType: 'OperationOutcome',
5104
+ id: NOT_FOUND_ID,
5105
+ issue: [
5106
+ {
5107
+ severity: 'error',
5108
+ code: 'not-found',
5109
+ details: {
5110
+ text: 'Not found',
5111
+ },
5112
+ },
5113
+ ],
5114
+ };
5115
+ const gone = {
5116
+ resourceType: 'OperationOutcome',
5117
+ id: GONE_ID,
5118
+ issue: [
5119
+ {
5120
+ severity: 'error',
5121
+ code: 'gone',
5122
+ details: {
5123
+ text: 'Gone',
5124
+ },
5125
+ },
5126
+ ],
5127
+ };
5128
+ const accessDenied = {
5129
+ resourceType: 'OperationOutcome',
5130
+ id: ACCESS_DENIED,
5131
+ issue: [
5132
+ {
5133
+ severity: 'error',
5134
+ code: 'access-denied',
5135
+ details: {
5136
+ text: 'Access Denied',
5137
+ },
5138
+ },
5139
+ ],
5140
+ };
5141
+ function badRequest(details, expression) {
5142
+ return {
5143
+ resourceType: 'OperationOutcome',
5144
+ issue: [
5145
+ {
5146
+ severity: 'error',
5147
+ code: 'invalid',
5148
+ details: {
5149
+ text: details,
5150
+ },
5151
+ expression: expression ? [expression] : undefined,
5152
+ },
5153
+ ],
5154
+ };
5155
+ }
5156
+ function isOk(outcome) {
5157
+ return outcome.id === OK_ID || outcome.id === CREATED_ID || outcome.id === NOT_MODIFIED_ID;
5158
+ }
5159
+ function isNotFound(outcome) {
5160
+ return outcome.id === NOT_FOUND_ID;
5161
+ }
5162
+ function isGone(outcome) {
5163
+ return outcome.id === GONE_ID;
5164
+ }
5165
+ function getStatus(outcome) {
5166
+ if (outcome.id === OK_ID) {
5167
+ return 200;
5168
+ }
5169
+ else if (outcome.id === CREATED_ID) {
5170
+ return 201;
5171
+ }
5172
+ else if (outcome.id === NOT_MODIFIED_ID) {
5173
+ return 304;
5174
+ }
5175
+ else if (outcome.id === ACCESS_DENIED) {
5176
+ return 403;
5177
+ }
5178
+ else if (outcome.id === NOT_FOUND_ID) {
5179
+ return 404;
5180
+ }
5181
+ else if (outcome.id === GONE_ID) {
5182
+ return 410;
5183
+ }
5184
+ else {
5185
+ return 400;
5186
+ }
5187
+ }
5188
+ /**
5189
+ * Asserts that the operation completed successfully and that the resource is defined.
5190
+ * @param outcome The operation outcome.
5191
+ * @param resource The resource that may or may not have been returned.
5192
+ */
5193
+ function assertOk(outcome, resource) {
5194
+ if (!isOk(outcome) || resource === undefined) {
5195
+ throw new OperationOutcomeError(outcome);
5196
+ }
5197
+ }
5198
+ class OperationOutcomeError extends Error {
5199
+ constructor(outcome) {
5200
+ var _a, _b;
5201
+ super((_b = (_a = outcome === null || outcome === void 0 ? void 0 : outcome.issue) === null || _a === void 0 ? void 0 : _a[0].details) === null || _b === void 0 ? void 0 : _b.text);
5202
+ this.outcome = outcome;
5203
+ }
5204
+ }
5205
+
5195
5206
  const DEFAULT_SEARCH_COUNT = 20;
5196
5207
  /**
5197
5208
  * Search operators.