@medplum/core 2.0.21 → 2.0.23
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.cjs +720 -494
- package/dist/cjs/index.cjs.map +1 -1
- package/dist/cjs/index.min.cjs +1 -1
- package/dist/esm/client.mjs +197 -114
- package/dist/esm/client.mjs.map +1 -1
- package/dist/esm/crypto.mjs +3 -1
- package/dist/esm/crypto.mjs.map +1 -1
- package/dist/esm/fhirlexer/parse.mjs.map +1 -1
- package/dist/esm/fhirlexer/tokenize.mjs +2 -2
- package/dist/esm/fhirlexer/tokenize.mjs.map +1 -1
- package/dist/esm/fhirpath/atoms.mjs +63 -56
- package/dist/esm/fhirpath/atoms.mjs.map +1 -1
- package/dist/esm/fhirpath/functions.mjs +370 -252
- package/dist/esm/fhirpath/functions.mjs.map +1 -1
- package/dist/esm/fhirpath/parse.mjs +4 -2
- package/dist/esm/fhirpath/parse.mjs.map +1 -1
- package/dist/esm/format.mjs +6 -4
- package/dist/esm/format.mjs.map +1 -1
- package/dist/esm/hl7.mjs +1 -1
- package/dist/esm/hl7.mjs.map +1 -1
- package/dist/esm/index.min.mjs +1 -1
- package/dist/esm/index.mjs +2 -1
- package/dist/esm/index.mjs.map +1 -1
- package/dist/esm/jwt.mjs +4 -2
- package/dist/esm/jwt.mjs.map +1 -1
- package/dist/esm/outcomes.mjs +14 -11
- package/dist/esm/outcomes.mjs.map +1 -1
- package/dist/esm/schema.mjs +4 -10
- package/dist/esm/schema.mjs.map +1 -1
- package/dist/esm/search/details.mjs +4 -5
- package/dist/esm/search/details.mjs.map +1 -1
- package/dist/esm/search/match.mjs +1 -0
- package/dist/esm/search/match.mjs.map +1 -1
- package/dist/esm/search/search.mjs +1 -1
- package/dist/esm/search/search.mjs.map +1 -1
- package/dist/esm/storage.mjs +8 -0
- package/dist/esm/storage.mjs.map +1 -1
- package/dist/esm/types.mjs +1 -0
- package/dist/esm/types.mjs.map +1 -1
- package/dist/esm/utils.mjs +8 -7
- package/dist/esm/utils.mjs.map +1 -1
- package/dist/types/client.d.ts +128 -69
- package/dist/types/crypto.d.ts +3 -1
- package/dist/types/fhirlexer/parse.d.ts +7 -3
- package/dist/types/fhirpath/atoms.d.ts +21 -21
- package/dist/types/fhirpath/functions.d.ts +2 -2
- package/dist/types/fhirpath/parse.d.ts +2 -1
- package/dist/types/hl7.d.ts +1 -1
- package/dist/types/index.d.ts +1 -0
- package/dist/types/jwt.d.ts +2 -1
- package/dist/types/outcomes.d.ts +7 -1
- package/dist/types/schema.d.ts +4 -10
- package/dist/types/search/details.d.ts +0 -1
- package/dist/types/search/search.d.ts +1 -1
- package/dist/types/storage.d.ts +8 -0
- package/dist/types/typeschema/types.d.ts +0 -1
- package/dist/types/utils.d.ts +5 -12
- package/package.json +1 -1
package/dist/cjs/index.cjs
CHANGED
|
@@ -4,6 +4,37 @@
|
|
|
4
4
|
(global = typeof globalThis !== 'undefined' ? globalThis : global || self, factory((global.medplum = global.medplum || {}, global.medplum.core = {})));
|
|
5
5
|
})(this, (function (exports) { 'use strict';
|
|
6
6
|
|
|
7
|
+
/**
|
|
8
|
+
* Decodes a base64 string.
|
|
9
|
+
* Handles both browser and Node environments.
|
|
10
|
+
* @param data The base-64 encoded input string.
|
|
11
|
+
* @returns The decoded string.
|
|
12
|
+
*/
|
|
13
|
+
function decodeBase64(data) {
|
|
14
|
+
if (typeof window !== 'undefined') {
|
|
15
|
+
return window.atob(data);
|
|
16
|
+
}
|
|
17
|
+
if (typeof Buffer !== 'undefined') {
|
|
18
|
+
return Buffer.from(data, 'base64').toString('binary');
|
|
19
|
+
}
|
|
20
|
+
throw new Error('Unable to decode base64');
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Encodes a base64 string.
|
|
24
|
+
* Handles both browser and Node environments.
|
|
25
|
+
* @param data The unencoded input string.
|
|
26
|
+
* @returns The base-64 encoded string.
|
|
27
|
+
*/
|
|
28
|
+
function encodeBase64(data) {
|
|
29
|
+
if (typeof window !== 'undefined') {
|
|
30
|
+
return window.btoa(data);
|
|
31
|
+
}
|
|
32
|
+
if (typeof Buffer !== 'undefined') {
|
|
33
|
+
return Buffer.from(data, 'binary').toString('base64');
|
|
34
|
+
}
|
|
35
|
+
throw new Error('Unable to encode base64');
|
|
36
|
+
}
|
|
37
|
+
|
|
7
38
|
/**
|
|
8
39
|
* More on Bundles can be found here
|
|
9
40
|
* http://hl7.org/fhir/R4/bundle.html
|
|
@@ -454,18 +485,20 @@
|
|
|
454
485
|
}
|
|
455
486
|
/**
|
|
456
487
|
* Returns the input number increased by the `n` units of the specified precision
|
|
457
|
-
* @param a The input number
|
|
488
|
+
* @param a The input number.
|
|
458
489
|
* @param precision The precision in number of digits.
|
|
459
|
-
* @param n (default 1) The number of units to add
|
|
490
|
+
* @param n (default 1) The number of units to add.
|
|
491
|
+
* @returns The result of the increment.
|
|
460
492
|
*/
|
|
461
493
|
function preciseIncrement(a, precision, n = 1) {
|
|
462
494
|
return (toPreciseInteger$1(a, precision) + n) * Math.pow(10, -precision);
|
|
463
495
|
}
|
|
464
496
|
/**
|
|
465
497
|
* Returns the input number decreased by the `n` units of the specified precision
|
|
466
|
-
* @param a The input number
|
|
498
|
+
* @param a The input number.
|
|
467
499
|
* @param precision The precision in number of digits.
|
|
468
|
-
* @param n (default 1) The number of units to subtract
|
|
500
|
+
* @param n (default 1) The number of units to subtract.
|
|
501
|
+
* @returns The result of the decrement.
|
|
469
502
|
*/
|
|
470
503
|
function preciseDecrement(a, precision, n = 1) {
|
|
471
504
|
return (toPreciseInteger$1(a, precision) - n) * Math.pow(10, -precision);
|
|
@@ -523,7 +556,7 @@
|
|
|
523
556
|
/**
|
|
524
557
|
* Returns a display string for the resource.
|
|
525
558
|
* @param resource The input resource.
|
|
526
|
-
* @
|
|
559
|
+
* @returns Human friendly display string.
|
|
527
560
|
*/
|
|
528
561
|
function getDisplayString(resource) {
|
|
529
562
|
if (isProfileResource(resource)) {
|
|
@@ -680,7 +713,7 @@
|
|
|
680
713
|
}
|
|
681
714
|
/**
|
|
682
715
|
* Recursively builds the questionnaire answer items map.
|
|
683
|
-
* @param
|
|
716
|
+
* @param items The current questionnaire response items.
|
|
684
717
|
* @param result The cumulative result map.
|
|
685
718
|
*/
|
|
686
719
|
function buildQuestionnaireAnswerItems(items, result) {
|
|
@@ -699,7 +732,6 @@
|
|
|
699
732
|
* If multiple identifiers exist with the same system, the first one is returned.
|
|
700
733
|
*
|
|
701
734
|
* If the system is not found, then returns undefined.
|
|
702
|
-
*
|
|
703
735
|
* @param resource The resource to check.
|
|
704
736
|
* @param system The identifier system.
|
|
705
737
|
* @returns The identifier value if found; otherwise undefined.
|
|
@@ -763,8 +795,9 @@
|
|
|
763
795
|
* Evaluates JSON key/value pairs for FHIR JSON stringify.
|
|
764
796
|
* Removes properties with empty string values.
|
|
765
797
|
* Removes objects with zero properties.
|
|
766
|
-
* @param
|
|
767
|
-
* @param
|
|
798
|
+
* @param k Property key.
|
|
799
|
+
* @param v Property value.
|
|
800
|
+
* @returns The replaced value.
|
|
768
801
|
*/
|
|
769
802
|
function stringifyReplacer(k, v) {
|
|
770
803
|
return !isArrayKey(k) && isEmpty(v) ? undefined : v;
|
|
@@ -794,6 +827,7 @@
|
|
|
794
827
|
* Ignores meta.versionId and meta.lastUpdated.
|
|
795
828
|
* @param object1 The first object.
|
|
796
829
|
* @param object2 The second object.
|
|
830
|
+
* @param path Optional path string.
|
|
797
831
|
* @returns True if the objects are equal.
|
|
798
832
|
*/
|
|
799
833
|
function deepEquals$1(object1, object2, path) {
|
|
@@ -859,7 +893,6 @@
|
|
|
859
893
|
*
|
|
860
894
|
* See: https://web.dev/structured-clone/
|
|
861
895
|
* See: https://stackoverflow.com/questions/40488190/how-is-structured-clone-algorithm-different-from-deep-copy
|
|
862
|
-
*
|
|
863
896
|
* @param input The input to clone.
|
|
864
897
|
* @returns A deep clone of the input.
|
|
865
898
|
*/
|
|
@@ -876,7 +909,7 @@
|
|
|
876
909
|
}
|
|
877
910
|
/**
|
|
878
911
|
* Returns true if the input is an object.
|
|
879
|
-
* @param
|
|
912
|
+
* @param obj The candidate object.
|
|
880
913
|
* @returns True if the input is a non-null non-undefined object.
|
|
881
914
|
*/
|
|
882
915
|
function isObject$1(obj) {
|
|
@@ -961,6 +994,7 @@
|
|
|
961
994
|
* @param definition The observation definition.
|
|
962
995
|
* @param patient The patient.
|
|
963
996
|
* @param value The observation value.
|
|
997
|
+
* @param category Optional interval category restriction.
|
|
964
998
|
* @returns The observation interval if found; otherwise undefined.
|
|
965
999
|
*/
|
|
966
1000
|
function findObservationInterval(definition, patient, value, category) {
|
|
@@ -1113,6 +1147,7 @@
|
|
|
1113
1147
|
|
|
1114
1148
|
/**
|
|
1115
1149
|
* Returns a cryptographically secure random string.
|
|
1150
|
+
* @returns A cryptographically secure random string.
|
|
1116
1151
|
*/
|
|
1117
1152
|
function getRandomString() {
|
|
1118
1153
|
const randomItems = new Uint32Array(28);
|
|
@@ -1121,7 +1156,8 @@
|
|
|
1121
1156
|
}
|
|
1122
1157
|
/**
|
|
1123
1158
|
* Encrypts a string with SHA256 encryption.
|
|
1124
|
-
* @param str
|
|
1159
|
+
* @param str The unencrypted input string.
|
|
1160
|
+
* @returns The encrypted value in an ArrayBuffer.
|
|
1125
1161
|
*/
|
|
1126
1162
|
async function encryptSHA256(str) {
|
|
1127
1163
|
return crypto.subtle.digest('SHA-256', new TextEncoder().encode(str));
|
|
@@ -1161,41 +1197,11 @@
|
|
|
1161
1197
|
}
|
|
1162
1198
|
}
|
|
1163
1199
|
|
|
1164
|
-
/**
|
|
1165
|
-
* Decodes a base64 string.
|
|
1166
|
-
* Handles both browser and Node environments.
|
|
1167
|
-
* @param data The base-64 encoded input string.
|
|
1168
|
-
* @returns The decoded string.
|
|
1169
|
-
*/
|
|
1170
|
-
function decodeBase64(data) {
|
|
1171
|
-
if (typeof window !== 'undefined') {
|
|
1172
|
-
return window.atob(data);
|
|
1173
|
-
}
|
|
1174
|
-
if (typeof Buffer !== 'undefined') {
|
|
1175
|
-
return Buffer.from(data, 'base64').toString('binary');
|
|
1176
|
-
}
|
|
1177
|
-
throw new Error('Unable to decode base64');
|
|
1178
|
-
}
|
|
1179
|
-
/**
|
|
1180
|
-
* Encodes a base64 string.
|
|
1181
|
-
* Handles both browser and Node environments.
|
|
1182
|
-
* @param data The unencoded input string.
|
|
1183
|
-
* @returns The base-64 encoded string.
|
|
1184
|
-
*/
|
|
1185
|
-
function encodeBase64(data) {
|
|
1186
|
-
if (typeof window !== 'undefined') {
|
|
1187
|
-
return window.btoa(data);
|
|
1188
|
-
}
|
|
1189
|
-
if (typeof Buffer !== 'undefined') {
|
|
1190
|
-
return Buffer.from(data, 'binary').toString('base64');
|
|
1191
|
-
}
|
|
1192
|
-
throw new Error('Unable to encode base64');
|
|
1193
|
-
}
|
|
1194
|
-
|
|
1195
1200
|
/**
|
|
1196
1201
|
* Decodes a section of a JWT.
|
|
1197
1202
|
* See: https://tools.ietf.org/html/rfc7519
|
|
1198
|
-
* @param payload
|
|
1203
|
+
* @param payload The JWT payload string.
|
|
1204
|
+
* @returns Collection of key value claims in the JWT payload.
|
|
1199
1205
|
*/
|
|
1200
1206
|
function decodePayload(payload) {
|
|
1201
1207
|
const cleanedPayload = payload.replace(/-/g, '+').replace(/_/g, '/');
|
|
@@ -1209,7 +1215,8 @@
|
|
|
1209
1215
|
}
|
|
1210
1216
|
/**
|
|
1211
1217
|
* Parses the JWT payload.
|
|
1212
|
-
* @param token JWT token
|
|
1218
|
+
* @param token JWT token.
|
|
1219
|
+
* @returns Collection of key value claims in the JWT payload.
|
|
1213
1220
|
*/
|
|
1214
1221
|
function parseJWTPayload(token) {
|
|
1215
1222
|
const [_header, payload, _signature] = token.split('.');
|
|
@@ -1469,18 +1476,21 @@
|
|
|
1469
1476
|
* @returns The string representation of the operation outcome.
|
|
1470
1477
|
*/
|
|
1471
1478
|
function operationOutcomeToString(outcome) {
|
|
1472
|
-
const strs = [];
|
|
1473
|
-
if (outcome.issue) {
|
|
1474
|
-
for (const issue of outcome.issue) {
|
|
1475
|
-
let issueStr = issue.details?.text || 'Unknown error';
|
|
1476
|
-
if (issue.expression?.length) {
|
|
1477
|
-
issueStr += ` (${issue.expression.join(', ')})`;
|
|
1478
|
-
}
|
|
1479
|
-
strs.push(issueStr);
|
|
1480
|
-
}
|
|
1481
|
-
}
|
|
1479
|
+
const strs = outcome.issue?.map(operationOutcomeIssueToString) ?? [];
|
|
1482
1480
|
return strs.length > 0 ? strs.join('; ') : 'Unknown error';
|
|
1483
1481
|
}
|
|
1482
|
+
/**
|
|
1483
|
+
* Returns a string represenation of the operation outcome issue.
|
|
1484
|
+
* @param issue The operation outcome issue.
|
|
1485
|
+
* @returns The string representation of the operation outcome issue.
|
|
1486
|
+
*/
|
|
1487
|
+
function operationOutcomeIssueToString(issue) {
|
|
1488
|
+
let issueStr = issue.details?.text ?? issue.diagnostics ?? 'Unknown error';
|
|
1489
|
+
if (issue.expression?.length) {
|
|
1490
|
+
issueStr += ` (${issue.expression.join(', ')})`;
|
|
1491
|
+
}
|
|
1492
|
+
return issueStr;
|
|
1493
|
+
}
|
|
1484
1494
|
|
|
1485
1495
|
var _a;
|
|
1486
1496
|
/**
|
|
@@ -1604,6 +1614,7 @@
|
|
|
1604
1614
|
}
|
|
1605
1615
|
/**
|
|
1606
1616
|
* Returns the number of key/value pairs.
|
|
1617
|
+
* @returns The number of key/value pairs.
|
|
1607
1618
|
*/
|
|
1608
1619
|
get length() {
|
|
1609
1620
|
return this.data.size;
|
|
@@ -1616,12 +1627,16 @@
|
|
|
1616
1627
|
}
|
|
1617
1628
|
/**
|
|
1618
1629
|
* Returns the current value associated with the given key, or null if the given key does not exist.
|
|
1630
|
+
* @param key The specified storage key.
|
|
1631
|
+
* @returns The current value associated with the given key, or null if the given key does not exist.
|
|
1619
1632
|
*/
|
|
1620
1633
|
getItem(key) {
|
|
1621
1634
|
return this.data.get(key) ?? null;
|
|
1622
1635
|
}
|
|
1623
1636
|
/**
|
|
1624
1637
|
* Sets the value of the pair identified by key to value, creating a new key/value pair if none existed for key previously.
|
|
1638
|
+
* @param key The storage key.
|
|
1639
|
+
* @param value The new value.
|
|
1625
1640
|
*/
|
|
1626
1641
|
setItem(key, value) {
|
|
1627
1642
|
if (value) {
|
|
@@ -1633,12 +1648,15 @@
|
|
|
1633
1648
|
}
|
|
1634
1649
|
/**
|
|
1635
1650
|
* Removes the key/value pair with the given key, if a key/value pair with the given key exists.
|
|
1651
|
+
* @param key The storage key.
|
|
1636
1652
|
*/
|
|
1637
1653
|
removeItem(key) {
|
|
1638
1654
|
this.data.delete(key);
|
|
1639
1655
|
}
|
|
1640
1656
|
/**
|
|
1641
1657
|
* Returns the name of the nth key, or null if n is greater than or equal to the number of key/value pairs.
|
|
1658
|
+
* @param index The numeric index.
|
|
1659
|
+
* @returns The nth key.
|
|
1642
1660
|
*/
|
|
1643
1661
|
key(index) {
|
|
1644
1662
|
return Array.from(this.data.keys())[index];
|
|
@@ -6181,6 +6199,7 @@
|
|
|
6181
6199
|
}
|
|
6182
6200
|
/**
|
|
6183
6201
|
* Indexes PropertySchema from an ElementDefinition.
|
|
6202
|
+
* @param structureDefinition The input StructureDefinition.
|
|
6184
6203
|
* @param element The input ElementDefinition.
|
|
6185
6204
|
* @see {@link IndexedStructureDefinition} for more details on indexed StructureDefinitions.
|
|
6186
6205
|
*/
|
|
@@ -6417,7 +6436,7 @@
|
|
|
6417
6436
|
|
|
6418
6437
|
// PKCE auth based on:
|
|
6419
6438
|
// https://aws.amazon.com/blogs/security/how-to-add-authentication-single-page-web-application-with-amazon-cognito-oauth2-implementation/
|
|
6420
|
-
const MEDPLUM_VERSION = "2.0.
|
|
6439
|
+
const MEDPLUM_VERSION = "2.0.23-b244eeae" ;
|
|
6421
6440
|
const DEFAULT_BASE_URL = 'https://api.medplum.com/';
|
|
6422
6441
|
const DEFAULT_RESOURCE_CACHE_SIZE = 1000;
|
|
6423
6442
|
const DEFAULT_CACHE_TIME = 60000; // 60 seconds
|
|
@@ -6504,7 +6523,6 @@
|
|
|
6504
6523
|
* <head>
|
|
6505
6524
|
* <meta name="algolia:pageRank" content="100" />
|
|
6506
6525
|
* </head>
|
|
6507
|
-
|
|
6508
6526
|
*/
|
|
6509
6527
|
class MedplumClient extends EventTarget {
|
|
6510
6528
|
constructor(options) {
|
|
@@ -6557,6 +6575,16 @@
|
|
|
6557
6575
|
getBaseUrl() {
|
|
6558
6576
|
return this.baseUrl;
|
|
6559
6577
|
}
|
|
6578
|
+
/**
|
|
6579
|
+
* Returns the current authorize URL.
|
|
6580
|
+
* By default, this is set to `https://api.medplum.com/oauth2/authorize`.
|
|
6581
|
+
* This can be overridden by setting the `authorizeUrl` option when creating the client.
|
|
6582
|
+
* @category HTTP
|
|
6583
|
+
* @returns The current authorize URL.
|
|
6584
|
+
*/
|
|
6585
|
+
getAuthorizeUrl() {
|
|
6586
|
+
return this.authorizeUrl;
|
|
6587
|
+
}
|
|
6560
6588
|
/**
|
|
6561
6589
|
* Clears all auth state including local storage and session storage.
|
|
6562
6590
|
* @category Authentication
|
|
@@ -6571,12 +6599,14 @@
|
|
|
6571
6599
|
* @category Authentication
|
|
6572
6600
|
*/
|
|
6573
6601
|
clearActiveLogin() {
|
|
6602
|
+
if (this.basicAuth) {
|
|
6603
|
+
return;
|
|
6604
|
+
}
|
|
6574
6605
|
this.storage.setString('activeLogin', undefined);
|
|
6575
6606
|
this.requestCache?.clear();
|
|
6576
6607
|
this.accessToken = undefined;
|
|
6577
6608
|
this.refreshToken = undefined;
|
|
6578
|
-
this.
|
|
6579
|
-
this.config = undefined;
|
|
6609
|
+
this.sessionDetails = undefined;
|
|
6580
6610
|
this.dispatchEvent({ type: 'change' });
|
|
6581
6611
|
}
|
|
6582
6612
|
/**
|
|
@@ -6616,7 +6646,6 @@
|
|
|
6616
6646
|
* This is a lower level method for custom requests.
|
|
6617
6647
|
* For common operations, we recommend using higher level methods
|
|
6618
6648
|
* such as `readResource()`, `search()`, etc.
|
|
6619
|
-
*
|
|
6620
6649
|
* @category HTTP
|
|
6621
6650
|
* @param url The target URL.
|
|
6622
6651
|
* @param options Optional fetch options.
|
|
@@ -6656,7 +6685,6 @@
|
|
|
6656
6685
|
* This is a lower level method for custom requests.
|
|
6657
6686
|
* For common operations, we recommend using higher level methods
|
|
6658
6687
|
* such as `createResource()`.
|
|
6659
|
-
*
|
|
6660
6688
|
* @category HTTP
|
|
6661
6689
|
* @param url The target URL.
|
|
6662
6690
|
* @param body The content body. Strings and `File` objects are passed directly. Other objects are converted to JSON.
|
|
@@ -6681,7 +6709,6 @@
|
|
|
6681
6709
|
* This is a lower level method for custom requests.
|
|
6682
6710
|
* For common operations, we recommend using higher level methods
|
|
6683
6711
|
* such as `updateResource()`.
|
|
6684
|
-
*
|
|
6685
6712
|
* @category HTTP
|
|
6686
6713
|
* @param url The target URL.
|
|
6687
6714
|
* @param body The content body. Strings and `File` objects are passed directly. Other objects are converted to JSON.
|
|
@@ -6706,7 +6733,6 @@
|
|
|
6706
6733
|
* This is a lower level method for custom requests.
|
|
6707
6734
|
* For common operations, we recommend using higher level methods
|
|
6708
6735
|
* such as `patchResource()`.
|
|
6709
|
-
*
|
|
6710
6736
|
* @category HTTP
|
|
6711
6737
|
* @param url The target URL.
|
|
6712
6738
|
* @param operations Array of JSONPatch operations.
|
|
@@ -6727,13 +6753,12 @@
|
|
|
6727
6753
|
* This is a lower level method for custom requests.
|
|
6728
6754
|
* For common operations, we recommend using higher level methods
|
|
6729
6755
|
* such as `deleteResource()`.
|
|
6730
|
-
*
|
|
6731
6756
|
* @category HTTP
|
|
6732
6757
|
* @param url The target URL.
|
|
6733
6758
|
* @param options Optional fetch options.
|
|
6734
6759
|
* @returns Promise to the response content.
|
|
6735
6760
|
*/
|
|
6736
|
-
delete(url, options
|
|
6761
|
+
delete(url, options) {
|
|
6737
6762
|
url = url.toString();
|
|
6738
6763
|
this.invalidateUrl(url);
|
|
6739
6764
|
return this.request('DELETE', url, options);
|
|
@@ -6744,53 +6769,54 @@
|
|
|
6744
6769
|
* This method is part of the two different user registration flows:
|
|
6745
6770
|
* 1) New Practitioner and new Project
|
|
6746
6771
|
* 2) New Patient registration
|
|
6747
|
-
*
|
|
6748
6772
|
* @category Authentication
|
|
6749
6773
|
* @param newUserRequest Register request including email and password.
|
|
6774
|
+
* @param options Optional fetch options.
|
|
6750
6775
|
* @returns Promise to the authentication response.
|
|
6751
6776
|
*/
|
|
6752
|
-
async startNewUser(newUserRequest) {
|
|
6777
|
+
async startNewUser(newUserRequest, options) {
|
|
6753
6778
|
const { codeChallengeMethod, codeChallenge } = await this.startPkce();
|
|
6754
6779
|
return this.post('auth/newuser', {
|
|
6755
6780
|
...newUserRequest,
|
|
6756
6781
|
codeChallengeMethod,
|
|
6757
6782
|
codeChallenge,
|
|
6758
|
-
});
|
|
6783
|
+
}, undefined, options);
|
|
6759
6784
|
}
|
|
6760
6785
|
/**
|
|
6761
6786
|
* Initiates a new project flow.
|
|
6762
6787
|
*
|
|
6763
6788
|
* This requires a partial login from `startNewUser` or `startNewGoogleUser`.
|
|
6764
|
-
*
|
|
6765
6789
|
* @param newProjectRequest Register request including email and password.
|
|
6790
|
+
* @param options Optional fetch options.
|
|
6766
6791
|
* @returns Promise to the authentication response.
|
|
6767
6792
|
*/
|
|
6768
|
-
async startNewProject(newProjectRequest) {
|
|
6769
|
-
return this.post('auth/newproject', newProjectRequest);
|
|
6793
|
+
async startNewProject(newProjectRequest, options) {
|
|
6794
|
+
return this.post('auth/newproject', newProjectRequest, undefined, options);
|
|
6770
6795
|
}
|
|
6771
6796
|
/**
|
|
6772
6797
|
* Initiates a new patient flow.
|
|
6773
6798
|
*
|
|
6774
6799
|
* This requires a partial login from `startNewUser` or `startNewGoogleUser`.
|
|
6775
|
-
*
|
|
6776
6800
|
* @param newPatientRequest Register request including email and password.
|
|
6801
|
+
* @param options Optional fetch options.
|
|
6777
6802
|
* @returns Promise to the authentication response.
|
|
6778
6803
|
*/
|
|
6779
|
-
async startNewPatient(newPatientRequest) {
|
|
6780
|
-
return this.post('auth/newpatient', newPatientRequest);
|
|
6804
|
+
async startNewPatient(newPatientRequest, options) {
|
|
6805
|
+
return this.post('auth/newpatient', newPatientRequest, undefined, options);
|
|
6781
6806
|
}
|
|
6782
6807
|
/**
|
|
6783
6808
|
* Initiates a user login flow.
|
|
6784
6809
|
* @category Authentication
|
|
6785
6810
|
* @param loginRequest Login request including email and password.
|
|
6811
|
+
* @param options Optional fetch options.
|
|
6786
6812
|
* @returns Promise to the authentication response.
|
|
6787
6813
|
*/
|
|
6788
|
-
async startLogin(loginRequest) {
|
|
6814
|
+
async startLogin(loginRequest, options) {
|
|
6789
6815
|
return this.post('auth/login', {
|
|
6790
6816
|
...(await this.ensureCodeChallenge(loginRequest)),
|
|
6791
6817
|
clientId: loginRequest.clientId ?? this.clientId,
|
|
6792
6818
|
scope: loginRequest.scope,
|
|
6793
|
-
});
|
|
6819
|
+
}, undefined, options);
|
|
6794
6820
|
}
|
|
6795
6821
|
/**
|
|
6796
6822
|
* Tries to sign in with Google authentication.
|
|
@@ -6798,14 +6824,15 @@
|
|
|
6798
6824
|
* See: https://developers.google.com/identity/gsi/web/guides/handle-credential-responses-js-functions
|
|
6799
6825
|
* @category Authentication
|
|
6800
6826
|
* @param loginRequest Login request including Google credential response.
|
|
6827
|
+
* @param options Optional fetch options.
|
|
6801
6828
|
* @returns Promise to the authentication response.
|
|
6802
6829
|
*/
|
|
6803
|
-
async startGoogleLogin(loginRequest) {
|
|
6830
|
+
async startGoogleLogin(loginRequest, options) {
|
|
6804
6831
|
return this.post('auth/google', {
|
|
6805
6832
|
...(await this.ensureCodeChallenge(loginRequest)),
|
|
6806
6833
|
clientId: loginRequest.clientId ?? this.clientId,
|
|
6807
6834
|
scope: loginRequest.scope,
|
|
6808
|
-
});
|
|
6835
|
+
}, undefined, options);
|
|
6809
6836
|
}
|
|
6810
6837
|
/**
|
|
6811
6838
|
* Returns the PKCE code challenge and method.
|
|
@@ -6836,6 +6863,7 @@
|
|
|
6836
6863
|
* This may result in navigating away to the sign in page.
|
|
6837
6864
|
* @category Authentication
|
|
6838
6865
|
* @param loginParams Optional login parameters.
|
|
6866
|
+
* @returns The user profile resource if available.
|
|
6839
6867
|
*/
|
|
6840
6868
|
async signInWithRedirect(loginParams) {
|
|
6841
6869
|
const urlParams = new URLSearchParams(window.location.search);
|
|
@@ -6872,6 +6900,7 @@
|
|
|
6872
6900
|
* Exchange an external access token for a Medplum access token.
|
|
6873
6901
|
* @param token The access token that was generated by the external identity provider.
|
|
6874
6902
|
* @param clientId The ID of the `ClientApplication` in your Medplum project that will be making the exchange request.
|
|
6903
|
+
* @returns The user profile resource.
|
|
6875
6904
|
* @category Authentication
|
|
6876
6905
|
*/
|
|
6877
6906
|
async exchangeExternalAccessToken(token, clientId) {
|
|
@@ -6970,14 +6999,13 @@
|
|
|
6970
6999
|
* ```
|
|
6971
7000
|
*
|
|
6972
7001
|
* See FHIR search for full details: https://www.hl7.org/fhir/search.html
|
|
6973
|
-
*
|
|
6974
7002
|
* @category Search
|
|
6975
7003
|
* @param resourceType The FHIR resource type.
|
|
6976
7004
|
* @param query Optional FHIR search query or structured query object. Can be any valid input to the URLSearchParams() constructor.
|
|
6977
7005
|
* @param options Optional fetch options.
|
|
6978
7006
|
* @returns Promise to the search result bundle.
|
|
6979
7007
|
*/
|
|
6980
|
-
search(resourceType, query, options
|
|
7008
|
+
search(resourceType, query, options) {
|
|
6981
7009
|
const url = this.fhirSearchUrl(resourceType, query);
|
|
6982
7010
|
const cacheKey = url.toString() + '-search';
|
|
6983
7011
|
const cached = this.getCacheEntry(cacheKey, options);
|
|
@@ -7011,14 +7039,13 @@
|
|
|
7011
7039
|
* The return value is the resource, if available; otherwise, undefined.
|
|
7012
7040
|
*
|
|
7013
7041
|
* See FHIR search for full details: https://www.hl7.org/fhir/search.html
|
|
7014
|
-
*
|
|
7015
7042
|
* @category Search
|
|
7016
7043
|
* @param resourceType The FHIR resource type.
|
|
7017
7044
|
* @param query Optional FHIR search query or structured query object. Can be any valid input to the URLSearchParams() constructor.
|
|
7018
7045
|
* @param options Optional fetch options.
|
|
7019
7046
|
* @returns Promise to the first search result.
|
|
7020
7047
|
*/
|
|
7021
|
-
searchOne(resourceType, query, options
|
|
7048
|
+
searchOne(resourceType, query, options) {
|
|
7022
7049
|
const url = this.fhirSearchUrl(resourceType, query);
|
|
7023
7050
|
url.searchParams.set('_count', '1');
|
|
7024
7051
|
url.searchParams.sort();
|
|
@@ -7046,14 +7073,13 @@
|
|
|
7046
7073
|
* The return value is an array of resources.
|
|
7047
7074
|
*
|
|
7048
7075
|
* See FHIR search for full details: https://www.hl7.org/fhir/search.html
|
|
7049
|
-
*
|
|
7050
7076
|
* @category Search
|
|
7051
7077
|
* @param resourceType The FHIR resource type.
|
|
7052
7078
|
* @param query Optional FHIR search query or structured query object. Can be any valid input to the URLSearchParams() constructor.
|
|
7053
7079
|
* @param options Optional fetch options.
|
|
7054
7080
|
* @returns Promise to the array of search results.
|
|
7055
7081
|
*/
|
|
7056
|
-
searchResources(resourceType, query, options
|
|
7082
|
+
searchResources(resourceType, query, options) {
|
|
7057
7083
|
const url = this.fhirSearchUrl(resourceType, query);
|
|
7058
7084
|
const cacheKey = url.toString() + '-searchResources';
|
|
7059
7085
|
const cached = this.getCacheEntry(cacheKey, options);
|
|
@@ -7078,14 +7104,13 @@
|
|
|
7078
7104
|
* }
|
|
7079
7105
|
* }
|
|
7080
7106
|
* ```
|
|
7081
|
-
*
|
|
7082
7107
|
* @category Search
|
|
7083
7108
|
* @param resourceType The FHIR resource type.
|
|
7084
7109
|
* @param query Optional FHIR search query or structured query object. Can be any valid input to the URLSearchParams() constructor.
|
|
7085
7110
|
* @param options Optional fetch options.
|
|
7086
|
-
* @
|
|
7111
|
+
* @yields An async generator, where each result is an array of resources for each page.
|
|
7087
7112
|
*/
|
|
7088
|
-
async *searchResourcePages(resourceType, query, options
|
|
7113
|
+
async *searchResourcePages(resourceType, query, options) {
|
|
7089
7114
|
let url = this.fhirSearchUrl(resourceType, query);
|
|
7090
7115
|
while (url) {
|
|
7091
7116
|
const searchParams = new URL(url).searchParams;
|
|
@@ -7101,14 +7126,13 @@
|
|
|
7101
7126
|
/**
|
|
7102
7127
|
* Searches a ValueSet resource using the "expand" operation.
|
|
7103
7128
|
* See: https://www.hl7.org/fhir/operation-valueset-expand.html
|
|
7104
|
-
*
|
|
7105
7129
|
* @category Search
|
|
7106
7130
|
* @param system The ValueSet system url.
|
|
7107
7131
|
* @param filter The search string.
|
|
7108
7132
|
* @param options Optional fetch options.
|
|
7109
7133
|
* @returns Promise to expanded ValueSet.
|
|
7110
7134
|
*/
|
|
7111
|
-
searchValueSet(system, filter, options
|
|
7135
|
+
searchValueSet(system, filter, options) {
|
|
7112
7136
|
const url = this.fhirUrl('ValueSet', '$expand');
|
|
7113
7137
|
url.searchParams.set('url', system);
|
|
7114
7138
|
url.searchParams.set('filter', filter);
|
|
@@ -7128,8 +7152,7 @@
|
|
|
7128
7152
|
/**
|
|
7129
7153
|
* Returns a cached resource if it is available.
|
|
7130
7154
|
* @category Caching
|
|
7131
|
-
* @param
|
|
7132
|
-
* @param id The FHIR resource ID.
|
|
7155
|
+
* @param reference The FHIR reference.
|
|
7133
7156
|
* @returns The resource if it is available in the cache; undefined otherwise.
|
|
7134
7157
|
*/
|
|
7135
7158
|
getCachedReference(reference) {
|
|
@@ -7157,14 +7180,13 @@
|
|
|
7157
7180
|
* ```
|
|
7158
7181
|
*
|
|
7159
7182
|
* See the FHIR "read" operation for full details: https://www.hl7.org/fhir/http.html#read
|
|
7160
|
-
*
|
|
7161
7183
|
* @category Read
|
|
7162
7184
|
* @param resourceType The FHIR resource type.
|
|
7163
7185
|
* @param id The resource ID.
|
|
7164
7186
|
* @param options Optional fetch options.
|
|
7165
7187
|
* @returns The resource if available; undefined otherwise.
|
|
7166
7188
|
*/
|
|
7167
|
-
readResource(resourceType, id, options
|
|
7189
|
+
readResource(resourceType, id, options) {
|
|
7168
7190
|
return this.get(this.fhirUrl(resourceType, id), options);
|
|
7169
7191
|
}
|
|
7170
7192
|
/**
|
|
@@ -7181,13 +7203,12 @@
|
|
|
7181
7203
|
* ```
|
|
7182
7204
|
*
|
|
7183
7205
|
* See the FHIR "read" operation for full details: https://www.hl7.org/fhir/http.html#read
|
|
7184
|
-
*
|
|
7185
7206
|
* @category Read
|
|
7186
7207
|
* @param reference The FHIR reference object.
|
|
7187
7208
|
* @param options Optional fetch options.
|
|
7188
7209
|
* @returns The resource if available; undefined otherwise.
|
|
7189
7210
|
*/
|
|
7190
|
-
readReference(reference, options
|
|
7211
|
+
readReference(reference, options) {
|
|
7191
7212
|
const refString = reference?.reference;
|
|
7192
7213
|
if (!refString) {
|
|
7193
7214
|
return new ReadablePromise(Promise.reject(new Error('Missing reference')));
|
|
@@ -7283,14 +7304,13 @@
|
|
|
7283
7304
|
* ```
|
|
7284
7305
|
*
|
|
7285
7306
|
* See the FHIR "history" operation for full details: https://www.hl7.org/fhir/http.html#history
|
|
7286
|
-
*
|
|
7287
7307
|
* @category Read
|
|
7288
7308
|
* @param resourceType The FHIR resource type.
|
|
7289
7309
|
* @param id The resource ID.
|
|
7290
7310
|
* @param options Optional fetch options.
|
|
7291
7311
|
* @returns Promise to the resource history.
|
|
7292
7312
|
*/
|
|
7293
|
-
readHistory(resourceType, id, options
|
|
7313
|
+
readHistory(resourceType, id, options) {
|
|
7294
7314
|
return this.get(this.fhirUrl(resourceType, id, '_history'), options);
|
|
7295
7315
|
}
|
|
7296
7316
|
/**
|
|
@@ -7304,7 +7324,6 @@
|
|
|
7304
7324
|
* ```
|
|
7305
7325
|
*
|
|
7306
7326
|
* See the FHIR "vread" operation for full details: https://www.hl7.org/fhir/http.html#vread
|
|
7307
|
-
*
|
|
7308
7327
|
* @category Read
|
|
7309
7328
|
* @param resourceType The FHIR resource type.
|
|
7310
7329
|
* @param id The resource ID.
|
|
@@ -7312,7 +7331,7 @@
|
|
|
7312
7331
|
* @param options Optional fetch options.
|
|
7313
7332
|
* @returns The resource if available; undefined otherwise.
|
|
7314
7333
|
*/
|
|
7315
|
-
readVersion(resourceType, id, vid, options
|
|
7334
|
+
readVersion(resourceType, id, vid, options) {
|
|
7316
7335
|
return this.get(this.fhirUrl(resourceType, id, '_history', vid), options);
|
|
7317
7336
|
}
|
|
7318
7337
|
/**
|
|
@@ -7326,13 +7345,12 @@
|
|
|
7326
7345
|
* ```
|
|
7327
7346
|
*
|
|
7328
7347
|
* See the FHIR "patient-everything" operation for full details: https://hl7.org/fhir/operation-patient-everything.html
|
|
7329
|
-
*
|
|
7330
7348
|
* @category Read
|
|
7331
7349
|
* @param id The Patient Id
|
|
7332
7350
|
* @param options Optional fetch options.
|
|
7333
7351
|
* @returns A Bundle of all Resources related to the Patient
|
|
7334
7352
|
*/
|
|
7335
|
-
readPatientEverything(id, options
|
|
7353
|
+
readPatientEverything(id, options) {
|
|
7336
7354
|
return this.get(this.fhirUrl('Patient', id, '$everything'), options);
|
|
7337
7355
|
}
|
|
7338
7356
|
/**
|
|
@@ -7354,17 +7372,17 @@
|
|
|
7354
7372
|
* ```
|
|
7355
7373
|
*
|
|
7356
7374
|
* See the FHIR "create" operation for full details: https://www.hl7.org/fhir/http.html#create
|
|
7357
|
-
*
|
|
7358
7375
|
* @category Create
|
|
7359
7376
|
* @param resource The FHIR resource to create.
|
|
7377
|
+
* @param options Optional fetch options.
|
|
7360
7378
|
* @returns The result of the create operation.
|
|
7361
7379
|
*/
|
|
7362
|
-
createResource(resource) {
|
|
7380
|
+
createResource(resource, options) {
|
|
7363
7381
|
if (!resource.resourceType) {
|
|
7364
7382
|
throw new Error('Missing resourceType');
|
|
7365
7383
|
}
|
|
7366
7384
|
this.invalidateSearches(resource.resourceType);
|
|
7367
|
-
return this.post(this.fhirUrl(resource.resourceType), resource);
|
|
7385
|
+
return this.post(this.fhirUrl(resource.resourceType), resource, undefined, options);
|
|
7368
7386
|
}
|
|
7369
7387
|
/**
|
|
7370
7388
|
* Conditionally create a new FHIR resource only if some equivalent resource does not already exist on the server.
|
|
@@ -7400,14 +7418,15 @@
|
|
|
7400
7418
|
* The query parameter only contains the search parameters (what would be in the URL following the "?").
|
|
7401
7419
|
*
|
|
7402
7420
|
* See the FHIR "conditional create" operation for full details: https://www.hl7.org/fhir/http.html#ccreate
|
|
7403
|
-
*
|
|
7404
7421
|
* @category Create
|
|
7405
7422
|
* @param resource The FHIR resource to create.
|
|
7406
7423
|
* @param query The search query for an equivalent resource (should not include resource type or "?").
|
|
7424
|
+
* @param options Optional fetch options.
|
|
7407
7425
|
* @returns The result of the create operation.
|
|
7408
7426
|
*/
|
|
7409
|
-
async createResourceIfNoneExist(resource, query) {
|
|
7410
|
-
return ((await this.searchOne(resource.resourceType, query)) ??
|
|
7427
|
+
async createResourceIfNoneExist(resource, query, options) {
|
|
7428
|
+
return ((await this.searchOne(resource.resourceType, query, options)) ??
|
|
7429
|
+
this.createResource(resource, options));
|
|
7411
7430
|
}
|
|
7412
7431
|
/**
|
|
7413
7432
|
* Creates a FHIR `Binary` resource with the provided data content.
|
|
@@ -7426,11 +7445,11 @@
|
|
|
7426
7445
|
* ```
|
|
7427
7446
|
*
|
|
7428
7447
|
* See the FHIR "create" operation for full details: https://www.hl7.org/fhir/http.html#create
|
|
7429
|
-
*
|
|
7430
7448
|
* @category Create
|
|
7431
7449
|
* @param data The binary data to upload.
|
|
7432
7450
|
* @param filename Optional filename for the binary.
|
|
7433
7451
|
* @param contentType Content type for the binary.
|
|
7452
|
+
* @param onProgress Optional callback for progress events.
|
|
7434
7453
|
* @returns The result of the create operation.
|
|
7435
7454
|
*/
|
|
7436
7455
|
createBinary(data, filename, contentType, onProgress) {
|
|
@@ -7489,9 +7508,11 @@
|
|
|
7489
7508
|
* ```
|
|
7490
7509
|
*
|
|
7491
7510
|
* See the pdfmake document definition for full details: https://pdfmake.github.io/docs/0.1/document-definition-object/
|
|
7492
|
-
*
|
|
7493
7511
|
* @category Media
|
|
7494
7512
|
* @param docDefinition The PDF document definition.
|
|
7513
|
+
* @param filename Optional filename for the PDF binary resource.
|
|
7514
|
+
* @param tableLayouts Optional pdfmake custom table layout.
|
|
7515
|
+
* @param fonts Optional pdfmake custom font dictionary.
|
|
7495
7516
|
* @returns The result of the create operation.
|
|
7496
7517
|
*/
|
|
7497
7518
|
async createPdf(docDefinition, filename, tableLayouts, fonts) {
|
|
@@ -7505,13 +7526,13 @@
|
|
|
7505
7526
|
* Creates a FHIR `Communication` resource with the provided data content.
|
|
7506
7527
|
*
|
|
7507
7528
|
* This is a convenience method to handle commmon cases where a `Communication` resource is created with a `payload`.
|
|
7508
|
-
*
|
|
7509
7529
|
* @category Create
|
|
7510
7530
|
* @param resource The FHIR resource to comment on.
|
|
7511
7531
|
* @param text The text of the comment.
|
|
7532
|
+
* @param options Optional fetch options.
|
|
7512
7533
|
* @returns The result of the create operation.
|
|
7513
7534
|
*/
|
|
7514
|
-
createComment(resource, text) {
|
|
7535
|
+
createComment(resource, text, options) {
|
|
7515
7536
|
const profile = this.getProfile();
|
|
7516
7537
|
let encounter = undefined;
|
|
7517
7538
|
let subject = undefined;
|
|
@@ -7534,7 +7555,7 @@
|
|
|
7534
7555
|
sender: profile ? createReference(profile) : undefined,
|
|
7535
7556
|
sent: new Date().toISOString(),
|
|
7536
7557
|
payload: [{ contentString: text }],
|
|
7537
|
-
});
|
|
7558
|
+
}, options);
|
|
7538
7559
|
}
|
|
7539
7560
|
/**
|
|
7540
7561
|
* Updates a FHIR resource.
|
|
@@ -7556,12 +7577,12 @@
|
|
|
7556
7577
|
* ```
|
|
7557
7578
|
*
|
|
7558
7579
|
* See the FHIR "update" operation for full details: https://www.hl7.org/fhir/http.html#update
|
|
7559
|
-
*
|
|
7560
7580
|
* @category Write
|
|
7561
7581
|
* @param resource The FHIR resource to update.
|
|
7582
|
+
* @param options Optional fetch options.
|
|
7562
7583
|
* @returns The result of the update operation.
|
|
7563
7584
|
*/
|
|
7564
|
-
async updateResource(resource) {
|
|
7585
|
+
async updateResource(resource, options) {
|
|
7565
7586
|
if (!resource.resourceType) {
|
|
7566
7587
|
throw new Error('Missing resourceType');
|
|
7567
7588
|
}
|
|
@@ -7569,7 +7590,7 @@
|
|
|
7569
7590
|
throw new Error('Missing id');
|
|
7570
7591
|
}
|
|
7571
7592
|
this.invalidateSearches(resource.resourceType);
|
|
7572
|
-
let result = await this.put(this.fhirUrl(resource.resourceType, resource.id), resource);
|
|
7593
|
+
let result = await this.put(this.fhirUrl(resource.resourceType, resource.id), resource, undefined, options);
|
|
7573
7594
|
if (!result) {
|
|
7574
7595
|
// On 304 not modified, result will be undefined
|
|
7575
7596
|
// Return the user input instead
|
|
@@ -7596,16 +7617,16 @@
|
|
|
7596
7617
|
* See the FHIR "update" operation for full details: https://www.hl7.org/fhir/http.html#patch
|
|
7597
7618
|
*
|
|
7598
7619
|
* See the JSONPatch specification for full details: https://tools.ietf.org/html/rfc6902
|
|
7599
|
-
*
|
|
7600
7620
|
* @category Write
|
|
7601
7621
|
* @param resourceType The FHIR resource type.
|
|
7602
7622
|
* @param id The resource ID.
|
|
7603
7623
|
* @param operations The JSONPatch operations.
|
|
7624
|
+
* @param options Optional fetch options.
|
|
7604
7625
|
* @returns The result of the patch operations.
|
|
7605
7626
|
*/
|
|
7606
|
-
patchResource(resourceType, id, operations) {
|
|
7627
|
+
patchResource(resourceType, id, operations, options) {
|
|
7607
7628
|
this.invalidateSearches(resourceType);
|
|
7608
|
-
return this.patch(this.fhirUrl(resourceType, id), operations);
|
|
7629
|
+
return this.patch(this.fhirUrl(resourceType, id), operations, options);
|
|
7609
7630
|
}
|
|
7610
7631
|
/**
|
|
7611
7632
|
* Deletes a FHIR resource by resource type and ID.
|
|
@@ -7617,16 +7638,16 @@
|
|
|
7617
7638
|
* ```
|
|
7618
7639
|
*
|
|
7619
7640
|
* See the FHIR "delete" operation for full details: https://www.hl7.org/fhir/http.html#delete
|
|
7620
|
-
*
|
|
7621
7641
|
* @category Delete
|
|
7622
7642
|
* @param resourceType The FHIR resource type.
|
|
7623
7643
|
* @param id The resource ID.
|
|
7644
|
+
* @param options Optional fetch options.
|
|
7624
7645
|
* @returns The result of the delete operation.
|
|
7625
7646
|
*/
|
|
7626
|
-
deleteResource(resourceType, id) {
|
|
7647
|
+
deleteResource(resourceType, id, options) {
|
|
7627
7648
|
this.deleteCacheEntry(this.fhirUrl(resourceType, id).toString());
|
|
7628
7649
|
this.invalidateSearches(resourceType);
|
|
7629
|
-
return this.delete(this.fhirUrl(resourceType, id));
|
|
7650
|
+
return this.delete(this.fhirUrl(resourceType, id), options);
|
|
7630
7651
|
}
|
|
7631
7652
|
/**
|
|
7632
7653
|
* Executes the validate operation with the provided resource.
|
|
@@ -7641,12 +7662,12 @@
|
|
|
7641
7662
|
* ```
|
|
7642
7663
|
*
|
|
7643
7664
|
* See the FHIR "$validate" operation for full details: https://www.hl7.org/fhir/resource-operation-validate.html
|
|
7644
|
-
*
|
|
7645
7665
|
* @param resource The FHIR resource.
|
|
7666
|
+
* @param options Optional fetch options.
|
|
7646
7667
|
* @returns The validate operation outcome.
|
|
7647
7668
|
*/
|
|
7648
|
-
validateResource(resource) {
|
|
7649
|
-
return this.post(this.fhirUrl(resource.resourceType, '$validate'), resource);
|
|
7669
|
+
validateResource(resource, options) {
|
|
7670
|
+
return this.post(this.fhirUrl(resource.resourceType, '$validate'), resource, undefined, options);
|
|
7650
7671
|
}
|
|
7651
7672
|
/**
|
|
7652
7673
|
* Executes a bot by ID or Identifier.
|
|
@@ -7656,7 +7677,7 @@
|
|
|
7656
7677
|
* @param options Optional fetch options.
|
|
7657
7678
|
* @returns The Bot return value.
|
|
7658
7679
|
*/
|
|
7659
|
-
executeBot(idOrIdentifier, body, contentType, options
|
|
7680
|
+
executeBot(idOrIdentifier, body, contentType, options) {
|
|
7660
7681
|
let url;
|
|
7661
7682
|
if (typeof idOrIdentifier === 'string') {
|
|
7662
7683
|
const id = idOrIdentifier;
|
|
@@ -7716,7 +7737,7 @@
|
|
|
7716
7737
|
* @param options Optional fetch options.
|
|
7717
7738
|
* @returns The FHIR batch/transaction response bundle.
|
|
7718
7739
|
*/
|
|
7719
|
-
executeBatch(bundle, options
|
|
7740
|
+
executeBatch(bundle, options) {
|
|
7720
7741
|
return this.post(this.fhirBaseUrl.slice(0, -1), bundle, undefined, options);
|
|
7721
7742
|
}
|
|
7722
7743
|
/**
|
|
@@ -7753,11 +7774,12 @@
|
|
|
7753
7774
|
*
|
|
7754
7775
|
* See options here: https://nodemailer.com/extras/mailcomposer/
|
|
7755
7776
|
* @category Media
|
|
7756
|
-
* @param
|
|
7777
|
+
* @param email The MailComposer options.
|
|
7778
|
+
* @param options Optional fetch options.
|
|
7757
7779
|
* @returns Promise to the operation outcome.
|
|
7758
7780
|
*/
|
|
7759
|
-
sendEmail(email) {
|
|
7760
|
-
return this.post('email/v1/send', email, 'application/json');
|
|
7781
|
+
sendEmail(email, options) {
|
|
7782
|
+
return this.post('email/v1/send', email, 'application/json', options);
|
|
7761
7783
|
}
|
|
7762
7784
|
/**
|
|
7763
7785
|
* Executes a GraphQL query.
|
|
@@ -7799,7 +7821,6 @@
|
|
|
7799
7821
|
* See the GraphQL documentation for more details: https://graphql.org/learn/
|
|
7800
7822
|
*
|
|
7801
7823
|
* See the FHIR GraphQL documentation for FHIR specific details: https://www.hl7.org/fhir/graphql.html
|
|
7802
|
-
*
|
|
7803
7824
|
* @category Read
|
|
7804
7825
|
* @param query The GraphQL query.
|
|
7805
7826
|
* @param operationName Optional GraphQL operation name.
|
|
@@ -7814,15 +7835,15 @@
|
|
|
7814
7835
|
*
|
|
7815
7836
|
* Executes the $graph operation on this resource to fetch a Bundle of resources linked to the target resource
|
|
7816
7837
|
* according to a graph definition
|
|
7817
|
-
|
|
7818
7838
|
* @category Read
|
|
7819
7839
|
* @param resourceType The FHIR resource type.
|
|
7820
7840
|
* @param id The resource ID.
|
|
7821
7841
|
* @param graphName `name` parameter of the GraphDefinition
|
|
7842
|
+
* @param options Optional fetch options.
|
|
7822
7843
|
* @returns A Bundle
|
|
7823
7844
|
*/
|
|
7824
|
-
readResourceGraph(resourceType, id, graphName) {
|
|
7825
|
-
return this.get(`${this.fhirUrl(resourceType, id)}/$graph?graph=${graphName}
|
|
7845
|
+
readResourceGraph(resourceType, id, graphName, options) {
|
|
7846
|
+
return this.get(`${this.fhirUrl(resourceType, id)}/$graph?graph=${graphName}`, options);
|
|
7826
7847
|
}
|
|
7827
7848
|
/**
|
|
7828
7849
|
* @category Authentication
|
|
@@ -7832,11 +7853,16 @@
|
|
|
7832
7853
|
return this.storage.getObject('activeLogin');
|
|
7833
7854
|
}
|
|
7834
7855
|
/**
|
|
7856
|
+
* Sets the active login.
|
|
7857
|
+
* @param login The new active login state.
|
|
7835
7858
|
* @category Authentication
|
|
7836
7859
|
*/
|
|
7837
7860
|
async setActiveLogin(login) {
|
|
7838
7861
|
this.clearActiveLogin();
|
|
7839
7862
|
this.accessToken = login.accessToken;
|
|
7863
|
+
if (this.basicAuth) {
|
|
7864
|
+
return;
|
|
7865
|
+
}
|
|
7840
7866
|
this.refreshToken = login.refreshToken;
|
|
7841
7867
|
this.storage.setObject('activeLogin', login);
|
|
7842
7868
|
this.addLogin(login);
|
|
@@ -7845,6 +7871,7 @@
|
|
|
7845
7871
|
}
|
|
7846
7872
|
/**
|
|
7847
7873
|
* Returns the current access token.
|
|
7874
|
+
* @returns The current access token.
|
|
7848
7875
|
* @category Authentication
|
|
7849
7876
|
*/
|
|
7850
7877
|
getAccessToken() {
|
|
@@ -7852,15 +7879,17 @@
|
|
|
7852
7879
|
}
|
|
7853
7880
|
/**
|
|
7854
7881
|
* Sets the current access token.
|
|
7882
|
+
* @param accessToken The new access token.
|
|
7855
7883
|
* @category Authentication
|
|
7856
7884
|
*/
|
|
7857
7885
|
setAccessToken(accessToken) {
|
|
7858
7886
|
this.accessToken = accessToken;
|
|
7859
7887
|
this.refreshToken = undefined;
|
|
7860
|
-
this.
|
|
7861
|
-
this.config = undefined;
|
|
7888
|
+
this.sessionDetails = undefined;
|
|
7862
7889
|
}
|
|
7863
7890
|
/**
|
|
7891
|
+
* Returns the list of available logins.
|
|
7892
|
+
* @returns The list of available logins.
|
|
7864
7893
|
* @category Authentication
|
|
7865
7894
|
*/
|
|
7866
7895
|
getLogins() {
|
|
@@ -7873,31 +7902,73 @@
|
|
|
7873
7902
|
}
|
|
7874
7903
|
async refreshProfile() {
|
|
7875
7904
|
this.profilePromise = new Promise((resolve, reject) => {
|
|
7905
|
+
if (this.basicAuth) {
|
|
7906
|
+
return;
|
|
7907
|
+
}
|
|
7876
7908
|
this.get('auth/me')
|
|
7877
7909
|
.then((result) => {
|
|
7878
7910
|
this.profilePromise = undefined;
|
|
7879
|
-
this.
|
|
7880
|
-
this.config = result.config;
|
|
7911
|
+
this.sessionDetails = result;
|
|
7881
7912
|
this.dispatchEvent({ type: 'change' });
|
|
7882
|
-
resolve(
|
|
7913
|
+
resolve(result.profile);
|
|
7883
7914
|
})
|
|
7884
7915
|
.catch(reject);
|
|
7885
7916
|
});
|
|
7886
7917
|
return this.profilePromise;
|
|
7887
7918
|
}
|
|
7888
7919
|
/**
|
|
7920
|
+
* Returns true if the client is waiting for authentication.
|
|
7921
|
+
* @returns True if the client is waiting for authentication.
|
|
7889
7922
|
* @category Authentication
|
|
7890
7923
|
*/
|
|
7891
7924
|
isLoading() {
|
|
7892
7925
|
return !!this.profilePromise;
|
|
7893
7926
|
}
|
|
7894
7927
|
/**
|
|
7928
|
+
* Returns true if the current user is authenticated as a super admin.
|
|
7929
|
+
* @returns True if the current user is authenticated as a super admin.
|
|
7930
|
+
* @category Authentication
|
|
7931
|
+
*/
|
|
7932
|
+
isSuperAdmin() {
|
|
7933
|
+
return !!this.sessionDetails?.project?.superAdmin;
|
|
7934
|
+
}
|
|
7935
|
+
/**
|
|
7936
|
+
* Returns true if the current user is authenticated as a project admin.
|
|
7937
|
+
* @returns True if the current user is authenticated as a project admin.
|
|
7938
|
+
* @category Authentication
|
|
7939
|
+
*/
|
|
7940
|
+
isProjectAdmin() {
|
|
7941
|
+
return !!this.sessionDetails?.membership?.admin;
|
|
7942
|
+
}
|
|
7943
|
+
/**
|
|
7944
|
+
* Returns the current project if available.
|
|
7945
|
+
* @returns The current project if available.
|
|
7946
|
+
* @category User Profile
|
|
7947
|
+
*/
|
|
7948
|
+
getProject() {
|
|
7949
|
+
return this.sessionDetails?.project;
|
|
7950
|
+
}
|
|
7951
|
+
/**
|
|
7952
|
+
* Returns the current project membership if available.
|
|
7953
|
+
* @returns The current project membership if available.
|
|
7954
|
+
* @category User Profile
|
|
7955
|
+
*/
|
|
7956
|
+
getProjectMembership() {
|
|
7957
|
+
return this.sessionDetails?.membership;
|
|
7958
|
+
}
|
|
7959
|
+
/**
|
|
7960
|
+
* Returns the current user profile resource if available.
|
|
7961
|
+
* This method does not wait for loading promises.
|
|
7962
|
+
* @returns The current user profile resource if available.
|
|
7895
7963
|
* @category User Profile
|
|
7896
7964
|
*/
|
|
7897
7965
|
getProfile() {
|
|
7898
|
-
return this.profile;
|
|
7966
|
+
return this.sessionDetails?.profile;
|
|
7899
7967
|
}
|
|
7900
7968
|
/**
|
|
7969
|
+
* Returns the current user profile resource if available.
|
|
7970
|
+
* This method waits for loading promises.
|
|
7971
|
+
* @returns The current user profile resource if available.
|
|
7901
7972
|
* @category User Profile
|
|
7902
7973
|
*/
|
|
7903
7974
|
async getProfileAsync() {
|
|
@@ -7907,16 +7978,26 @@
|
|
|
7907
7978
|
return this.getProfile();
|
|
7908
7979
|
}
|
|
7909
7980
|
/**
|
|
7981
|
+
* Returns the current user configuration if available.
|
|
7982
|
+
* @returns The current user configuration if available.
|
|
7910
7983
|
* @category User Profile
|
|
7911
7984
|
*/
|
|
7912
7985
|
getUserConfiguration() {
|
|
7913
|
-
return this.config;
|
|
7986
|
+
return this.sessionDetails?.config;
|
|
7987
|
+
}
|
|
7988
|
+
/**
|
|
7989
|
+
* Returns the current user access policy if available.
|
|
7990
|
+
* @returns The current user access policy if available.
|
|
7991
|
+
* @category User Profile
|
|
7992
|
+
*/
|
|
7993
|
+
getAccessPolicy() {
|
|
7994
|
+
return this.sessionDetails?.accessPolicy;
|
|
7914
7995
|
}
|
|
7915
7996
|
/**
|
|
7916
7997
|
* Downloads the URL as a blob.
|
|
7917
|
-
*
|
|
7918
7998
|
* @category Read
|
|
7919
7999
|
* @param url The URL to request.
|
|
8000
|
+
* @param options Optional fetch request init options.
|
|
7920
8001
|
* @returns Promise to the response body as a blob.
|
|
7921
8002
|
*/
|
|
7922
8003
|
async download(url, options = {}) {
|
|
@@ -7930,12 +8011,13 @@
|
|
|
7930
8011
|
/**
|
|
7931
8012
|
* Upload media to the server and create a Media instance for the uploaded content.
|
|
7932
8013
|
* @param contents The contents of the media file, as a string, Uint8Array, File, or Blob.
|
|
7933
|
-
* @param contentType The media type of the content
|
|
7934
|
-
* @param filename The name of the file to be uploaded, or undefined if not applicable
|
|
7935
|
-
* @param additionalFields
|
|
8014
|
+
* @param contentType The media type of the content.
|
|
8015
|
+
* @param filename The name of the file to be uploaded, or undefined if not applicable.
|
|
8016
|
+
* @param additionalFields Additional fields for Media.
|
|
8017
|
+
* @param options Optional fetch options.
|
|
7936
8018
|
* @returns Promise that resolves to the created Media
|
|
7937
8019
|
*/
|
|
7938
|
-
async uploadMedia(contents, contentType, filename, additionalFields) {
|
|
8020
|
+
async uploadMedia(contents, contentType, filename, additionalFields, options) {
|
|
7939
8021
|
const binary = await this.createBinary(contents, filename, contentType);
|
|
7940
8022
|
return this.createResource({
|
|
7941
8023
|
...additionalFields,
|
|
@@ -7945,11 +8027,10 @@
|
|
|
7945
8027
|
url: 'Binary/' + binary.id,
|
|
7946
8028
|
title: filename,
|
|
7947
8029
|
},
|
|
7948
|
-
});
|
|
8030
|
+
}, options);
|
|
7949
8031
|
}
|
|
7950
8032
|
/**
|
|
7951
8033
|
* Performs Bulk Data Export operation request flow. See The FHIR "Bulk Data Export" for full details: https://build.fhir.org/ig/HL7/bulk-data/export.html#bulk-data-export
|
|
7952
|
-
*
|
|
7953
8034
|
* @param exportLevel Optional export level. Defaults to system level export. 'Group/:id' - Group of Patients, 'Patient' - All Patients.
|
|
7954
8035
|
* @param resourceTypes A string of comma-delimited FHIR resource types.
|
|
7955
8036
|
* @param since Resources will be included in the response if their state has changed after the supplied time (e.g. if Resource.meta.lastUpdated is later than the supplied _since time).
|
|
@@ -7965,7 +8046,6 @@
|
|
|
7965
8046
|
if (since) {
|
|
7966
8047
|
url.searchParams.set('_since', since);
|
|
7967
8048
|
}
|
|
7968
|
-
options.method = exportLevel ? 'GET' : 'POST';
|
|
7969
8049
|
this.addFetchOptionsDefaults(options);
|
|
7970
8050
|
const headers = options.headers;
|
|
7971
8051
|
headers['Prefer'] = 'respond-async';
|
|
@@ -8029,10 +8109,10 @@
|
|
|
8029
8109
|
}
|
|
8030
8110
|
/**
|
|
8031
8111
|
* Makes an HTTP request.
|
|
8032
|
-
* @param
|
|
8033
|
-
* @param
|
|
8034
|
-
* @param
|
|
8035
|
-
* @
|
|
8112
|
+
* @param method The HTTP method (GET, POST, etc).
|
|
8113
|
+
* @param url The target URL.
|
|
8114
|
+
* @param options Optional fetch request init options.
|
|
8115
|
+
* @returns The JSON content body if available.
|
|
8036
8116
|
*/
|
|
8037
8117
|
async request(method, url, options = {}) {
|
|
8038
8118
|
if (this.refreshPromise) {
|
|
@@ -8097,9 +8177,7 @@
|
|
|
8097
8177
|
let resultResponse;
|
|
8098
8178
|
const retryDelay = 200;
|
|
8099
8179
|
while (checkStatus) {
|
|
8100
|
-
const fetchOptions = {
|
|
8101
|
-
method: 'GET',
|
|
8102
|
-
};
|
|
8180
|
+
const fetchOptions = {};
|
|
8103
8181
|
this.addFetchOptionsDefaults(fetchOptions);
|
|
8104
8182
|
const statusResponse = await this.fetchWithRetry(statusUrl, fetchOptions);
|
|
8105
8183
|
if (statusResponse.status !== 202) {
|
|
@@ -8175,7 +8253,7 @@
|
|
|
8175
8253
|
if (this.accessToken) {
|
|
8176
8254
|
headers['Authorization'] = 'Bearer ' + this.accessToken;
|
|
8177
8255
|
}
|
|
8178
|
-
if (this.basicAuth) {
|
|
8256
|
+
else if (this.basicAuth) {
|
|
8179
8257
|
headers['Authorization'] = 'Basic ' + this.basicAuth;
|
|
8180
8258
|
}
|
|
8181
8259
|
if (!options.cache) {
|
|
@@ -8219,8 +8297,8 @@
|
|
|
8219
8297
|
* Otherwise, calls unauthenticated callbacks and rejects.
|
|
8220
8298
|
* @param method The HTTP method of the original request.
|
|
8221
8299
|
* @param url The URL of the original request.
|
|
8222
|
-
* @param
|
|
8223
|
-
* @
|
|
8300
|
+
* @param options Optional fetch request init options.
|
|
8301
|
+
* @returns The result of the retry.
|
|
8224
8302
|
*/
|
|
8225
8303
|
handleUnauthenticated(method, url, options) {
|
|
8226
8304
|
if (this.refresh()) {
|
|
@@ -8236,6 +8314,7 @@
|
|
|
8236
8314
|
* Starts a new PKCE flow.
|
|
8237
8315
|
* These PKCE values are stateful, and must survive redirects and page refreshes.
|
|
8238
8316
|
* @category Authentication
|
|
8317
|
+
* @returns The PKCE code challenge details.
|
|
8239
8318
|
*/
|
|
8240
8319
|
async startPkce() {
|
|
8241
8320
|
const pkceState = getRandomString();
|
|
@@ -8250,7 +8329,8 @@
|
|
|
8250
8329
|
/**
|
|
8251
8330
|
* Redirects the user to the login screen for authorization.
|
|
8252
8331
|
* Clears all auth state including local storage and session storage.
|
|
8253
|
-
*
|
|
8332
|
+
* @param loginParams The authorization login parameters.
|
|
8333
|
+
* @see https://openid.net/specs/openid-connect-core-1_0.html#AuthorizationEndpoint
|
|
8254
8334
|
*/
|
|
8255
8335
|
async requestAuthorization(loginParams) {
|
|
8256
8336
|
const loginRequest = await this.ensureCodeChallenge(loginParams || {});
|
|
@@ -8269,6 +8349,7 @@
|
|
|
8269
8349
|
* See: https://openid.net/specs/openid-connect-core-1_0.html#TokenRequest
|
|
8270
8350
|
* @param code The authorization code received by URL parameter.
|
|
8271
8351
|
* @param loginParams Optional login parameters.
|
|
8352
|
+
* @returns The user profile resource.
|
|
8272
8353
|
* @category Authentication
|
|
8273
8354
|
*/
|
|
8274
8355
|
processCode(code, loginParams) {
|
|
@@ -8287,7 +8368,8 @@
|
|
|
8287
8368
|
}
|
|
8288
8369
|
/**
|
|
8289
8370
|
* Tries to refresh the auth tokens.
|
|
8290
|
-
*
|
|
8371
|
+
* @returns The refresh promise if available; otherwise undefined.
|
|
8372
|
+
* @see https://openid.net/specs/openid-connect-core-1_0.html#RefreshTokens
|
|
8291
8373
|
*/
|
|
8292
8374
|
refresh() {
|
|
8293
8375
|
if (this.refreshPromise) {
|
|
@@ -8340,7 +8422,6 @@
|
|
|
8340
8422
|
* // Example Search
|
|
8341
8423
|
* await medplum.searchResources('Patient')
|
|
8342
8424
|
* ```
|
|
8343
|
-
*
|
|
8344
8425
|
* @category Authentication
|
|
8345
8426
|
* @param clientId The client ID.
|
|
8346
8427
|
* @param clientSecret The client secret.
|
|
@@ -8354,7 +8435,7 @@
|
|
|
8354
8435
|
* Invite a user to a project.
|
|
8355
8436
|
* @param projectId The project ID.
|
|
8356
8437
|
* @param body The InviteBody.
|
|
8357
|
-
* @returns Promise that returns
|
|
8438
|
+
* @returns Promise that returns a project membership or an operation outcome.
|
|
8358
8439
|
*/
|
|
8359
8440
|
async invite(projectId, body) {
|
|
8360
8441
|
return this.post('admin/projects/' + projectId + '/invite', body);
|
|
@@ -8363,17 +8444,29 @@
|
|
|
8363
8444
|
* Makes a POST request to the tokens endpoint.
|
|
8364
8445
|
* See: https://openid.net/specs/openid-connect-core-1_0.html#TokenEndpoint
|
|
8365
8446
|
* @param formBody Token parameters in URL encoded format.
|
|
8447
|
+
* @returns The user profile resource.
|
|
8366
8448
|
*/
|
|
8367
8449
|
async fetchTokens(formBody) {
|
|
8368
|
-
const
|
|
8450
|
+
const options = {
|
|
8369
8451
|
method: 'POST',
|
|
8370
8452
|
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
|
|
8371
8453
|
body: formBody,
|
|
8372
8454
|
credentials: 'include',
|
|
8373
|
-
}
|
|
8455
|
+
};
|
|
8456
|
+
const headers = options.headers;
|
|
8457
|
+
if (this.basicAuth) {
|
|
8458
|
+
headers['Authorization'] = `Basic ${this.basicAuth}`;
|
|
8459
|
+
}
|
|
8460
|
+
const response = await this.fetch(this.tokenUrl, options);
|
|
8374
8461
|
if (!response.ok) {
|
|
8375
8462
|
this.clearActiveLogin();
|
|
8376
|
-
|
|
8463
|
+
try {
|
|
8464
|
+
const error = await response.json();
|
|
8465
|
+
throw new OperationOutcomeError(badRequest(error.error_description));
|
|
8466
|
+
}
|
|
8467
|
+
catch (err) {
|
|
8468
|
+
throw new OperationOutcomeError(badRequest('Failed to fetch tokens'), err);
|
|
8469
|
+
}
|
|
8377
8470
|
}
|
|
8378
8471
|
const tokens = await response.json();
|
|
8379
8472
|
await this.verifyTokens(tokens);
|
|
@@ -8383,7 +8476,8 @@
|
|
|
8383
8476
|
* Verifies the tokens received from the auth server.
|
|
8384
8477
|
* Validates the JWT against the JWKS.
|
|
8385
8478
|
* See: https://openid.net/specs/openid-connect-core-1_0.html#TokenEndpoint
|
|
8386
|
-
* @param tokens
|
|
8479
|
+
* @param tokens The token response.
|
|
8480
|
+
* @returns Promise to complete.
|
|
8387
8481
|
*/
|
|
8388
8482
|
async verifyTokens(tokens) {
|
|
8389
8483
|
const token = tokens.access_token;
|
|
@@ -8394,7 +8488,14 @@
|
|
|
8394
8488
|
throw new Error('Token expired');
|
|
8395
8489
|
}
|
|
8396
8490
|
// Verify app_client_id
|
|
8397
|
-
|
|
8491
|
+
// external tokenPayload
|
|
8492
|
+
if (tokenPayload.cid) {
|
|
8493
|
+
if (tokenPayload.cid !== this.clientId) {
|
|
8494
|
+
this.clearActiveLogin();
|
|
8495
|
+
throw new Error('Token was not issued for this audience');
|
|
8496
|
+
}
|
|
8497
|
+
}
|
|
8498
|
+
else if (this.clientId && tokenPayload.client_id !== this.clientId) {
|
|
8398
8499
|
this.clearActiveLogin();
|
|
8399
8500
|
throw new Error('Token was not issued for this audience');
|
|
8400
8501
|
}
|
|
@@ -8448,6 +8549,7 @@
|
|
|
8448
8549
|
}
|
|
8449
8550
|
/**
|
|
8450
8551
|
* Returns the base URL for the current page.
|
|
8552
|
+
* @returns The window origin string.
|
|
8451
8553
|
* @category HTTP
|
|
8452
8554
|
*/
|
|
8453
8555
|
function getWindowOrigin() {
|
|
@@ -8610,7 +8712,7 @@
|
|
|
8610
8712
|
this.keywords = keywords;
|
|
8611
8713
|
this.operators = operators;
|
|
8612
8714
|
this.dateTimeLiterals = !!options?.dateTimeLiterals;
|
|
8613
|
-
this.symbolRegex = options?.symbolRegex ?? /[$\w]/;
|
|
8715
|
+
this.symbolRegex = options?.symbolRegex ?? /[$\w%]/;
|
|
8614
8716
|
}
|
|
8615
8717
|
tokenize() {
|
|
8616
8718
|
while (this.pos.index < this.str.length) {
|
|
@@ -8659,7 +8761,7 @@
|
|
|
8659
8761
|
if (c.match(/\w/)) {
|
|
8660
8762
|
return this.consumeSymbol();
|
|
8661
8763
|
}
|
|
8662
|
-
if (c === '$' && next.match(/\w/)) {
|
|
8764
|
+
if ((c === '$' || c === '%') && next.match(/\w/)) {
|
|
8663
8765
|
return this.consumeSymbol();
|
|
8664
8766
|
}
|
|
8665
8767
|
return this.consumeOperator();
|
|
@@ -9209,6 +9311,7 @@
|
|
|
9209
9311
|
|
|
9210
9312
|
/**
|
|
9211
9313
|
* Temporary placholder for unimplemented methods.
|
|
9314
|
+
* @returns Empty array.
|
|
9212
9315
|
*/
|
|
9213
9316
|
const stub = () => [];
|
|
9214
9317
|
const functions = {
|
|
@@ -9220,11 +9323,11 @@
|
|
|
9220
9323
|
* Returns true if the input collection is empty ({ }) and false otherwise.
|
|
9221
9324
|
*
|
|
9222
9325
|
* See: https://hl7.org/fhirpath/#empty-boolean
|
|
9223
|
-
*
|
|
9326
|
+
* @param _context The evaluation context.
|
|
9224
9327
|
* @param input The input collection.
|
|
9225
9328
|
* @returns True if the input collection is empty ({ }) and false otherwise.
|
|
9226
9329
|
*/
|
|
9227
|
-
empty: (input) => {
|
|
9330
|
+
empty: (_context, input) => {
|
|
9228
9331
|
return booleanToTypedValue(input.length === 0);
|
|
9229
9332
|
},
|
|
9230
9333
|
/**
|
|
@@ -9237,14 +9340,14 @@
|
|
|
9237
9340
|
* for where(criteria).exists().
|
|
9238
9341
|
*
|
|
9239
9342
|
* See: https://hl7.org/fhirpath/#existscriteria-expression-boolean
|
|
9240
|
-
*
|
|
9241
|
-
* @param input
|
|
9242
|
-
* @param criteria
|
|
9343
|
+
* @param context The evaluation context.
|
|
9344
|
+
* @param input The input collection.
|
|
9345
|
+
* @param criteria The evaluation criteria.
|
|
9243
9346
|
* @returns True if the collection has unknown elements, and false otherwise.
|
|
9244
9347
|
*/
|
|
9245
|
-
exists: (input, criteria) => {
|
|
9348
|
+
exists: (context, input, criteria) => {
|
|
9246
9349
|
if (criteria) {
|
|
9247
|
-
return booleanToTypedValue(input.filter((e) => toJsBoolean(criteria.eval([e]))).length > 0);
|
|
9350
|
+
return booleanToTypedValue(input.filter((e) => toJsBoolean(criteria.eval(context, [e]))).length > 0);
|
|
9248
9351
|
}
|
|
9249
9352
|
else {
|
|
9250
9353
|
return booleanToTypedValue(input.length > 0);
|
|
@@ -9257,13 +9360,13 @@
|
|
|
9257
9360
|
* If the input collection is empty ({ }), the result is true.
|
|
9258
9361
|
*
|
|
9259
9362
|
* See: https://hl7.org/fhirpath/#allcriteria-expression-boolean
|
|
9260
|
-
*
|
|
9363
|
+
* @param context The evaluation context.
|
|
9261
9364
|
* @param input The input collection.
|
|
9262
9365
|
* @param criteria The evaluation criteria.
|
|
9263
9366
|
* @returns True if for every element in the input collection, criteria evaluates to true.
|
|
9264
9367
|
*/
|
|
9265
|
-
all: (input, criteria) => {
|
|
9266
|
-
return booleanToTypedValue(input.every((e) => toJsBoolean(criteria.eval([e]))));
|
|
9368
|
+
all: (context, input, criteria) => {
|
|
9369
|
+
return booleanToTypedValue(input.every((e) => toJsBoolean(criteria.eval(context, [e]))));
|
|
9267
9370
|
},
|
|
9268
9371
|
/**
|
|
9269
9372
|
* Takes a collection of Boolean values and returns true if all the items are true.
|
|
@@ -9271,12 +9374,11 @@
|
|
|
9271
9374
|
* If the input is empty ({ }), the result is true.
|
|
9272
9375
|
*
|
|
9273
9376
|
* See: https://hl7.org/fhirpath/#alltrue-boolean
|
|
9274
|
-
*
|
|
9377
|
+
* @param _context The evaluation context.
|
|
9275
9378
|
* @param input The input collection.
|
|
9276
|
-
* @param criteria The evaluation criteria.
|
|
9277
9379
|
* @returns True if all the items are true.
|
|
9278
9380
|
*/
|
|
9279
|
-
allTrue: (input) => {
|
|
9381
|
+
allTrue: (_context, input) => {
|
|
9280
9382
|
for (const value of input) {
|
|
9281
9383
|
if (!value.value) {
|
|
9282
9384
|
return booleanToTypedValue(false);
|
|
@@ -9289,12 +9391,11 @@
|
|
|
9289
9391
|
* If all the items are false, or if the input is empty ({ }), the result is false.
|
|
9290
9392
|
*
|
|
9291
9393
|
* See: https://hl7.org/fhirpath/#anytrue-boolean
|
|
9292
|
-
*
|
|
9394
|
+
* @param _context The evaluation context.
|
|
9293
9395
|
* @param input The input collection.
|
|
9294
|
-
* @param criteria The evaluation criteria.
|
|
9295
9396
|
* @returns True if unknown of the items are true.
|
|
9296
9397
|
*/
|
|
9297
|
-
anyTrue: (input) => {
|
|
9398
|
+
anyTrue: (_context, input) => {
|
|
9298
9399
|
for (const value of input) {
|
|
9299
9400
|
if (value.value) {
|
|
9300
9401
|
return booleanToTypedValue(true);
|
|
@@ -9308,12 +9409,11 @@
|
|
|
9308
9409
|
* If the input is empty ({ }), the result is true.
|
|
9309
9410
|
*
|
|
9310
9411
|
* See: https://hl7.org/fhirpath/#allfalse-boolean
|
|
9311
|
-
*
|
|
9412
|
+
* @param _context The evaluation context.
|
|
9312
9413
|
* @param input The input collection.
|
|
9313
|
-
* @param criteria The evaluation criteria.
|
|
9314
9414
|
* @returns True if all the items are false.
|
|
9315
9415
|
*/
|
|
9316
|
-
allFalse: (input) => {
|
|
9416
|
+
allFalse: (_context, input) => {
|
|
9317
9417
|
for (const value of input) {
|
|
9318
9418
|
if (value.value) {
|
|
9319
9419
|
return booleanToTypedValue(false);
|
|
@@ -9326,12 +9426,11 @@
|
|
|
9326
9426
|
* If all the items are true, or if the input is empty ({ }), the result is false.
|
|
9327
9427
|
*
|
|
9328
9428
|
* See: https://hl7.org/fhirpath/#anyfalse-boolean
|
|
9329
|
-
*
|
|
9429
|
+
* @param _context The evaluation context.
|
|
9330
9430
|
* @param input The input collection.
|
|
9331
|
-
* @param criteria The evaluation criteria.
|
|
9332
9431
|
* @returns True if for every element in the input collection, criteria evaluates to true.
|
|
9333
9432
|
*/
|
|
9334
|
-
anyFalse: (input) => {
|
|
9433
|
+
anyFalse: (_context, input) => {
|
|
9335
9434
|
for (const value of input) {
|
|
9336
9435
|
if (!value.value) {
|
|
9337
9436
|
return booleanToTypedValue(true);
|
|
@@ -9368,11 +9467,11 @@
|
|
|
9368
9467
|
* Returns 0 when the input collection is empty.
|
|
9369
9468
|
*
|
|
9370
9469
|
* See: https://hl7.org/fhirpath/#count-integer
|
|
9371
|
-
*
|
|
9470
|
+
* @param _context The evaluation context.
|
|
9372
9471
|
* @param input The input collection.
|
|
9373
9472
|
* @returns The integer count of the number of items in the input collection.
|
|
9374
9473
|
*/
|
|
9375
|
-
count: (input) => {
|
|
9474
|
+
count: (_context, input) => {
|
|
9376
9475
|
return [{ type: exports.PropertyType.integer, value: input.length }];
|
|
9377
9476
|
},
|
|
9378
9477
|
/**
|
|
@@ -9386,11 +9485,11 @@
|
|
|
9386
9485
|
* preserved in the result.
|
|
9387
9486
|
*
|
|
9388
9487
|
* See: https://hl7.org/fhirpath/#distinct-collection
|
|
9389
|
-
*
|
|
9488
|
+
* @param _context The evaluation context.
|
|
9390
9489
|
* @param input The input collection.
|
|
9391
9490
|
* @returns The integer count of the number of items in the input collection.
|
|
9392
9491
|
*/
|
|
9393
|
-
distinct: (input) => {
|
|
9492
|
+
distinct: (_context, input) => {
|
|
9394
9493
|
const result = [];
|
|
9395
9494
|
for (const value of input) {
|
|
9396
9495
|
if (!result.some((e) => e.value === value.value)) {
|
|
@@ -9405,12 +9504,12 @@
|
|
|
9405
9504
|
* as defined below.
|
|
9406
9505
|
*
|
|
9407
9506
|
* See: https://hl7.org/fhirpath/#isdistinct-boolean
|
|
9408
|
-
*
|
|
9507
|
+
* @param context The evaluation context.
|
|
9409
9508
|
* @param input The input collection.
|
|
9410
9509
|
* @returns The integer count of the number of items in the input collection.
|
|
9411
9510
|
*/
|
|
9412
|
-
isDistinct: (input) => {
|
|
9413
|
-
return booleanToTypedValue(input.length === functions.distinct(input).length);
|
|
9511
|
+
isDistinct: (context, input) => {
|
|
9512
|
+
return booleanToTypedValue(input.length === functions.distinct(context, input).length);
|
|
9414
9513
|
},
|
|
9415
9514
|
/*
|
|
9416
9515
|
* 5.2 Filtering and projection
|
|
@@ -9428,13 +9527,13 @@
|
|
|
9428
9527
|
* consistent with singleton evaluation of collections behavior.
|
|
9429
9528
|
*
|
|
9430
9529
|
* See: https://hl7.org/fhirpath/#wherecriteria-expression-collection
|
|
9431
|
-
*
|
|
9530
|
+
* @param context The evaluation context.
|
|
9432
9531
|
* @param input The input collection.
|
|
9433
|
-
* @param
|
|
9532
|
+
* @param criteria The condition atom.
|
|
9434
9533
|
* @returns A collection containing only those elements in the input collection for which the stated criteria expression evaluates to true.
|
|
9435
9534
|
*/
|
|
9436
|
-
where: (input, criteria) => {
|
|
9437
|
-
return input.filter((e) => toJsBoolean(criteria.eval([e])));
|
|
9535
|
+
where: (context, input, criteria) => {
|
|
9536
|
+
return input.filter((e) => toJsBoolean(criteria.eval(context, [e])));
|
|
9438
9537
|
},
|
|
9439
9538
|
/**
|
|
9440
9539
|
* Evaluates the projection expression for each item in the input collection.
|
|
@@ -9446,9 +9545,13 @@
|
|
|
9446
9545
|
* the input collection is empty ({ }), the result is empty as well.
|
|
9447
9546
|
*
|
|
9448
9547
|
* See: http://hl7.org/fhirpath/#selectprojection-expression-collection
|
|
9548
|
+
* @param context The evaluation context.
|
|
9549
|
+
* @param input The input collection.
|
|
9550
|
+
* @param criteria The condition atom.
|
|
9551
|
+
* @returns A collection containing only those elements in the input collection for which the stated criteria expression evaluates to true.
|
|
9449
9552
|
*/
|
|
9450
|
-
select: (input, criteria) => {
|
|
9451
|
-
return input.map((e) => criteria.eval([e])).flat();
|
|
9553
|
+
select: (context, input, criteria) => {
|
|
9554
|
+
return input.map((e) => criteria.eval(context, [e])).flat();
|
|
9452
9555
|
},
|
|
9453
9556
|
/**
|
|
9454
9557
|
* A version of select that will repeat the projection and add it to the output
|
|
@@ -9465,8 +9568,12 @@
|
|
|
9465
9568
|
* must resolve to the name of a type in a model
|
|
9466
9569
|
*
|
|
9467
9570
|
* See: http://hl7.org/fhirpath/#oftypetype-type-specifier-collection
|
|
9571
|
+
* @param _context The evaluation context.
|
|
9572
|
+
* @param input The input collection.
|
|
9573
|
+
* @param criteria The condition atom.
|
|
9574
|
+
* @returns A collection containing only those elements in the input collection that are of the given type or a subclass thereof.
|
|
9468
9575
|
*/
|
|
9469
|
-
ofType: (input, criteria) => {
|
|
9576
|
+
ofType: (_context, input, criteria) => {
|
|
9470
9577
|
return input.filter((e) => e.type === criteria.name);
|
|
9471
9578
|
},
|
|
9472
9579
|
/*
|
|
@@ -9480,11 +9587,11 @@
|
|
|
9480
9587
|
* about cardinality is violated at run-time.
|
|
9481
9588
|
*
|
|
9482
9589
|
* See: https://hl7.org/fhirpath/#single-collection
|
|
9483
|
-
*
|
|
9590
|
+
* @param _context The evaluation context.
|
|
9484
9591
|
* @param input The input collection.
|
|
9485
9592
|
* @returns The single item in the input if there is just one item.
|
|
9486
9593
|
*/
|
|
9487
|
-
single: (input) => {
|
|
9594
|
+
single: (_context, input) => {
|
|
9488
9595
|
if (input.length > 1) {
|
|
9489
9596
|
throw new Error('Expected input length one for single()');
|
|
9490
9597
|
}
|
|
@@ -9495,11 +9602,11 @@
|
|
|
9495
9602
|
* This function is equivalent to item[0], so it will return an empty collection if the input collection has no items.
|
|
9496
9603
|
*
|
|
9497
9604
|
* See: https://hl7.org/fhirpath/#first-collection
|
|
9498
|
-
*
|
|
9605
|
+
* @param context The evaluation context.
|
|
9499
9606
|
* @param input The input collection.
|
|
9500
9607
|
* @returns A collection containing only the first item in the input collection.
|
|
9501
9608
|
*/
|
|
9502
|
-
first: (input) => {
|
|
9609
|
+
first: (context, input) => {
|
|
9503
9610
|
return input.length === 0 ? [] : input.slice(0, 1);
|
|
9504
9611
|
},
|
|
9505
9612
|
/**
|
|
@@ -9507,11 +9614,11 @@
|
|
|
9507
9614
|
* Will return an empty collection if the input collection has no items.
|
|
9508
9615
|
*
|
|
9509
9616
|
* See: https://hl7.org/fhirpath/#last-collection
|
|
9510
|
-
*
|
|
9617
|
+
* @param context The evaluation context.
|
|
9511
9618
|
* @param input The input collection.
|
|
9512
9619
|
* @returns A collection containing only the last item in the input collection.
|
|
9513
9620
|
*/
|
|
9514
|
-
last: (input) => {
|
|
9621
|
+
last: (context, input) => {
|
|
9515
9622
|
return input.length === 0 ? [] : input.slice(input.length - 1, input.length);
|
|
9516
9623
|
},
|
|
9517
9624
|
/**
|
|
@@ -9519,11 +9626,11 @@
|
|
|
9519
9626
|
* Will return an empty collection if the input collection has no items, or only one item.
|
|
9520
9627
|
*
|
|
9521
9628
|
* See: https://hl7.org/fhirpath/#tail-collection
|
|
9522
|
-
*
|
|
9629
|
+
* @param context The evaluation context.
|
|
9523
9630
|
* @param input The input collection.
|
|
9524
9631
|
* @returns A collection containing all but the first item in the input collection.
|
|
9525
9632
|
*/
|
|
9526
|
-
tail: (input) => {
|
|
9633
|
+
tail: (context, input) => {
|
|
9527
9634
|
return input.length === 0 ? [] : input.slice(1, input.length);
|
|
9528
9635
|
},
|
|
9529
9636
|
/**
|
|
@@ -9533,12 +9640,13 @@
|
|
|
9533
9640
|
* If num is less than or equal to zero, the input collection is simply returned.
|
|
9534
9641
|
*
|
|
9535
9642
|
* See: https://hl7.org/fhirpath/#skipnum-integer-collection
|
|
9536
|
-
*
|
|
9643
|
+
* @param context The evaluation context.
|
|
9537
9644
|
* @param input The input collection.
|
|
9645
|
+
* @param num The atom representing the number of elements to skip.
|
|
9538
9646
|
* @returns A collection containing all but the first item in the input collection.
|
|
9539
9647
|
*/
|
|
9540
|
-
skip: (input, num) => {
|
|
9541
|
-
const numValue = num.eval(input)[0]?.value;
|
|
9648
|
+
skip: (context, input, num) => {
|
|
9649
|
+
const numValue = num.eval(context, input)[0]?.value;
|
|
9542
9650
|
if (typeof numValue !== 'number') {
|
|
9543
9651
|
throw new Error('Expected a number for skip(num)');
|
|
9544
9652
|
}
|
|
@@ -9557,12 +9665,13 @@
|
|
|
9557
9665
|
* take returns an empty collection.
|
|
9558
9666
|
*
|
|
9559
9667
|
* See: https://hl7.org/fhirpath/#takenum-integer-collection
|
|
9560
|
-
*
|
|
9668
|
+
* @param context The evaluation context.
|
|
9561
9669
|
* @param input The input collection.
|
|
9670
|
+
* @param num The atom representing the number of elements to take.
|
|
9562
9671
|
* @returns A collection containing the first num items in the input collection.
|
|
9563
9672
|
*/
|
|
9564
|
-
take: (input, num) => {
|
|
9565
|
-
const numValue = num.eval(input)[0]?.value;
|
|
9673
|
+
take: (context, input, num) => {
|
|
9674
|
+
const numValue = num.eval(context, input)[0]?.value;
|
|
9566
9675
|
if (typeof numValue !== 'number') {
|
|
9567
9676
|
throw new Error('Expected a number for take(num)');
|
|
9568
9677
|
}
|
|
@@ -9580,12 +9689,16 @@
|
|
|
9580
9689
|
* Order of items is not guaranteed to be preserved in the result of this function.
|
|
9581
9690
|
*
|
|
9582
9691
|
* See: http://hl7.org/fhirpath/#intersectother-collection-collection
|
|
9692
|
+
* @param context The evaluation context.
|
|
9693
|
+
* @param input The input collection.
|
|
9694
|
+
* @param other The atom representing the collection of elements to intersect.
|
|
9695
|
+
* @returns A collection containing the elements that are in both collections.
|
|
9583
9696
|
*/
|
|
9584
|
-
intersect: (input, other) => {
|
|
9697
|
+
intersect: (context, input, other) => {
|
|
9585
9698
|
if (!other) {
|
|
9586
9699
|
return input;
|
|
9587
9700
|
}
|
|
9588
|
-
const otherArray = other.eval(input);
|
|
9701
|
+
const otherArray = other.eval(context, input);
|
|
9589
9702
|
const result = [];
|
|
9590
9703
|
for (const value of input) {
|
|
9591
9704
|
if (!result.some((e) => e.value === value.value) && otherArray.some((e) => e.value === value.value)) {
|
|
@@ -9601,12 +9714,16 @@
|
|
|
9601
9714
|
* e.g. (1 | 2 | 3).exclude(2) returns (1 | 3).
|
|
9602
9715
|
*
|
|
9603
9716
|
* See: http://hl7.org/fhirpath/#excludeother-collection-collection
|
|
9717
|
+
* @param context The evaluation context.
|
|
9718
|
+
* @param input The input collection.
|
|
9719
|
+
* @param other The atom representing the collection of elements to exclude.
|
|
9720
|
+
* @returns A collection containing the elements that are in the input collection but not the other collection.
|
|
9604
9721
|
*/
|
|
9605
|
-
exclude: (input, other) => {
|
|
9722
|
+
exclude: (context, input, other) => {
|
|
9606
9723
|
if (!other) {
|
|
9607
9724
|
return input;
|
|
9608
9725
|
}
|
|
9609
|
-
const otherArray = other.eval(input);
|
|
9726
|
+
const otherArray = other.eval(context, input);
|
|
9610
9727
|
const result = [];
|
|
9611
9728
|
for (const value of input) {
|
|
9612
9729
|
if (!otherArray.some((e) => e.value === value.value)) {
|
|
@@ -9628,12 +9745,16 @@
|
|
|
9628
9745
|
* In other words, this function returns the distinct list of elements from both inputs.
|
|
9629
9746
|
*
|
|
9630
9747
|
* See: http://hl7.org/fhirpath/#unionother-collection
|
|
9748
|
+
* @param context The evaluation context.
|
|
9749
|
+
* @param input The input collection.
|
|
9750
|
+
* @param other The atom representing the collection of elements to merge.
|
|
9751
|
+
* @returns A collection containing the elements that represent the union of both collections.
|
|
9631
9752
|
*/
|
|
9632
|
-
union: (input, other) => {
|
|
9753
|
+
union: (context, input, other) => {
|
|
9633
9754
|
if (!other) {
|
|
9634
9755
|
return input;
|
|
9635
9756
|
}
|
|
9636
|
-
const otherArray = other.eval(input);
|
|
9757
|
+
const otherArray = other.eval(context, input);
|
|
9637
9758
|
return removeDuplicates([...input, ...otherArray]);
|
|
9638
9759
|
},
|
|
9639
9760
|
/**
|
|
@@ -9644,12 +9765,16 @@
|
|
|
9644
9765
|
* There is no expectation of order in the resulting collection.
|
|
9645
9766
|
*
|
|
9646
9767
|
* See: http://hl7.org/fhirpath/#combineother-collection-collection
|
|
9768
|
+
* @param context The evaluation context.
|
|
9769
|
+
* @param input The input collection.
|
|
9770
|
+
* @param other The atom representing the collection of elements to merge.
|
|
9771
|
+
* @returns A collection containing the elements that represent the combination of both collections including duplicates.
|
|
9647
9772
|
*/
|
|
9648
|
-
combine: (input, other) => {
|
|
9773
|
+
combine: (context, input, other) => {
|
|
9649
9774
|
if (!other) {
|
|
9650
9775
|
return input;
|
|
9651
9776
|
}
|
|
9652
|
-
const otherArray = other.eval(input);
|
|
9777
|
+
const otherArray = other.eval(context, input);
|
|
9653
9778
|
return [...input, ...otherArray];
|
|
9654
9779
|
},
|
|
9655
9780
|
/*
|
|
@@ -9672,23 +9797,23 @@
|
|
|
9672
9797
|
* true-result should only be evaluated if the criterion evaluates to true,
|
|
9673
9798
|
* and otherwise-result should only be evaluated otherwise. For implementations,
|
|
9674
9799
|
* this means delaying evaluation of the arguments.
|
|
9675
|
-
*
|
|
9676
|
-
* @param input
|
|
9677
|
-
* @param criterion
|
|
9678
|
-
* @param trueResult
|
|
9679
|
-
* @param otherwiseResult
|
|
9680
|
-
* @returns
|
|
9800
|
+
* @param context The evaluation context.
|
|
9801
|
+
* @param input The input collection.
|
|
9802
|
+
* @param criterion The atom representing the conditional.
|
|
9803
|
+
* @param trueResult The atom to be used if the conditional evaluates to true.
|
|
9804
|
+
* @param otherwiseResult Optional atom to be used if the conditional evaluates to false.
|
|
9805
|
+
* @returns The result of the iif function.
|
|
9681
9806
|
*/
|
|
9682
|
-
iif: (input, criterion, trueResult, otherwiseResult) => {
|
|
9683
|
-
const evalResult = criterion.eval(input);
|
|
9807
|
+
iif: (context, input, criterion, trueResult, otherwiseResult) => {
|
|
9808
|
+
const evalResult = criterion.eval(context, input);
|
|
9684
9809
|
if (evalResult.length > 1 || (evalResult.length === 1 && typeof evalResult[0].value !== 'boolean')) {
|
|
9685
9810
|
throw new Error('Expected criterion to evaluate to a Boolean');
|
|
9686
9811
|
}
|
|
9687
9812
|
if (toJsBoolean(evalResult)) {
|
|
9688
|
-
return trueResult.eval(input);
|
|
9813
|
+
return trueResult.eval(context, input);
|
|
9689
9814
|
}
|
|
9690
9815
|
if (otherwiseResult) {
|
|
9691
|
-
return otherwiseResult.eval(input);
|
|
9816
|
+
return otherwiseResult.eval(context, input);
|
|
9692
9817
|
}
|
|
9693
9818
|
return [];
|
|
9694
9819
|
},
|
|
@@ -9704,11 +9829,11 @@
|
|
|
9704
9829
|
* If the item is not one the above types, or the item is a String, Integer, or Decimal, but is not equal to one of the possible values convertible to a Boolean, the result is empty.
|
|
9705
9830
|
*
|
|
9706
9831
|
* See: https://hl7.org/fhirpath/#toboolean-boolean
|
|
9707
|
-
*
|
|
9708
|
-
* @param input
|
|
9709
|
-
* @returns
|
|
9832
|
+
* @param _context The evaluation context.
|
|
9833
|
+
* @param input The input collection.
|
|
9834
|
+
* @returns The input converted to boolean value.
|
|
9710
9835
|
*/
|
|
9711
|
-
toBoolean: (input) => {
|
|
9836
|
+
toBoolean: (_context, input) => {
|
|
9712
9837
|
if (input.length === 0) {
|
|
9713
9838
|
return [];
|
|
9714
9839
|
}
|
|
@@ -9748,15 +9873,15 @@
|
|
|
9748
9873
|
* If the input collection is empty, the result is empty.
|
|
9749
9874
|
*
|
|
9750
9875
|
* See: http://hl7.org/fhirpath/#convertstoboolean-boolean
|
|
9751
|
-
*
|
|
9752
|
-
* @param input
|
|
9753
|
-
* @returns
|
|
9876
|
+
* @param context The evaluation context.
|
|
9877
|
+
* @param input The input collection.
|
|
9878
|
+
* @returns True if the input can be converted to boolean.
|
|
9754
9879
|
*/
|
|
9755
|
-
convertsToBoolean: (input) => {
|
|
9880
|
+
convertsToBoolean: (context, input) => {
|
|
9756
9881
|
if (input.length === 0) {
|
|
9757
9882
|
return [];
|
|
9758
9883
|
}
|
|
9759
|
-
return booleanToTypedValue(functions.toBoolean(input).length === 1);
|
|
9884
|
+
return booleanToTypedValue(functions.toBoolean(context, input).length === 1);
|
|
9760
9885
|
},
|
|
9761
9886
|
/**
|
|
9762
9887
|
* Returns the integer representation of the input.
|
|
@@ -9775,11 +9900,11 @@
|
|
|
9775
9900
|
* If the input collection is empty, the result is empty.
|
|
9776
9901
|
*
|
|
9777
9902
|
* See: https://hl7.org/fhirpath/#tointeger-integer
|
|
9778
|
-
*
|
|
9903
|
+
* @param _context The evaluation context.
|
|
9779
9904
|
* @param input The input collection.
|
|
9780
9905
|
* @returns The string representation of the input.
|
|
9781
9906
|
*/
|
|
9782
|
-
toInteger: (input) => {
|
|
9907
|
+
toInteger: (_context, input) => {
|
|
9783
9908
|
if (input.length === 0) {
|
|
9784
9909
|
return [];
|
|
9785
9910
|
}
|
|
@@ -9809,15 +9934,15 @@
|
|
|
9809
9934
|
* If the input collection is empty, the result is empty.
|
|
9810
9935
|
*
|
|
9811
9936
|
* See: https://hl7.org/fhirpath/#convertstointeger-boolean
|
|
9812
|
-
*
|
|
9937
|
+
* @param context The evaluation context.
|
|
9813
9938
|
* @param input The input collection.
|
|
9814
|
-
* @returns
|
|
9939
|
+
* @returns True if the input can be converted to an integer.
|
|
9815
9940
|
*/
|
|
9816
|
-
convertsToInteger: (input) => {
|
|
9941
|
+
convertsToInteger: (context, input) => {
|
|
9817
9942
|
if (input.length === 0) {
|
|
9818
9943
|
return [];
|
|
9819
9944
|
}
|
|
9820
|
-
return booleanToTypedValue(functions.toInteger(input).length === 1);
|
|
9945
|
+
return booleanToTypedValue(functions.toInteger(context, input).length === 1);
|
|
9821
9946
|
},
|
|
9822
9947
|
/**
|
|
9823
9948
|
* If the input collection contains a single item, this function will return a single date if:
|
|
@@ -9834,8 +9959,11 @@
|
|
|
9834
9959
|
* If the input collection is empty, the result is empty.
|
|
9835
9960
|
*
|
|
9836
9961
|
* See: https://hl7.org/fhirpath/#todate-date
|
|
9962
|
+
* @param _context The evaluation context.
|
|
9963
|
+
* @param input The input collection.
|
|
9964
|
+
* @returns The value converted to a date if possible; otherwise empty array.
|
|
9837
9965
|
*/
|
|
9838
|
-
toDate: (input) => {
|
|
9966
|
+
toDate: (_context, input) => {
|
|
9839
9967
|
if (input.length === 0) {
|
|
9840
9968
|
return [];
|
|
9841
9969
|
}
|
|
@@ -9860,35 +9988,38 @@
|
|
|
9860
9988
|
* If the input collection is empty, the result is empty.
|
|
9861
9989
|
*
|
|
9862
9990
|
* See: https://hl7.org/fhirpath/#convertstodate-boolean
|
|
9991
|
+
* @param context The evaluation context.
|
|
9992
|
+
* @param input The input collection.
|
|
9993
|
+
* @returns True if the item can be converted to a date.
|
|
9863
9994
|
*/
|
|
9864
|
-
convertsToDate: (input) => {
|
|
9995
|
+
convertsToDate: (context, input) => {
|
|
9865
9996
|
if (input.length === 0) {
|
|
9866
9997
|
return [];
|
|
9867
9998
|
}
|
|
9868
|
-
return booleanToTypedValue(functions.toDate(input).length === 1);
|
|
9999
|
+
return booleanToTypedValue(functions.toDate(context, input).length === 1);
|
|
9869
10000
|
},
|
|
9870
10001
|
/**
|
|
9871
|
-
|
|
9872
|
-
|
|
9873
|
-
|
|
9874
|
-
|
|
9875
|
-
|
|
9876
|
-
|
|
9877
|
-
|
|
9878
|
-
|
|
9879
|
-
|
|
9880
|
-
|
|
9881
|
-
|
|
9882
|
-
|
|
9883
|
-
|
|
9884
|
-
|
|
9885
|
-
|
|
9886
|
-
|
|
9887
|
-
|
|
9888
|
-
|
|
9889
|
-
|
|
9890
|
-
|
|
9891
|
-
toDateTime: (input) => {
|
|
10002
|
+
* If the input collection contains a single item, this function will return a single datetime if:
|
|
10003
|
+
* 1) the item is a DateTime
|
|
10004
|
+
* 2) the item is a Date, in which case the result is a DateTime with the year, month, and day of the Date, and the time components empty (not set to zero)
|
|
10005
|
+
* 3) the item is a String and is convertible to a DateTime
|
|
10006
|
+
*
|
|
10007
|
+
* If the item is not one of the above types, the result is empty.
|
|
10008
|
+
*
|
|
10009
|
+
* If the item is a String, but the string is not convertible to a DateTime (using the format YYYY-MM-DDThh:mm:ss.fff(+|-)hh:mm), the result is empty.
|
|
10010
|
+
*
|
|
10011
|
+
* If the item contains a partial datetime (e.g. '2012-01-01T10:00'), the result is a partial datetime.
|
|
10012
|
+
*
|
|
10013
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10014
|
+
*
|
|
10015
|
+
* If the input collection is empty, the result is empty.
|
|
10016
|
+
*
|
|
10017
|
+
* See: https://hl7.org/fhirpath/#todatetime-datetime
|
|
10018
|
+
* @param _context The evaluation context.
|
|
10019
|
+
* @param input The input collection.
|
|
10020
|
+
* @returns The value converted to a datetime if possible; otherwise empty array.
|
|
10021
|
+
*/
|
|
10022
|
+
toDateTime: (_context, input) => {
|
|
9892
10023
|
if (input.length === 0) {
|
|
9893
10024
|
return [];
|
|
9894
10025
|
}
|
|
@@ -9911,15 +10042,15 @@
|
|
|
9911
10042
|
* If the input collection is empty, the result is empty.
|
|
9912
10043
|
*
|
|
9913
10044
|
* See: https://hl7.org/fhirpath/#convertstodatetime-boolean
|
|
9914
|
-
*
|
|
9915
|
-
* @param input
|
|
9916
|
-
* @returns
|
|
10045
|
+
* @param context The evaluation context.
|
|
10046
|
+
* @param input The input collection.
|
|
10047
|
+
* @returns True if the item can be converted to a dateTime.
|
|
9917
10048
|
*/
|
|
9918
|
-
convertsToDateTime: (input) => {
|
|
10049
|
+
convertsToDateTime: (context, input) => {
|
|
9919
10050
|
if (input.length === 0) {
|
|
9920
10051
|
return [];
|
|
9921
10052
|
}
|
|
9922
|
-
return booleanToTypedValue(functions.toDateTime(input).length === 1);
|
|
10053
|
+
return booleanToTypedValue(functions.toDateTime(context, input).length === 1);
|
|
9923
10054
|
},
|
|
9924
10055
|
/**
|
|
9925
10056
|
* If the input collection contains a single item, this function will return a single decimal if:
|
|
@@ -9935,11 +10066,11 @@
|
|
|
9935
10066
|
* If the input collection is empty, the result is empty.
|
|
9936
10067
|
*
|
|
9937
10068
|
* See: https://hl7.org/fhirpath/#decimal-conversion-functions
|
|
9938
|
-
*
|
|
10069
|
+
* @param _context The evaluation context.
|
|
9939
10070
|
* @param input The input collection.
|
|
9940
|
-
* @returns
|
|
10071
|
+
* @returns The value converted to a decimal if possible; otherwise empty array.
|
|
9941
10072
|
*/
|
|
9942
|
-
toDecimal: (input) => {
|
|
10073
|
+
toDecimal: (_context, input) => {
|
|
9943
10074
|
if (input.length === 0) {
|
|
9944
10075
|
return [];
|
|
9945
10076
|
}
|
|
@@ -9956,27 +10087,27 @@
|
|
|
9956
10087
|
return [];
|
|
9957
10088
|
},
|
|
9958
10089
|
/**
|
|
9959
|
-
|
|
9960
|
-
|
|
9961
|
-
|
|
9962
|
-
|
|
9963
|
-
|
|
9964
|
-
|
|
9965
|
-
|
|
9966
|
-
|
|
9967
|
-
|
|
9968
|
-
|
|
9969
|
-
|
|
9970
|
-
|
|
9971
|
-
|
|
9972
|
-
|
|
9973
|
-
|
|
9974
|
-
|
|
9975
|
-
convertsToDecimal: (input) => {
|
|
10090
|
+
* If the input collection contains a single item, this function will true if:
|
|
10091
|
+
* 1) the item is an Integer or Decimal
|
|
10092
|
+
* 2) the item is a String and is convertible to a Decimal
|
|
10093
|
+
* 3) the item is a Boolean
|
|
10094
|
+
*
|
|
10095
|
+
* If the item is not one of the above types, or is not convertible to a Decimal (using the regex format (\\+|-)?\d+(\.\d+)?), the result is false.
|
|
10096
|
+
*
|
|
10097
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10098
|
+
*
|
|
10099
|
+
* If the input collection is empty, the result is empty.
|
|
10100
|
+
*
|
|
10101
|
+
* See: https://hl7.org/fhirpath/#convertstodecimal-boolean
|
|
10102
|
+
* @param context The evaluation context.
|
|
10103
|
+
* @param input The input collection.
|
|
10104
|
+
* @returns The value converted to a decimal if possible; otherwise empty array.
|
|
10105
|
+
*/
|
|
10106
|
+
convertsToDecimal: (context, input) => {
|
|
9976
10107
|
if (input.length === 0) {
|
|
9977
10108
|
return [];
|
|
9978
10109
|
}
|
|
9979
|
-
return booleanToTypedValue(functions.toDecimal(input).length === 1);
|
|
10110
|
+
return booleanToTypedValue(functions.toDecimal(context, input).length === 1);
|
|
9980
10111
|
},
|
|
9981
10112
|
/**
|
|
9982
10113
|
* If the input collection contains a single item, this function will return a single quantity if:
|
|
@@ -9988,11 +10119,11 @@
|
|
|
9988
10119
|
* If the item is not one of the above types, the result is empty.
|
|
9989
10120
|
*
|
|
9990
10121
|
* See: https://hl7.org/fhirpath/#quantity-conversion-functions
|
|
9991
|
-
*
|
|
10122
|
+
* @param _context The evaluation context.
|
|
9992
10123
|
* @param input The input collection.
|
|
9993
|
-
* @returns
|
|
10124
|
+
* @returns The value converted to a quantity if possible; otherwise empty array.
|
|
9994
10125
|
*/
|
|
9995
|
-
toQuantity: (input) => {
|
|
10126
|
+
toQuantity: (_context, input) => {
|
|
9996
10127
|
if (input.length === 0) {
|
|
9997
10128
|
return [];
|
|
9998
10129
|
}
|
|
@@ -10030,15 +10161,15 @@
|
|
|
10030
10161
|
* If the unit argument is provided, it must be the string representation of a UCUM code (or a FHIRPath calendar duration keyword), and is used to determine whether the input quantity can be converted to the given unit, according to the unit conversion rules specified by UCUM. If the input quantity can be converted, the result is true, otherwise, the result is false.
|
|
10031
10162
|
*
|
|
10032
10163
|
* See: https://hl7.org/fhirpath/#convertstoquantityunit-string-boolean
|
|
10033
|
-
*
|
|
10164
|
+
* @param context The evaluation context.
|
|
10034
10165
|
* @param input The input collection.
|
|
10035
|
-
* @returns
|
|
10166
|
+
* @returns True if the item can be converted to a quantity.
|
|
10036
10167
|
*/
|
|
10037
|
-
convertsToQuantity: (input) => {
|
|
10168
|
+
convertsToQuantity: (context, input) => {
|
|
10038
10169
|
if (input.length === 0) {
|
|
10039
10170
|
return [];
|
|
10040
10171
|
}
|
|
10041
|
-
return booleanToTypedValue(functions.toQuantity(input).length === 1);
|
|
10172
|
+
return booleanToTypedValue(functions.toQuantity(context, input).length === 1);
|
|
10042
10173
|
},
|
|
10043
10174
|
/**
|
|
10044
10175
|
* Returns the string representation of the input.
|
|
@@ -10052,11 +10183,11 @@
|
|
|
10052
10183
|
* If the item is not one of the above types, the result is false.
|
|
10053
10184
|
*
|
|
10054
10185
|
* See: https://hl7.org/fhirpath/#tostring-string
|
|
10055
|
-
*
|
|
10186
|
+
* @param _context The evaluation context.
|
|
10056
10187
|
* @param input The input collection.
|
|
10057
10188
|
* @returns The string representation of the input.
|
|
10058
10189
|
*/
|
|
10059
|
-
toString: (input) => {
|
|
10190
|
+
toString: (_context, input) => {
|
|
10060
10191
|
if (input.length === 0) {
|
|
10061
10192
|
return [];
|
|
10062
10193
|
}
|
|
@@ -10085,15 +10216,15 @@
|
|
|
10085
10216
|
* If the input collection is empty, the result is empty.
|
|
10086
10217
|
*
|
|
10087
10218
|
* See: https://hl7.org/fhirpath/#tostring-string
|
|
10088
|
-
*
|
|
10219
|
+
* @param context The evaluation context.
|
|
10089
10220
|
* @param input The input collection.
|
|
10090
|
-
* @returns
|
|
10221
|
+
* @returns True if the item can be converted to a string
|
|
10091
10222
|
*/
|
|
10092
|
-
convertsToString: (input) => {
|
|
10223
|
+
convertsToString: (context, input) => {
|
|
10093
10224
|
if (input.length === 0) {
|
|
10094
10225
|
return [];
|
|
10095
10226
|
}
|
|
10096
|
-
return booleanToTypedValue(functions.toString(input).length === 1);
|
|
10227
|
+
return booleanToTypedValue(functions.toString(context, input).length === 1);
|
|
10097
10228
|
},
|
|
10098
10229
|
/**
|
|
10099
10230
|
* If the input collection contains a single item, this function will return a single time if:
|
|
@@ -10111,11 +10242,11 @@
|
|
|
10111
10242
|
* If the input collection is empty, the result is empty.
|
|
10112
10243
|
*
|
|
10113
10244
|
* See: https://hl7.org/fhirpath/#totime-time
|
|
10114
|
-
*
|
|
10115
|
-
* @param input
|
|
10116
|
-
* @returns
|
|
10245
|
+
* @param _context The evaluation context.
|
|
10246
|
+
* @param input The input collection.
|
|
10247
|
+
* @returns The value converted to a time if possible; otherwise empty array.
|
|
10117
10248
|
*/
|
|
10118
|
-
toTime: (input) => {
|
|
10249
|
+
toTime: (_context, input) => {
|
|
10119
10250
|
if (input.length === 0) {
|
|
10120
10251
|
return [];
|
|
10121
10252
|
}
|
|
@@ -10140,15 +10271,15 @@
|
|
|
10140
10271
|
* If the input collection is empty, the result is empty.
|
|
10141
10272
|
*
|
|
10142
10273
|
* See: https://hl7.org/fhirpath/#convertstotime-boolean
|
|
10143
|
-
*
|
|
10144
|
-
* @param input
|
|
10145
|
-
* @returns
|
|
10274
|
+
* @param context The evaluation context.
|
|
10275
|
+
* @param input The input collection.
|
|
10276
|
+
* @returns True if the item can be converted to a time.
|
|
10146
10277
|
*/
|
|
10147
|
-
convertsToTime: (input) => {
|
|
10278
|
+
convertsToTime: (context, input) => {
|
|
10148
10279
|
if (input.length === 0) {
|
|
10149
10280
|
return [];
|
|
10150
10281
|
}
|
|
10151
|
-
return booleanToTypedValue(functions.toTime(input).length === 1);
|
|
10282
|
+
return booleanToTypedValue(functions.toTime(context, input).length === 1);
|
|
10152
10283
|
},
|
|
10153
10284
|
/*
|
|
10154
10285
|
* 5.6. String Manipulation.
|
|
@@ -10165,12 +10296,13 @@
|
|
|
10165
10296
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10166
10297
|
*
|
|
10167
10298
|
* See: https://hl7.org/fhirpath/#indexofsubstring-string-integer
|
|
10168
|
-
*
|
|
10299
|
+
* @param context The evaluation context.
|
|
10169
10300
|
* @param input The input collection.
|
|
10301
|
+
* @param substringAtom The substring to search for.
|
|
10170
10302
|
* @returns The index of the substring.
|
|
10171
10303
|
*/
|
|
10172
|
-
indexOf: (input, substringAtom) => {
|
|
10173
|
-
return applyStringFunc((str, substring) => str.indexOf(substring), input, substringAtom);
|
|
10304
|
+
indexOf: (context, input, substringAtom) => {
|
|
10305
|
+
return applyStringFunc((str, substring) => str.indexOf(substring), context, input, substringAtom);
|
|
10174
10306
|
},
|
|
10175
10307
|
/**
|
|
10176
10308
|
* Returns the part of the string starting at position start (zero-based). If length is given, will return at most length number of characters from the input string.
|
|
@@ -10182,98 +10314,172 @@
|
|
|
10182
10314
|
* If an empty length is provided, the behavior is the same as if length had not been provided.
|
|
10183
10315
|
*
|
|
10184
10316
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10185
|
-
*
|
|
10317
|
+
* @param context The evaluation context.
|
|
10186
10318
|
* @param input The input collection.
|
|
10187
|
-
* @
|
|
10319
|
+
* @param startAtom The start index atom.
|
|
10320
|
+
* @param lengthAtom Optional length atom.
|
|
10321
|
+
* @returns The substring.
|
|
10188
10322
|
*/
|
|
10189
|
-
substring: (input, startAtom, lengthAtom) => {
|
|
10323
|
+
substring: (context, input, startAtom, lengthAtom) => {
|
|
10190
10324
|
return applyStringFunc((str, start, length) => {
|
|
10191
10325
|
const startIndex = start;
|
|
10192
10326
|
const endIndex = length ? startIndex + length : str.length;
|
|
10193
10327
|
return startIndex < 0 || startIndex >= str.length ? undefined : str.substring(startIndex, endIndex);
|
|
10194
|
-
}, input, startAtom, lengthAtom);
|
|
10328
|
+
}, context, input, startAtom, lengthAtom);
|
|
10195
10329
|
},
|
|
10196
10330
|
/**
|
|
10331
|
+
* Returns true when the input string starts with the given prefix.
|
|
10197
10332
|
*
|
|
10333
|
+
* If prefix is the empty string (''), the result is true.
|
|
10334
|
+
*
|
|
10335
|
+
* If the input collection is empty, the result is empty.
|
|
10336
|
+
*
|
|
10337
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10338
|
+
*
|
|
10339
|
+
* See: https://hl7.org/fhirpath/#startswithprefix-string-boolean
|
|
10340
|
+
* @param context The evaluation context.
|
|
10198
10341
|
* @param input The input collection.
|
|
10199
|
-
* @
|
|
10342
|
+
* @param prefixAtom The prefix substring to test.
|
|
10343
|
+
* @returns True if the input string starts with the given prefix string.
|
|
10200
10344
|
*/
|
|
10201
|
-
startsWith: (input, prefixAtom) => {
|
|
10202
|
-
return applyStringFunc((str, prefix) => str.startsWith(prefix), input, prefixAtom);
|
|
10345
|
+
startsWith: (context, input, prefixAtom) => {
|
|
10346
|
+
return applyStringFunc((str, prefix) => str.startsWith(prefix), context, input, prefixAtom);
|
|
10203
10347
|
},
|
|
10204
10348
|
/**
|
|
10349
|
+
* Returns true when the input string ends with the given suffix.
|
|
10350
|
+
*
|
|
10351
|
+
* If suffix is the empty string (''), the result is true.
|
|
10352
|
+
*
|
|
10353
|
+
* If the input collection is empty, the result is empty.
|
|
10354
|
+
*
|
|
10355
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10205
10356
|
*
|
|
10357
|
+
* See: https://hl7.org/fhirpath/#endswithsuffix-string-boolean
|
|
10358
|
+
* @param context The evaluation context.
|
|
10206
10359
|
* @param input The input collection.
|
|
10207
|
-
* @
|
|
10360
|
+
* @param suffixAtom The suffix substring to test.
|
|
10361
|
+
* @returns True if the input string ends with the given suffix string.
|
|
10208
10362
|
*/
|
|
10209
|
-
endsWith: (input, suffixAtom) => {
|
|
10210
|
-
return applyStringFunc((str, suffix) => str.endsWith(suffix), input, suffixAtom);
|
|
10363
|
+
endsWith: (context, input, suffixAtom) => {
|
|
10364
|
+
return applyStringFunc((str, suffix) => str.endsWith(suffix), context, input, suffixAtom);
|
|
10211
10365
|
},
|
|
10212
10366
|
/**
|
|
10367
|
+
* Returns true when the given substring is a substring of the input string.
|
|
10368
|
+
*
|
|
10369
|
+
* If substring is the empty string (''), the result is true.
|
|
10370
|
+
*
|
|
10371
|
+
* If the input collection is empty, the result is empty.
|
|
10213
10372
|
*
|
|
10373
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10374
|
+
*
|
|
10375
|
+
* See: https://hl7.org/fhirpath/#containssubstring-string-boolean
|
|
10376
|
+
* @param context The evaluation context.
|
|
10214
10377
|
* @param input The input collection.
|
|
10215
|
-
* @
|
|
10378
|
+
* @param substringAtom The substring to test.
|
|
10379
|
+
* @returns True if the input string contains the given substring.
|
|
10216
10380
|
*/
|
|
10217
|
-
contains: (input, substringAtom) => {
|
|
10218
|
-
return applyStringFunc((str, substring) => str.includes(substring), input, substringAtom);
|
|
10381
|
+
contains: (context, input, substringAtom) => {
|
|
10382
|
+
return applyStringFunc((str, substring) => str.includes(substring), context, input, substringAtom);
|
|
10219
10383
|
},
|
|
10220
10384
|
/**
|
|
10385
|
+
* Returns the input string with all characters converted to upper case.
|
|
10386
|
+
* If the input collection is empty, the result is empty.
|
|
10387
|
+
*
|
|
10388
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10221
10389
|
*
|
|
10390
|
+
* See: https://hl7.org/fhirpath/#upper-string
|
|
10391
|
+
* @param context The evaluation context.
|
|
10222
10392
|
* @param input The input collection.
|
|
10223
|
-
* @returns The
|
|
10393
|
+
* @returns The string converted to upper case.
|
|
10224
10394
|
*/
|
|
10225
|
-
upper: (input) => {
|
|
10226
|
-
return applyStringFunc((str) => str.toUpperCase(), input);
|
|
10395
|
+
upper: (context, input) => {
|
|
10396
|
+
return applyStringFunc((str) => str.toUpperCase(), context, input);
|
|
10227
10397
|
},
|
|
10228
10398
|
/**
|
|
10399
|
+
* Returns the input string with all characters converted to lower case.
|
|
10400
|
+
*
|
|
10401
|
+
* If the input collection is empty, the result is empty.
|
|
10402
|
+
*
|
|
10403
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10229
10404
|
*
|
|
10405
|
+
* See: https://hl7.org/fhirpath/#lower-string
|
|
10406
|
+
* @param context The evaluation context.
|
|
10230
10407
|
* @param input The input collection.
|
|
10231
|
-
* @returns The
|
|
10408
|
+
* @returns The string converted to lower case.
|
|
10232
10409
|
*/
|
|
10233
|
-
lower: (input) => {
|
|
10234
|
-
return applyStringFunc((str) => str.toLowerCase(), input);
|
|
10410
|
+
lower: (context, input) => {
|
|
10411
|
+
return applyStringFunc((str) => str.toLowerCase(), context, input);
|
|
10235
10412
|
},
|
|
10236
10413
|
/**
|
|
10414
|
+
* Returns the input string with all instances of pattern replaced with substitution. If the substitution is the empty string (''),
|
|
10415
|
+
* instances of pattern are removed from the result. If pattern is the empty string (''), every character in the input string is
|
|
10416
|
+
* surrounded by the substitution, e.g. 'abc'.replace('','x') becomes 'xaxbxcx'.
|
|
10417
|
+
*
|
|
10418
|
+
* If the input collection, pattern, or substitution are empty, the result is empty ({ }).
|
|
10419
|
+
*
|
|
10420
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10237
10421
|
*
|
|
10422
|
+
* See: https://hl7.org/fhirpath/#replacepattern-string-substitution-string-string
|
|
10423
|
+
* @param context The evaluation context.
|
|
10238
10424
|
* @param input The input collection.
|
|
10239
|
-
* @
|
|
10425
|
+
* @param patternAtom The pattern to search for.
|
|
10426
|
+
* @param substitionAtom The substition to replace with.
|
|
10427
|
+
* @returns The string with all instances of the search pattern replaced with the substitution string.
|
|
10240
10428
|
*/
|
|
10241
|
-
replace: (input, patternAtom, substitionAtom) => {
|
|
10242
|
-
return applyStringFunc((str, pattern, substition) => str.replaceAll(pattern, substition), input, patternAtom, substitionAtom);
|
|
10429
|
+
replace: (context, input, patternAtom, substitionAtom) => {
|
|
10430
|
+
return applyStringFunc((str, pattern, substition) => str.replaceAll(pattern, substition), context, input, patternAtom, substitionAtom);
|
|
10243
10431
|
},
|
|
10244
10432
|
/**
|
|
10433
|
+
* Returns true when the value matches the given regular expression. Regular expressions should function consistently, regardless of any culture- and locale-specific settings in the environment, should be case-sensitive, use 'single line' mode and allow Unicode characters.
|
|
10434
|
+
*
|
|
10435
|
+
* If the input collection or regex are empty, the result is empty ({ }).
|
|
10245
10436
|
*
|
|
10437
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10438
|
+
*
|
|
10439
|
+
* See: https://hl7.org/fhirpath/#matchesregex-string-boolean
|
|
10440
|
+
* @param context The evaluation context.
|
|
10246
10441
|
* @param input The input collection.
|
|
10247
|
-
* @
|
|
10442
|
+
* @param regexAtom The regular expression atom.
|
|
10443
|
+
* @returns True if the input string matches the given regular expression.
|
|
10248
10444
|
*/
|
|
10249
|
-
matches: (input, regexAtom) => {
|
|
10250
|
-
return applyStringFunc((str, regex) => !!str.match(regex), input, regexAtom);
|
|
10445
|
+
matches: (context, input, regexAtom) => {
|
|
10446
|
+
return applyStringFunc((str, regex) => !!str.match(regex), context, input, regexAtom);
|
|
10251
10447
|
},
|
|
10252
10448
|
/**
|
|
10449
|
+
* Matches the input using the regular expression in regex and replaces each match with the substitution string. The substitution may refer to identified match groups in the regular expression.
|
|
10253
10450
|
*
|
|
10451
|
+
* If the input collection, regex, or substitution are empty, the result is empty ({ }).
|
|
10452
|
+
*
|
|
10453
|
+
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10454
|
+
*
|
|
10455
|
+
* See: https://hl7.org/fhirpath/#replacematchesregex-string-substitution-string-string
|
|
10456
|
+
* @param context The evaluation context.
|
|
10254
10457
|
* @param input The input collection.
|
|
10255
|
-
* @
|
|
10458
|
+
* @param regexAtom The regular expression atom.
|
|
10459
|
+
* @param substitionAtom The substition to replace with.
|
|
10460
|
+
* @returns The string with all instances of the search pattern replaced with the substitution string.
|
|
10256
10461
|
*/
|
|
10257
|
-
replaceMatches: (input, regexAtom, substitionAtom) => {
|
|
10258
|
-
return applyStringFunc((str, pattern, substition) => str.replaceAll(pattern, substition), input, regexAtom, substitionAtom);
|
|
10462
|
+
replaceMatches: (context, input, regexAtom, substitionAtom) => {
|
|
10463
|
+
return applyStringFunc((str, pattern, substition) => str.replaceAll(pattern, substition), context, input, regexAtom, substitionAtom);
|
|
10259
10464
|
},
|
|
10260
10465
|
/**
|
|
10261
|
-
*
|
|
10466
|
+
* @param context The evaluation context.
|
|
10262
10467
|
* @param input The input collection.
|
|
10263
10468
|
* @returns The index of the substring.
|
|
10264
10469
|
*/
|
|
10265
|
-
length: (input) => {
|
|
10266
|
-
return applyStringFunc((str) => str.length, input);
|
|
10470
|
+
length: (context, input) => {
|
|
10471
|
+
return applyStringFunc((str) => str.length, context, input);
|
|
10267
10472
|
},
|
|
10268
10473
|
/**
|
|
10269
10474
|
* Returns the list of characters in the input string. If the input collection is empty ({ }), the result is empty.
|
|
10270
10475
|
*
|
|
10271
10476
|
* See: https://hl7.org/fhirpath/#tochars-collection
|
|
10272
|
-
*
|
|
10477
|
+
* @param context The evaluation context.
|
|
10273
10478
|
* @param input The input collection.
|
|
10479
|
+
* @returns Array of characters.
|
|
10274
10480
|
*/
|
|
10275
|
-
toChars: (input) => {
|
|
10276
|
-
return applyStringFunc((str) => (str ? str.split('') : undefined), input);
|
|
10481
|
+
toChars: (context, input) => {
|
|
10482
|
+
return applyStringFunc((str) => (str ? str.split('') : undefined), context, input);
|
|
10277
10483
|
},
|
|
10278
10484
|
/*
|
|
10279
10485
|
* 5.7. Math
|
|
@@ -10286,12 +10492,12 @@
|
|
|
10286
10492
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10287
10493
|
*
|
|
10288
10494
|
* See: https://hl7.org/fhirpath/#abs-integer-decimal-quantity
|
|
10289
|
-
*
|
|
10495
|
+
* @param context The evaluation context.
|
|
10290
10496
|
* @param input The input collection.
|
|
10291
10497
|
* @returns A collection containing the result.
|
|
10292
10498
|
*/
|
|
10293
|
-
abs: (input) => {
|
|
10294
|
-
return applyMathFunc(Math.abs, input);
|
|
10499
|
+
abs: (context, input) => {
|
|
10500
|
+
return applyMathFunc(Math.abs, context, input);
|
|
10295
10501
|
},
|
|
10296
10502
|
/**
|
|
10297
10503
|
* Returns the first integer greater than or equal to the input.
|
|
@@ -10301,12 +10507,12 @@
|
|
|
10301
10507
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10302
10508
|
*
|
|
10303
10509
|
* See: https://hl7.org/fhirpath/#ceiling-integer
|
|
10304
|
-
*
|
|
10510
|
+
* @param context The evaluation context.
|
|
10305
10511
|
* @param input The input collection.
|
|
10306
10512
|
* @returns A collection containing the result.
|
|
10307
10513
|
*/
|
|
10308
|
-
ceiling: (input) => {
|
|
10309
|
-
return applyMathFunc(Math.ceil, input);
|
|
10514
|
+
ceiling: (context, input) => {
|
|
10515
|
+
return applyMathFunc(Math.ceil, context, input);
|
|
10310
10516
|
},
|
|
10311
10517
|
/**
|
|
10312
10518
|
* Returns e raised to the power of the input.
|
|
@@ -10318,12 +10524,12 @@
|
|
|
10318
10524
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10319
10525
|
*
|
|
10320
10526
|
* See: https://hl7.org/fhirpath/#exp-decimal
|
|
10321
|
-
*
|
|
10527
|
+
* @param context The evaluation context.
|
|
10322
10528
|
* @param input The input collection.
|
|
10323
10529
|
* @returns A collection containing the result.
|
|
10324
10530
|
*/
|
|
10325
|
-
exp: (input) => {
|
|
10326
|
-
return applyMathFunc(Math.exp, input);
|
|
10531
|
+
exp: (context, input) => {
|
|
10532
|
+
return applyMathFunc(Math.exp, context, input);
|
|
10327
10533
|
},
|
|
10328
10534
|
/**
|
|
10329
10535
|
* Returns the first integer less than or equal to the input.
|
|
@@ -10333,12 +10539,12 @@
|
|
|
10333
10539
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10334
10540
|
*
|
|
10335
10541
|
* See: https://hl7.org/fhirpath/#floor-integer
|
|
10336
|
-
*
|
|
10542
|
+
* @param context The evaluation context.
|
|
10337
10543
|
* @param input The input collection.
|
|
10338
10544
|
* @returns A collection containing the result.
|
|
10339
10545
|
*/
|
|
10340
|
-
floor: (input) => {
|
|
10341
|
-
return applyMathFunc(Math.floor, input);
|
|
10546
|
+
floor: (context, input) => {
|
|
10547
|
+
return applyMathFunc(Math.floor, context, input);
|
|
10342
10548
|
},
|
|
10343
10549
|
/**
|
|
10344
10550
|
* Returns the natural logarithm of the input (i.e. the logarithm base e).
|
|
@@ -10350,12 +10556,12 @@
|
|
|
10350
10556
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10351
10557
|
*
|
|
10352
10558
|
* See: https://hl7.org/fhirpath/#ln-decimal
|
|
10353
|
-
*
|
|
10559
|
+
* @param context The evaluation context.
|
|
10354
10560
|
* @param input The input collection.
|
|
10355
10561
|
* @returns A collection containing the result.
|
|
10356
10562
|
*/
|
|
10357
|
-
ln: (input) => {
|
|
10358
|
-
return applyMathFunc(Math.log, input);
|
|
10563
|
+
ln: (context, input) => {
|
|
10564
|
+
return applyMathFunc(Math.log, context, input);
|
|
10359
10565
|
},
|
|
10360
10566
|
/**
|
|
10361
10567
|
* Returns the logarithm base base of the input number.
|
|
@@ -10369,12 +10575,13 @@
|
|
|
10369
10575
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10370
10576
|
*
|
|
10371
10577
|
* See: https://hl7.org/fhirpath/#logbase-decimal-decimal
|
|
10372
|
-
*
|
|
10578
|
+
* @param context The evaluation context.
|
|
10373
10579
|
* @param input The input collection.
|
|
10580
|
+
* @param baseAtom The logarithm base.
|
|
10374
10581
|
* @returns A collection containing the result.
|
|
10375
10582
|
*/
|
|
10376
|
-
log: (input, baseAtom) => {
|
|
10377
|
-
return applyMathFunc((value, base) => Math.log(value) / Math.log(base), input, baseAtom);
|
|
10583
|
+
log: (context, input, baseAtom) => {
|
|
10584
|
+
return applyMathFunc((value, base) => Math.log(value) / Math.log(base), context, input, baseAtom);
|
|
10378
10585
|
},
|
|
10379
10586
|
/**
|
|
10380
10587
|
* Raises a number to the exponent power. If this function is used with Integers, the result is an Integer. If the function is used with Decimals, the result is a Decimal. If the function is used with a mixture of Integer and Decimal, the Integer is implicitly converted to a Decimal and the result is a Decimal.
|
|
@@ -10386,12 +10593,13 @@
|
|
|
10386
10593
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10387
10594
|
*
|
|
10388
10595
|
* See: https://hl7.org/fhirpath/#powerexponent-integer-decimal-integer-decimal
|
|
10389
|
-
*
|
|
10596
|
+
* @param context The evaluation context.
|
|
10390
10597
|
* @param input The input collection.
|
|
10598
|
+
* @param expAtom The exponent power.
|
|
10391
10599
|
* @returns A collection containing the result.
|
|
10392
10600
|
*/
|
|
10393
|
-
power: (input, expAtom) => {
|
|
10394
|
-
return applyMathFunc(Math.pow, input, expAtom);
|
|
10601
|
+
power: (context, input, expAtom) => {
|
|
10602
|
+
return applyMathFunc(Math.pow, context, input, expAtom);
|
|
10395
10603
|
},
|
|
10396
10604
|
/**
|
|
10397
10605
|
* Rounds the decimal to the nearest whole number using a traditional round (i.e. 0.5 or higher will round to 1). If specified, the precision argument determines the decimal place at which the rounding will occur. If not specified, the rounding will default to 0 decimal places.
|
|
@@ -10405,12 +10613,12 @@
|
|
|
10405
10613
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10406
10614
|
*
|
|
10407
10615
|
* See: https://hl7.org/fhirpath/#roundprecision-integer-decimal
|
|
10408
|
-
*
|
|
10616
|
+
* @param context The evaluation context.
|
|
10409
10617
|
* @param input The input collection.
|
|
10410
10618
|
* @returns A collection containing the result.
|
|
10411
10619
|
*/
|
|
10412
|
-
round: (input) => {
|
|
10413
|
-
return applyMathFunc(Math.round, input);
|
|
10620
|
+
round: (context, input) => {
|
|
10621
|
+
return applyMathFunc(Math.round, context, input);
|
|
10414
10622
|
},
|
|
10415
10623
|
/**
|
|
10416
10624
|
* Returns the square root of the input number as a Decimal.
|
|
@@ -10424,12 +10632,12 @@
|
|
|
10424
10632
|
* Note that this function is equivalent to raising a number of the power of 0.5 using the power() function.
|
|
10425
10633
|
*
|
|
10426
10634
|
* See: https://hl7.org/fhirpath/#sqrt-decimal
|
|
10427
|
-
*
|
|
10635
|
+
* @param context The evaluation context.
|
|
10428
10636
|
* @param input The input collection.
|
|
10429
10637
|
* @returns A collection containing the result.
|
|
10430
10638
|
*/
|
|
10431
|
-
sqrt: (input) => {
|
|
10432
|
-
return applyMathFunc(Math.sqrt, input);
|
|
10639
|
+
sqrt: (context, input) => {
|
|
10640
|
+
return applyMathFunc(Math.sqrt, context, input);
|
|
10433
10641
|
},
|
|
10434
10642
|
/**
|
|
10435
10643
|
* Returns the integer portion of the input.
|
|
@@ -10439,12 +10647,12 @@
|
|
|
10439
10647
|
* If the input collection contains multiple items, the evaluation of the expression will end and signal an error to the calling environment.
|
|
10440
10648
|
*
|
|
10441
10649
|
* See: https://hl7.org/fhirpath/#truncate-integer
|
|
10442
|
-
*
|
|
10650
|
+
* @param context The evaluation context.
|
|
10443
10651
|
* @param input The input collection.
|
|
10444
10652
|
* @returns A collection containing the result.
|
|
10445
10653
|
*/
|
|
10446
|
-
truncate: (input) => {
|
|
10447
|
-
return applyMathFunc((x) => x | 0, input);
|
|
10654
|
+
truncate: (context, input) => {
|
|
10655
|
+
return applyMathFunc((x) => x | 0, context, input);
|
|
10448
10656
|
},
|
|
10449
10657
|
/*
|
|
10450
10658
|
* 5.8. Tree navigation
|
|
@@ -10465,11 +10673,12 @@
|
|
|
10465
10673
|
* function unchanged.
|
|
10466
10674
|
*
|
|
10467
10675
|
* See: https://hl7.org/fhirpath/#tracename-string-projection-expression-collection
|
|
10468
|
-
*
|
|
10676
|
+
* @param context The evaluation context.
|
|
10469
10677
|
* @param input The input collection.
|
|
10470
10678
|
* @param nameAtom The log name.
|
|
10679
|
+
* @returns The input collection.
|
|
10471
10680
|
*/
|
|
10472
|
-
trace: (input, nameAtom) => {
|
|
10681
|
+
trace: (context, input, nameAtom) => {
|
|
10473
10682
|
console.log('trace', input, nameAtom);
|
|
10474
10683
|
return input;
|
|
10475
10684
|
},
|
|
@@ -10477,6 +10686,7 @@
|
|
|
10477
10686
|
* Returns the current date and time, including timezone offset.
|
|
10478
10687
|
*
|
|
10479
10688
|
* See: https://hl7.org/fhirpath/#now-datetime
|
|
10689
|
+
* @returns The current dateTime.
|
|
10480
10690
|
*/
|
|
10481
10691
|
now: () => {
|
|
10482
10692
|
return [{ type: exports.PropertyType.dateTime, value: new Date().toISOString() }];
|
|
@@ -10485,6 +10695,7 @@
|
|
|
10485
10695
|
* Returns the current time.
|
|
10486
10696
|
*
|
|
10487
10697
|
* See: https://hl7.org/fhirpath/#timeofday-time
|
|
10698
|
+
* @returns The current time string.
|
|
10488
10699
|
*/
|
|
10489
10700
|
timeOfDay: () => {
|
|
10490
10701
|
return [{ type: exports.PropertyType.time, value: new Date().toISOString().substring(11) }];
|
|
@@ -10493,6 +10704,7 @@
|
|
|
10493
10704
|
* Returns the current date.
|
|
10494
10705
|
*
|
|
10495
10706
|
* See: https://hl7.org/fhirpath/#today-date
|
|
10707
|
+
* @returns The current date string.
|
|
10496
10708
|
*/
|
|
10497
10709
|
today: () => {
|
|
10498
10710
|
return [{ type: exports.PropertyType.date, value: new Date().toISOString().substring(0, 10) }];
|
|
@@ -10504,17 +10716,23 @@
|
|
|
10504
10716
|
*
|
|
10505
10717
|
* IBM FHIR issue: https://github.com/IBM/FHIR/issues/1014
|
|
10506
10718
|
* IBM FHIR PR: https://github.com/IBM/FHIR/pull/1023
|
|
10719
|
+
* @param context The evaluation context.
|
|
10720
|
+
* @param input The input collection.
|
|
10721
|
+
* @param startAtom The start date/time.
|
|
10722
|
+
* @param endAtom The end date/time.
|
|
10723
|
+
* @param unitsAtom Which units to return ("years", "months", or "days").
|
|
10724
|
+
* @returns The Quantity of time between the two dates.
|
|
10507
10725
|
*/
|
|
10508
|
-
between: (input, startAtom, endAtom, unitsAtom) => {
|
|
10509
|
-
const startDate = functions.toDateTime(startAtom.eval(input));
|
|
10726
|
+
between: (context, input, startAtom, endAtom, unitsAtom) => {
|
|
10727
|
+
const startDate = functions.toDateTime(context, startAtom.eval(context, input));
|
|
10510
10728
|
if (startDate.length === 0) {
|
|
10511
10729
|
throw new Error('Invalid start date');
|
|
10512
10730
|
}
|
|
10513
|
-
const endDate = functions.toDateTime(endAtom.eval(input));
|
|
10731
|
+
const endDate = functions.toDateTime(context, endAtom.eval(context, input));
|
|
10514
10732
|
if (endDate.length === 0) {
|
|
10515
10733
|
throw new Error('Invalid end date');
|
|
10516
10734
|
}
|
|
10517
|
-
const unit = unitsAtom.eval(input)[0]?.value;
|
|
10735
|
+
const unit = unitsAtom.eval(context, input)[0]?.value;
|
|
10518
10736
|
if (unit !== 'years' && unit !== 'months' && unit !== 'days') {
|
|
10519
10737
|
throw new Error('Invalid units');
|
|
10520
10738
|
}
|
|
@@ -10532,12 +10750,12 @@
|
|
|
10532
10750
|
* For implementations with compile-time typing, this requires special-case
|
|
10533
10751
|
* handling when processing the argument to treat it as a type specifier rather
|
|
10534
10752
|
* than an identifier expression:
|
|
10535
|
-
*
|
|
10536
|
-
* @param input
|
|
10537
|
-
* @param typeAtom
|
|
10538
|
-
* @returns
|
|
10753
|
+
* @param _context The evaluation context.
|
|
10754
|
+
* @param input The input collection.
|
|
10755
|
+
* @param typeAtom The desired type.
|
|
10756
|
+
* @returns True if the input element is of the desired type.
|
|
10539
10757
|
*/
|
|
10540
|
-
is: (input, typeAtom) => {
|
|
10758
|
+
is: (_context, input, typeAtom) => {
|
|
10541
10759
|
let typeName = '';
|
|
10542
10760
|
if (typeAtom instanceof SymbolAtom) {
|
|
10543
10761
|
typeName = typeAtom.name;
|
|
@@ -10557,12 +10775,12 @@
|
|
|
10557
10775
|
* 6.5.3. not() : Boolean
|
|
10558
10776
|
*
|
|
10559
10777
|
* Returns true if the input collection evaluates to false, and false if it evaluates to true. Otherwise, the result is empty ({ }):
|
|
10560
|
-
*
|
|
10561
|
-
* @param input
|
|
10562
|
-
* @returns
|
|
10778
|
+
* @param context The evaluation context.
|
|
10779
|
+
* @param input The input collection.
|
|
10780
|
+
* @returns True if the input evaluates to false.
|
|
10563
10781
|
*/
|
|
10564
|
-
not: (input) => {
|
|
10565
|
-
return functions.toBoolean(input).map((value) => ({ type: exports.PropertyType.boolean, value: !value.value }));
|
|
10782
|
+
not: (context, input) => {
|
|
10783
|
+
return functions.toBoolean(context, input).map((value) => ({ type: exports.PropertyType.boolean, value: !value.value }));
|
|
10566
10784
|
},
|
|
10567
10785
|
/*
|
|
10568
10786
|
* Additional functions
|
|
@@ -10571,10 +10789,11 @@
|
|
|
10571
10789
|
/**
|
|
10572
10790
|
* For each item in the collection, if it is a string that is a uri (or canonical or url), locate the target of the reference, and add it to the resulting collection. If the item does not resolve to a resource, the item is ignored and nothing is added to the output collection.
|
|
10573
10791
|
* The items in the collection may also represent a Reference, in which case the Reference.reference is resolved.
|
|
10792
|
+
* @param _context The evaluation context.
|
|
10574
10793
|
* @param input The input collection.
|
|
10575
|
-
* @returns
|
|
10794
|
+
* @returns The resolved resource.
|
|
10576
10795
|
*/
|
|
10577
|
-
resolve: (input) => {
|
|
10796
|
+
resolve: (_context, input) => {
|
|
10578
10797
|
return input
|
|
10579
10798
|
.map((e) => {
|
|
10580
10799
|
const value = e.value;
|
|
@@ -10608,10 +10827,11 @@
|
|
|
10608
10827
|
},
|
|
10609
10828
|
/**
|
|
10610
10829
|
* The as operator can be used to treat a value as a specific type.
|
|
10830
|
+
* @param _context The evaluation context.
|
|
10611
10831
|
* @param input The input value.
|
|
10612
10832
|
* @returns The value as the specific type.
|
|
10613
10833
|
*/
|
|
10614
|
-
as: (input) => {
|
|
10834
|
+
as: (_context, input) => {
|
|
10615
10835
|
return input;
|
|
10616
10836
|
},
|
|
10617
10837
|
/*
|
|
@@ -10627,11 +10847,11 @@
|
|
|
10627
10847
|
* https://hl7.org/fhirpath/modelinfo.xsd
|
|
10628
10848
|
*
|
|
10629
10849
|
* See: https://hl7.org/fhirpath/#model-information
|
|
10630
|
-
*
|
|
10850
|
+
* @param _context The evaluation context.
|
|
10631
10851
|
* @param input The input collection.
|
|
10632
|
-
* @returns
|
|
10852
|
+
* @returns The type of the input value.
|
|
10633
10853
|
*/
|
|
10634
|
-
type: (input) => {
|
|
10854
|
+
type: (_context, input) => {
|
|
10635
10855
|
return input.map(({ value }) => {
|
|
10636
10856
|
if (typeof value === 'boolean') {
|
|
10637
10857
|
return { type: exports.PropertyType.BackboneElement, value: { namespace: 'System', name: 'Boolean' } };
|
|
@@ -10648,8 +10868,8 @@
|
|
|
10648
10868
|
return { type: exports.PropertyType.BackboneElement, value: null };
|
|
10649
10869
|
});
|
|
10650
10870
|
},
|
|
10651
|
-
conformsTo: (input, systemAtom) => {
|
|
10652
|
-
const system = systemAtom.eval(input)[0].value;
|
|
10871
|
+
conformsTo: (context, input, systemAtom) => {
|
|
10872
|
+
const system = systemAtom.eval(context, input)[0].value;
|
|
10653
10873
|
if (!system.startsWith('http://hl7.org/fhir/StructureDefinition/')) {
|
|
10654
10874
|
throw new Error('Expected a StructureDefinition URL');
|
|
10655
10875
|
}
|
|
@@ -10663,7 +10883,7 @@
|
|
|
10663
10883
|
/*
|
|
10664
10884
|
* Helper utilities
|
|
10665
10885
|
*/
|
|
10666
|
-
function applyStringFunc(func, input, ...argsAtoms) {
|
|
10886
|
+
function applyStringFunc(func, context, input, ...argsAtoms) {
|
|
10667
10887
|
if (input.length === 0) {
|
|
10668
10888
|
return [];
|
|
10669
10889
|
}
|
|
@@ -10671,7 +10891,7 @@
|
|
|
10671
10891
|
if (typeof value !== 'string') {
|
|
10672
10892
|
throw new Error('String function cannot be called with non-string');
|
|
10673
10893
|
}
|
|
10674
|
-
const result = func(value, ...argsAtoms.map((atom) => atom && atom.eval(input)?.[0]?.value));
|
|
10894
|
+
const result = func(value, ...argsAtoms.map((atom) => atom && atom.eval(context, input)?.[0]?.value));
|
|
10675
10895
|
if (result === undefined) {
|
|
10676
10896
|
return [];
|
|
10677
10897
|
}
|
|
@@ -10680,7 +10900,7 @@
|
|
|
10680
10900
|
}
|
|
10681
10901
|
return [toTypedValue(result)];
|
|
10682
10902
|
}
|
|
10683
|
-
function applyMathFunc(func, input, ...argsAtoms) {
|
|
10903
|
+
function applyMathFunc(func, context, input, ...argsAtoms) {
|
|
10684
10904
|
if (input.length === 0) {
|
|
10685
10905
|
return [];
|
|
10686
10906
|
}
|
|
@@ -10690,7 +10910,7 @@
|
|
|
10690
10910
|
if (typeof numberInput !== 'number') {
|
|
10691
10911
|
throw new Error('Math function cannot be called with non-number');
|
|
10692
10912
|
}
|
|
10693
|
-
const result = func(numberInput, ...argsAtoms.map((atom) => atom.eval(input)?.[0]?.value));
|
|
10913
|
+
const result = func(numberInput, ...argsAtoms.map((atom) => atom.eval(context, input)?.[0]?.value));
|
|
10694
10914
|
const type = quantity ? exports.PropertyType.Quantity : input[0].type;
|
|
10695
10915
|
const returnValue = quantity ? { ...value, value: result } : result;
|
|
10696
10916
|
return [{ type, value: returnValue }];
|
|
@@ -10712,13 +10932,13 @@
|
|
|
10712
10932
|
this.original = original;
|
|
10713
10933
|
this.child = child;
|
|
10714
10934
|
}
|
|
10715
|
-
eval(context) {
|
|
10935
|
+
eval(context, input) {
|
|
10716
10936
|
try {
|
|
10717
|
-
if (
|
|
10718
|
-
return
|
|
10937
|
+
if (input.length > 0) {
|
|
10938
|
+
return input.map((e) => this.child.eval(context, [e])).flat();
|
|
10719
10939
|
}
|
|
10720
10940
|
else {
|
|
10721
|
-
return this.child.eval([]);
|
|
10941
|
+
return this.child.eval(context, []);
|
|
10722
10942
|
}
|
|
10723
10943
|
}
|
|
10724
10944
|
catch (error) {
|
|
@@ -10748,11 +10968,18 @@
|
|
|
10748
10968
|
constructor(name) {
|
|
10749
10969
|
this.name = name;
|
|
10750
10970
|
}
|
|
10751
|
-
eval(context) {
|
|
10971
|
+
eval(context, input) {
|
|
10752
10972
|
if (this.name === '$this') {
|
|
10753
|
-
return
|
|
10973
|
+
return input;
|
|
10974
|
+
}
|
|
10975
|
+
if (this.name.startsWith('%')) {
|
|
10976
|
+
const symbol = context.variables[this.name.slice(1)];
|
|
10977
|
+
if (!symbol) {
|
|
10978
|
+
throw new Error(`Undefined variable ${this.name}`);
|
|
10979
|
+
}
|
|
10980
|
+
return [symbol];
|
|
10754
10981
|
}
|
|
10755
|
-
return
|
|
10982
|
+
return input.flatMap((e) => this.evalValue(e)).filter((e) => e?.value !== undefined);
|
|
10756
10983
|
}
|
|
10757
10984
|
evalValue(typedValue) {
|
|
10758
10985
|
const input = typedValue.value;
|
|
@@ -10781,8 +11008,8 @@
|
|
|
10781
11008
|
super(operator, child);
|
|
10782
11009
|
this.impl = impl;
|
|
10783
11010
|
}
|
|
10784
|
-
eval(context) {
|
|
10785
|
-
return this.impl(this.child.eval(context));
|
|
11011
|
+
eval(context, input) {
|
|
11012
|
+
return this.impl(this.child.eval(context, input));
|
|
10786
11013
|
}
|
|
10787
11014
|
toString() {
|
|
10788
11015
|
return this.child.toString();
|
|
@@ -10792,8 +11019,8 @@
|
|
|
10792
11019
|
constructor(left, right) {
|
|
10793
11020
|
super('as', left, right);
|
|
10794
11021
|
}
|
|
10795
|
-
eval(context) {
|
|
10796
|
-
return functions.ofType(this.left.eval(context), this.right);
|
|
11022
|
+
eval(context, input) {
|
|
11023
|
+
return functions.ofType(context, this.left.eval(context, input), this.right);
|
|
10797
11024
|
}
|
|
10798
11025
|
}
|
|
10799
11026
|
class ArithemticOperatorAtom extends InfixOperatorAtom {
|
|
@@ -10801,12 +11028,12 @@
|
|
|
10801
11028
|
super(operator, left, right);
|
|
10802
11029
|
this.impl = impl;
|
|
10803
11030
|
}
|
|
10804
|
-
eval(context) {
|
|
10805
|
-
const leftEvalResult = this.left.eval(context);
|
|
11031
|
+
eval(context, input) {
|
|
11032
|
+
const leftEvalResult = this.left.eval(context, input);
|
|
10806
11033
|
if (leftEvalResult.length !== 1) {
|
|
10807
11034
|
return [];
|
|
10808
11035
|
}
|
|
10809
|
-
const rightEvalResult = this.right.eval(context);
|
|
11036
|
+
const rightEvalResult = this.right.eval(context, input);
|
|
10810
11037
|
if (rightEvalResult.length !== 1) {
|
|
10811
11038
|
return [];
|
|
10812
11039
|
}
|
|
@@ -10830,9 +11057,9 @@
|
|
|
10830
11057
|
constructor(left, right) {
|
|
10831
11058
|
super('&', left, right);
|
|
10832
11059
|
}
|
|
10833
|
-
eval(context) {
|
|
10834
|
-
const leftValue = this.left.eval(context);
|
|
10835
|
-
const rightValue = this.right.eval(context);
|
|
11060
|
+
eval(context, input) {
|
|
11061
|
+
const leftValue = this.left.eval(context, input);
|
|
11062
|
+
const rightValue = this.right.eval(context, input);
|
|
10836
11063
|
const result = [...leftValue, ...rightValue];
|
|
10837
11064
|
if (result.length > 0 && result.every((e) => typeof e.value === 'string')) {
|
|
10838
11065
|
return [{ type: exports.PropertyType.string, value: result.map((e) => e.value).join('') }];
|
|
@@ -10844,9 +11071,9 @@
|
|
|
10844
11071
|
constructor(left, right) {
|
|
10845
11072
|
super('contains', left, right);
|
|
10846
11073
|
}
|
|
10847
|
-
eval(context) {
|
|
10848
|
-
const leftValue = this.left.eval(context);
|
|
10849
|
-
const rightValue = this.right.eval(context);
|
|
11074
|
+
eval(context, input) {
|
|
11075
|
+
const leftValue = this.left.eval(context, input);
|
|
11076
|
+
const rightValue = this.right.eval(context, input);
|
|
10850
11077
|
return booleanToTypedValue(leftValue.some((e) => e.value === rightValue[0].value));
|
|
10851
11078
|
}
|
|
10852
11079
|
}
|
|
@@ -10854,9 +11081,9 @@
|
|
|
10854
11081
|
constructor(left, right) {
|
|
10855
11082
|
super('in', left, right);
|
|
10856
11083
|
}
|
|
10857
|
-
eval(context) {
|
|
10858
|
-
const leftValue = this.left.eval(context);
|
|
10859
|
-
const rightValue = this.right.eval(context);
|
|
11084
|
+
eval(context, input) {
|
|
11085
|
+
const leftValue = this.left.eval(context, input);
|
|
11086
|
+
const rightValue = this.right.eval(context, input);
|
|
10860
11087
|
return booleanToTypedValue(rightValue.some((e) => e.value === leftValue[0].value));
|
|
10861
11088
|
}
|
|
10862
11089
|
}
|
|
@@ -10864,8 +11091,8 @@
|
|
|
10864
11091
|
constructor(left, right) {
|
|
10865
11092
|
super('.', left, right);
|
|
10866
11093
|
}
|
|
10867
|
-
eval(context) {
|
|
10868
|
-
return this.right.eval(this.left.eval(context));
|
|
11094
|
+
eval(context, input) {
|
|
11095
|
+
return this.right.eval(context, this.left.eval(context, input));
|
|
10869
11096
|
}
|
|
10870
11097
|
toString() {
|
|
10871
11098
|
return `${this.left.toString()}.${this.right.toString()}`;
|
|
@@ -10875,9 +11102,9 @@
|
|
|
10875
11102
|
constructor(left, right) {
|
|
10876
11103
|
super('|', left, right);
|
|
10877
11104
|
}
|
|
10878
|
-
eval(context) {
|
|
10879
|
-
const leftResult = this.left.eval(context);
|
|
10880
|
-
const rightResult = this.right.eval(context);
|
|
11105
|
+
eval(context, input) {
|
|
11106
|
+
const leftResult = this.left.eval(context, input);
|
|
11107
|
+
const rightResult = this.right.eval(context, input);
|
|
10881
11108
|
return removeDuplicates([...leftResult, ...rightResult]);
|
|
10882
11109
|
}
|
|
10883
11110
|
}
|
|
@@ -10885,9 +11112,9 @@
|
|
|
10885
11112
|
constructor(left, right) {
|
|
10886
11113
|
super('=', left, right);
|
|
10887
11114
|
}
|
|
10888
|
-
eval(context) {
|
|
10889
|
-
const leftValue = this.left.eval(context);
|
|
10890
|
-
const rightValue = this.right.eval(context);
|
|
11115
|
+
eval(context, input) {
|
|
11116
|
+
const leftValue = this.left.eval(context, input);
|
|
11117
|
+
const rightValue = this.right.eval(context, input);
|
|
10891
11118
|
return fhirPathArrayEquals(leftValue, rightValue);
|
|
10892
11119
|
}
|
|
10893
11120
|
}
|
|
@@ -10895,9 +11122,9 @@
|
|
|
10895
11122
|
constructor(left, right) {
|
|
10896
11123
|
super('!=', left, right);
|
|
10897
11124
|
}
|
|
10898
|
-
eval(context) {
|
|
10899
|
-
const leftValue = this.left.eval(context);
|
|
10900
|
-
const rightValue = this.right.eval(context);
|
|
11125
|
+
eval(context, input) {
|
|
11126
|
+
const leftValue = this.left.eval(context, input);
|
|
11127
|
+
const rightValue = this.right.eval(context, input);
|
|
10901
11128
|
return fhirPathNot(fhirPathArrayEquals(leftValue, rightValue));
|
|
10902
11129
|
}
|
|
10903
11130
|
}
|
|
@@ -10905,9 +11132,9 @@
|
|
|
10905
11132
|
constructor(left, right) {
|
|
10906
11133
|
super('~', left, right);
|
|
10907
11134
|
}
|
|
10908
|
-
eval(context) {
|
|
10909
|
-
const leftValue = this.left.eval(context);
|
|
10910
|
-
const rightValue = this.right.eval(context);
|
|
11135
|
+
eval(context, input) {
|
|
11136
|
+
const leftValue = this.left.eval(context, input);
|
|
11137
|
+
const rightValue = this.right.eval(context, input);
|
|
10911
11138
|
return fhirPathArrayEquivalent(leftValue, rightValue);
|
|
10912
11139
|
}
|
|
10913
11140
|
}
|
|
@@ -10915,9 +11142,9 @@
|
|
|
10915
11142
|
constructor(left, right) {
|
|
10916
11143
|
super('!~', left, right);
|
|
10917
11144
|
}
|
|
10918
|
-
eval(context) {
|
|
10919
|
-
const leftValue = this.left.eval(context);
|
|
10920
|
-
const rightValue = this.right.eval(context);
|
|
11145
|
+
eval(context, input) {
|
|
11146
|
+
const leftValue = this.left.eval(context, input);
|
|
11147
|
+
const rightValue = this.right.eval(context, input);
|
|
10921
11148
|
return fhirPathNot(fhirPathArrayEquivalent(leftValue, rightValue));
|
|
10922
11149
|
}
|
|
10923
11150
|
}
|
|
@@ -10925,8 +11152,8 @@
|
|
|
10925
11152
|
constructor(left, right) {
|
|
10926
11153
|
super('is', left, right);
|
|
10927
11154
|
}
|
|
10928
|
-
eval(context) {
|
|
10929
|
-
const leftValue = this.left.eval(context);
|
|
11155
|
+
eval(context, input) {
|
|
11156
|
+
const leftValue = this.left.eval(context, input);
|
|
10930
11157
|
if (leftValue.length !== 1) {
|
|
10931
11158
|
return [];
|
|
10932
11159
|
}
|
|
@@ -10944,9 +11171,9 @@
|
|
|
10944
11171
|
constructor(left, right) {
|
|
10945
11172
|
super('and', left, right);
|
|
10946
11173
|
}
|
|
10947
|
-
eval(context) {
|
|
10948
|
-
const leftValue = this.left.eval(context);
|
|
10949
|
-
const rightValue = this.right.eval(context);
|
|
11174
|
+
eval(context, input) {
|
|
11175
|
+
const leftValue = this.left.eval(context, input);
|
|
11176
|
+
const rightValue = this.right.eval(context, input);
|
|
10950
11177
|
if (leftValue[0]?.value === true && rightValue[0]?.value === true) {
|
|
10951
11178
|
return booleanToTypedValue(true);
|
|
10952
11179
|
}
|
|
@@ -10960,12 +11187,12 @@
|
|
|
10960
11187
|
constructor(left, right) {
|
|
10961
11188
|
super('or', left, right);
|
|
10962
11189
|
}
|
|
10963
|
-
eval(context) {
|
|
10964
|
-
const leftValue = this.left.eval(context);
|
|
11190
|
+
eval(context, input) {
|
|
11191
|
+
const leftValue = this.left.eval(context, input);
|
|
10965
11192
|
if (toJsBoolean(leftValue)) {
|
|
10966
11193
|
return leftValue;
|
|
10967
11194
|
}
|
|
10968
|
-
const rightValue = this.right.eval(context);
|
|
11195
|
+
const rightValue = this.right.eval(context, input);
|
|
10969
11196
|
if (toJsBoolean(rightValue)) {
|
|
10970
11197
|
return rightValue;
|
|
10971
11198
|
}
|
|
@@ -10982,9 +11209,9 @@
|
|
|
10982
11209
|
constructor(left, right) {
|
|
10983
11210
|
super('xor', left, right);
|
|
10984
11211
|
}
|
|
10985
|
-
eval(context) {
|
|
10986
|
-
const leftResult = this.left.eval(context);
|
|
10987
|
-
const rightResult = this.right.eval(context);
|
|
11212
|
+
eval(context, input) {
|
|
11213
|
+
const leftResult = this.left.eval(context, input);
|
|
11214
|
+
const rightResult = this.right.eval(context, input);
|
|
10988
11215
|
if (leftResult.length === 0 && rightResult.length === 0) {
|
|
10989
11216
|
return [];
|
|
10990
11217
|
}
|
|
@@ -11004,12 +11231,12 @@
|
|
|
11004
11231
|
this.name = name;
|
|
11005
11232
|
this.args = args;
|
|
11006
11233
|
}
|
|
11007
|
-
eval(context) {
|
|
11234
|
+
eval(context, input) {
|
|
11008
11235
|
const impl = functions[this.name];
|
|
11009
11236
|
if (!impl) {
|
|
11010
11237
|
throw new Error('Unrecognized function: ' + this.name);
|
|
11011
11238
|
}
|
|
11012
|
-
return impl(context, ...this.args);
|
|
11239
|
+
return impl(context, input, ...this.args);
|
|
11013
11240
|
}
|
|
11014
11241
|
toString() {
|
|
11015
11242
|
return `${this.name}(${this.args.map((arg) => arg.toString()).join(', ')})`;
|
|
@@ -11020,8 +11247,8 @@
|
|
|
11020
11247
|
this.left = left;
|
|
11021
11248
|
this.expr = expr;
|
|
11022
11249
|
}
|
|
11023
|
-
eval(context) {
|
|
11024
|
-
const evalResult = this.expr.eval(context);
|
|
11250
|
+
eval(context, input) {
|
|
11251
|
+
const evalResult = this.expr.eval(context, input);
|
|
11025
11252
|
if (evalResult.length !== 1) {
|
|
11026
11253
|
return [];
|
|
11027
11254
|
}
|
|
@@ -11029,7 +11256,7 @@
|
|
|
11029
11256
|
if (typeof index !== 'number') {
|
|
11030
11257
|
throw new Error(`Invalid indexer expression: should return integer}`);
|
|
11031
11258
|
}
|
|
11032
|
-
const leftResult = this.left.eval(context);
|
|
11259
|
+
const leftResult = this.left.eval(context, input);
|
|
11033
11260
|
if (!(index in leftResult)) {
|
|
11034
11261
|
return [];
|
|
11035
11262
|
}
|
|
@@ -11173,10 +11400,12 @@
|
|
|
11173
11400
|
* Evaluates a FHIRPath expression against a resource or other object.
|
|
11174
11401
|
* @param expression The FHIRPath expression to parse.
|
|
11175
11402
|
* @param input The resource or object to evaluate the expression against.
|
|
11403
|
+
* @param variables A map of variables for eval input.
|
|
11176
11404
|
* @returns The result of the FHIRPath expression against the resource or object.
|
|
11177
11405
|
*/
|
|
11178
|
-
function evalFhirPathTyped(expression, input) {
|
|
11179
|
-
|
|
11406
|
+
function evalFhirPathTyped(expression, input, variables) {
|
|
11407
|
+
const variableInput = variables ? variables : {};
|
|
11408
|
+
return parseFhirPath(expression).eval({ variables: variableInput }, input);
|
|
11180
11409
|
}
|
|
11181
11410
|
|
|
11182
11411
|
const MAPPING_LANGUAGE_OPERATORS$1 = [...FHIRPATH_OPERATORS, '->', '<<', '>>'];
|
|
@@ -11831,7 +12060,7 @@
|
|
|
11831
12060
|
/**
|
|
11832
12061
|
* Formats a search definition object into a query string.
|
|
11833
12062
|
* Note: The return value does not include the resource type.
|
|
11834
|
-
* @param
|
|
12063
|
+
* @param definition The search definition.
|
|
11835
12064
|
* @returns Formatted URL.
|
|
11836
12065
|
*/
|
|
11837
12066
|
function formatSearchQuery(definition) {
|
|
@@ -12219,7 +12448,7 @@
|
|
|
12219
12448
|
* Returns a formatted string representing the date in ISO-8601 format.
|
|
12220
12449
|
* @param hl7Date Date string.
|
|
12221
12450
|
* @param options Optional configuration Object
|
|
12222
|
-
* @returns
|
|
12451
|
+
* @returns The date in ISO-8601 format.
|
|
12223
12452
|
*/
|
|
12224
12453
|
function parseHl7Date(hl7Date, options) {
|
|
12225
12454
|
if (!hl7Date) {
|
|
@@ -12308,7 +12537,6 @@
|
|
|
12308
12537
|
* const medplum = new MedplumClient();
|
|
12309
12538
|
* await medplum.requestSchema('Patient');
|
|
12310
12539
|
* ```
|
|
12311
|
-
*
|
|
12312
12540
|
* @param resourceType The candidate resource type string.
|
|
12313
12541
|
* @returns True if the resource type is a valid FHIR resource type.
|
|
12314
12542
|
*/
|
|
@@ -12348,9 +12576,7 @@
|
|
|
12348
12576
|
* const medplum = new MedplumClient();
|
|
12349
12577
|
* await medplum.requestSchema('Patient');
|
|
12350
12578
|
* ```
|
|
12351
|
-
*
|
|
12352
12579
|
* @param resourceType The candidate resource type string.
|
|
12353
|
-
* @returns True if the resource type is a valid FHIR resource type.
|
|
12354
12580
|
*/
|
|
12355
12581
|
function validateResourceType(resourceType) {
|
|
12356
12582
|
if (!resourceType) {
|
|
@@ -12390,9 +12616,7 @@
|
|
|
12390
12616
|
* const medplum = new MedplumClient();
|
|
12391
12617
|
* await medplum.requestSchema('Patient');
|
|
12392
12618
|
* ```
|
|
12393
|
-
*
|
|
12394
|
-
* @param resourceType The candidate resource type string.
|
|
12395
|
-
* @returns True if the resource type is a valid FHIR resource type.
|
|
12619
|
+
* @param resource The candidate resource.
|
|
12396
12620
|
*/
|
|
12397
12621
|
function validateResource(resource) {
|
|
12398
12622
|
new FhirSchemaValidator(resource).validate();
|
|
@@ -12555,10 +12779,10 @@
|
|
|
12555
12779
|
* 2) a JSON property with _ prepended to the name of the element, which, if present, contains the value's id and/or extensions
|
|
12556
12780
|
*
|
|
12557
12781
|
* See: https://hl7.org/fhir/json.html#primitive
|
|
12558
|
-
*
|
|
12559
12782
|
* @param path The path to the property
|
|
12560
|
-
* @param key
|
|
12561
|
-
* @param typedValue
|
|
12783
|
+
* @param key The key in the current typed value.
|
|
12784
|
+
* @param typedValue The current typed value.
|
|
12785
|
+
* @returns True if the primitive element is valid.
|
|
12562
12786
|
*/
|
|
12563
12787
|
checkPrimitiveElement(path, key, typedValue) {
|
|
12564
12788
|
// Primitive element starts with underscore
|
|
@@ -12611,7 +12835,6 @@
|
|
|
12611
12835
|
* Recursively checks for null values in an object.
|
|
12612
12836
|
*
|
|
12613
12837
|
* Note that "null" is a special value in JSON that is not allowed in FHIR.
|
|
12614
|
-
*
|
|
12615
12838
|
* @param value Input value of any type.
|
|
12616
12839
|
* @param path Path string to the value for OperationOutcome.
|
|
12617
12840
|
* @param issues Output list of issues.
|
|
@@ -12675,7 +12898,6 @@
|
|
|
12675
12898
|
* 1) The "date" type includes "date", "datetime", and "period".
|
|
12676
12899
|
* 2) The "token" type includes enums and booleans.
|
|
12677
12900
|
* 3) Arrays/multiple values are not reflected at all.
|
|
12678
|
-
*
|
|
12679
12901
|
* @param resourceType The root resource type.
|
|
12680
12902
|
* @param searchParam The search parameter.
|
|
12681
12903
|
* @returns The search parameter type details.
|
|
@@ -12683,18 +12905,18 @@
|
|
|
12683
12905
|
function getSearchParameterDetails(resourceType, searchParam) {
|
|
12684
12906
|
let result = globalSchema.types[resourceType]?.searchParamsDetails?.[searchParam.code];
|
|
12685
12907
|
if (!result) {
|
|
12686
|
-
result =
|
|
12908
|
+
result = buildSearchParameterDetails(resourceType, searchParam);
|
|
12687
12909
|
}
|
|
12688
12910
|
return result;
|
|
12689
12911
|
}
|
|
12690
|
-
function
|
|
12912
|
+
function setSearchParameterDetails(resourceType, code, details) {
|
|
12691
12913
|
const typeSchema = globalSchema.types[resourceType];
|
|
12692
12914
|
if (!typeSchema.searchParamsDetails) {
|
|
12693
12915
|
typeSchema.searchParamsDetails = {};
|
|
12694
12916
|
}
|
|
12695
12917
|
typeSchema.searchParamsDetails[code] = details;
|
|
12696
12918
|
}
|
|
12697
|
-
function
|
|
12919
|
+
function buildSearchParameterDetails(resourceType, searchParam) {
|
|
12698
12920
|
const code = searchParam.code;
|
|
12699
12921
|
const columnName = convertCodeToColumnName(code);
|
|
12700
12922
|
const expression = getExpressionForResourceType(resourceType, searchParam.expression)?.split('.');
|
|
@@ -12736,7 +12958,7 @@
|
|
|
12736
12958
|
}
|
|
12737
12959
|
const type = getSearchParameterType(searchParam, propertyType);
|
|
12738
12960
|
const result = { columnName, type, elementDefinition, array };
|
|
12739
|
-
|
|
12961
|
+
setSearchParameterDetails(resourceType, code, result);
|
|
12740
12962
|
return result;
|
|
12741
12963
|
}
|
|
12742
12964
|
function isBackboneElement(propertyType) {
|
|
@@ -12835,6 +13057,7 @@
|
|
|
12835
13057
|
/**
|
|
12836
13058
|
* Determines if the resource matches the search filter.
|
|
12837
13059
|
* @param resource The resource that was created or updated.
|
|
13060
|
+
* @param searchRequest The search request.
|
|
12838
13061
|
* @param filter One of the filters of a subscription criteria.
|
|
12839
13062
|
* @returns True if the resource satisfies the search filter.
|
|
12840
13063
|
*/
|
|
@@ -13051,8 +13274,10 @@
|
|
|
13051
13274
|
exports.createReference = createReference;
|
|
13052
13275
|
exports.createStructureIssue = createStructureIssue;
|
|
13053
13276
|
exports.created = created;
|
|
13277
|
+
exports.decodeBase64 = decodeBase64;
|
|
13054
13278
|
exports.deepClone = deepClone;
|
|
13055
13279
|
exports.deepEquals = deepEquals$1;
|
|
13280
|
+
exports.encodeBase64 = encodeBase64;
|
|
13056
13281
|
exports.evalFhirPath = evalFhirPath;
|
|
13057
13282
|
exports.evalFhirPathTyped = evalFhirPathTyped;
|
|
13058
13283
|
exports.fhirPathArrayEquals = fhirPathArrayEquals;
|
|
@@ -13131,6 +13356,7 @@
|
|
|
13131
13356
|
exports.normalizeOperationOutcome = normalizeOperationOutcome;
|
|
13132
13357
|
exports.notFound = notFound;
|
|
13133
13358
|
exports.notModified = notModified;
|
|
13359
|
+
exports.operationOutcomeIssueToString = operationOutcomeIssueToString;
|
|
13134
13360
|
exports.operationOutcomeToString = operationOutcomeToString;
|
|
13135
13361
|
exports.parseFhirPath = parseFhirPath;
|
|
13136
13362
|
exports.parseFilterParameter = parseFilterParameter;
|