@nsshunt/stsfhirpg 1.1.7 → 1.2.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/stsfhirpg.cjs +226 -536
- package/dist/stsfhirpg.cjs.map +1 -1
- package/dist/stsfhirpg.mjs +228 -538
- package/dist/stsfhirpg.mjs.map +1 -1
- package/package.json +2 -3
- package/types/fhir-database/dbsearchindex.d.ts +1 -7
- package/types/fhir-database/dbsearchindex.d.ts.map +1 -1
- package/types/fhir-utils/resourceHelper.d.ts +8 -1
- package/types/fhir-utils/resourceHelper.d.ts.map +1 -1
- package/types/index.d.ts +0 -2
- package/types/index.d.ts.map +1 -1
- package/types/redisDistributedLock.d.ts +0 -36
- package/types/redisDistributedLock.d.ts.map +0 -1
- package/types/searchParameterManager.d.ts +0 -13
- package/types/searchParameterManager.d.ts.map +0 -1
package/dist/stsfhirpg.cjs
CHANGED
|
@@ -15,7 +15,6 @@ const require$$1$2 = require("tls");
|
|
|
15
15
|
const require$$0$7 = require("path");
|
|
16
16
|
const require$$0$6 = require("stream");
|
|
17
17
|
const require$$0$5 = require("buffer");
|
|
18
|
-
const redis = require("redis");
|
|
19
18
|
class LuxonError extends Error {
|
|
20
19
|
}
|
|
21
20
|
class InvalidDateTimeError extends LuxonError {
|
|
@@ -7026,7 +7025,8 @@ class ResourceHelper {
|
|
|
7026
7025
|
this.#definitions = {
|
|
7027
7026
|
resources: {},
|
|
7028
7027
|
types: {},
|
|
7029
|
-
|
|
7028
|
+
searchParametersByUrl: {},
|
|
7029
|
+
searchParametersByResourceType: {}
|
|
7030
7030
|
};
|
|
7031
7031
|
}
|
|
7032
7032
|
__resources.entry.forEach((entry) => {
|
|
@@ -7043,25 +7043,22 @@ class ResourceHelper {
|
|
|
7043
7043
|
}
|
|
7044
7044
|
});
|
|
7045
7045
|
__searchParams.entry.forEach((entry) => {
|
|
7046
|
-
this.#definitions.
|
|
7046
|
+
this.#definitions.searchParametersByUrl[entry.fullUrl] = entry.resource;
|
|
7047
7047
|
});
|
|
7048
|
+
this._LoadSearchParameters();
|
|
7048
7049
|
return this.#definitions;
|
|
7049
7050
|
};
|
|
7050
|
-
|
|
7051
|
+
get definitions() {
|
|
7051
7052
|
if (!this.#definitions) {
|
|
7052
7053
|
this.#LoadDefinitions();
|
|
7053
7054
|
}
|
|
7054
|
-
|
|
7055
|
-
|
|
7056
|
-
|
|
7057
|
-
|
|
7058
|
-
return [];
|
|
7055
|
+
return this.#definitions;
|
|
7056
|
+
}
|
|
7057
|
+
GetType = (typeName) => {
|
|
7058
|
+
return this.definitions.types[typeName];
|
|
7059
7059
|
};
|
|
7060
7060
|
GetResource = (resourceType) => {
|
|
7061
|
-
|
|
7062
|
-
this.#LoadDefinitions();
|
|
7063
|
-
}
|
|
7064
|
-
return this.#definitions.resources[resourceType];
|
|
7061
|
+
return this.definitions.resources[resourceType];
|
|
7065
7062
|
};
|
|
7066
7063
|
GetResourceField = (resourceType, fieldPath) => {
|
|
7067
7064
|
const resource = this.GetResource(resourceType);
|
|
@@ -7074,22 +7071,215 @@ class ResourceHelper {
|
|
|
7074
7071
|
}
|
|
7075
7072
|
};
|
|
7076
7073
|
GetSearchParam = (url) => {
|
|
7077
|
-
|
|
7078
|
-
this.#LoadDefinitions();
|
|
7079
|
-
}
|
|
7080
|
-
return this.#definitions.searchParameters[url];
|
|
7074
|
+
return this.definitions.searchParametersByUrl[url];
|
|
7081
7075
|
};
|
|
7082
7076
|
GetSearchParams = () => {
|
|
7083
|
-
|
|
7084
|
-
this.#LoadDefinitions();
|
|
7085
|
-
}
|
|
7086
|
-
return this.#definitions.searchParameters;
|
|
7077
|
+
return this.definitions.searchParametersByUrl;
|
|
7087
7078
|
};
|
|
7088
7079
|
GetSearchParamsByResource = (resource) => {
|
|
7089
|
-
|
|
7090
|
-
|
|
7080
|
+
return Object.values(this.definitions.searchParametersByUrl).filter((sp) => sp.base.includes(resource)).map((sp) => sp);
|
|
7081
|
+
};
|
|
7082
|
+
// ------------------------------------------------------------------------------------------------------------------
|
|
7083
|
+
// Remove ( ) when either are present
|
|
7084
|
+
#RemoveOuterParentheses = (input) => {
|
|
7085
|
+
return input.replace(/^\(|\)$/g, "");
|
|
7086
|
+
};
|
|
7087
|
+
// Remove ( ) only when both are present
|
|
7088
|
+
#RemoveSurroundingParentheses = (input) => {
|
|
7089
|
+
return input.replace(/^\((.*)\)$/, "$1").trim();
|
|
7090
|
+
};
|
|
7091
|
+
/*
|
|
7092
|
+
|
|
7093
|
+
NamingSystem derived-from reference NamingSystem.relatedArtifact.where(type='derived-from').resource
|
|
7094
|
+
|
|
7095
|
+
NamingSystem predecessor reference NamingSystem.relatedArtifact.where(type='predecessor').resource
|
|
7096
|
+
|
|
7097
|
+
ClinicalUseDefinition product reference ClinicalUseDefinition.subject.where(resolve() is MedicinalProductDefinition)
|
|
7098
|
+
|
|
7099
|
+
OrganizationAffiliation email token OrganizationAffiliation.contact.telecom.where(system='email')
|
|
7100
|
+
OrganizationAffiliation phone token OrganizationAffiliation.contact.telecom.where(system='phone')
|
|
7101
|
+
|
|
7102
|
+
PackagedProductDefinition biological reference PackagedProductDefinition.packaging.containedItem.item.reference
|
|
7103
|
+
PackagedProductDefinition contained-item reference PackagedProductDefinition.packaging.containedItem.item.reference
|
|
7104
|
+
|
|
7105
|
+
Patient deceased token Patient.deceased.exists() and Patient.deceased != false
|
|
7106
|
+
Practitioner deceased token Practitioner.deceased.exists() and Practitioner.deceased != false
|
|
7107
|
+
|
|
7108
|
+
Location contains special Location.extension('http://hl7.org/fhir/StructureDefinition/location-boundary-geojson').value
|
|
7109
|
+
|
|
7110
|
+
QuestionnaireResponse item-subject reference QuestionnaireResponse.item.where(extension('http://hl7.org/fhir/StructureDefinition/questionnaireresponse-isSubject').exists()).answer.valueReference
|
|
7111
|
+
*/
|
|
7112
|
+
ProcessExpressions = (resourceName, SP_EXPRESSION) => {
|
|
7113
|
+
let expressions = [];
|
|
7114
|
+
expressions = SP_EXPRESSION.split("|").map((e) => e.trim());
|
|
7115
|
+
expressions = expressions.map((e) => this.#RemoveSurroundingParentheses(e).trim());
|
|
7116
|
+
if (resourceName !== "") {
|
|
7117
|
+
expressions = expressions.filter((e) => e.split(".")[0].trim().localeCompare(resourceName) === 0);
|
|
7091
7118
|
}
|
|
7092
|
-
|
|
7119
|
+
let original_expressions = [...expressions];
|
|
7120
|
+
expressions = expressions.map((e) => {
|
|
7121
|
+
let capturedTypeOf = void 0;
|
|
7122
|
+
return {
|
|
7123
|
+
path: e.replace(
|
|
7124
|
+
/\.ofType\(([^)]+)\)/g,
|
|
7125
|
+
(_, typeName) => {
|
|
7126
|
+
capturedTypeOf = true;
|
|
7127
|
+
return typeName.charAt(0).toUpperCase() + typeName.slice(1);
|
|
7128
|
+
}
|
|
7129
|
+
),
|
|
7130
|
+
typeOf: capturedTypeOf
|
|
7131
|
+
};
|
|
7132
|
+
});
|
|
7133
|
+
expressions.forEach((expression) => {
|
|
7134
|
+
try {
|
|
7135
|
+
const sp = expression;
|
|
7136
|
+
if (sp.path.indexOf("exists()") >= 0) {
|
|
7137
|
+
const parts = sp.path.split(" ");
|
|
7138
|
+
const i = parts[0].indexOf("exists()");
|
|
7139
|
+
if (i >= 0) {
|
|
7140
|
+
let fieldExistsEx = parts[0].substring(0, i - 1);
|
|
7141
|
+
let op = parts[1];
|
|
7142
|
+
let fieldTestEx = parts[2];
|
|
7143
|
+
let comparator = parts[3];
|
|
7144
|
+
let value = parts[4];
|
|
7145
|
+
const fieldExistsParts = fieldExistsEx.split(".");
|
|
7146
|
+
let fieldExists = fieldExistsParts.slice(1).join(".");
|
|
7147
|
+
const fieldTestParts = fieldTestEx.split(".");
|
|
7148
|
+
let fieldTest = fieldTestParts.slice(1).join(".");
|
|
7149
|
+
sp.exists = {
|
|
7150
|
+
fieldExists: [`${fieldExists}Boolean`, `${fieldExists}DataTime`],
|
|
7151
|
+
// [x]Boolean or [x]DateTime
|
|
7152
|
+
op,
|
|
7153
|
+
fieldTest: [`${fieldTest}Boolean`, `${fieldTest}DataTime`],
|
|
7154
|
+
comparator,
|
|
7155
|
+
value: [value, void 0]
|
|
7156
|
+
};
|
|
7157
|
+
}
|
|
7158
|
+
}
|
|
7159
|
+
} catch (error) {
|
|
7160
|
+
}
|
|
7161
|
+
});
|
|
7162
|
+
let capturedType;
|
|
7163
|
+
expressions = expressions.map((obj) => {
|
|
7164
|
+
capturedType = void 0;
|
|
7165
|
+
const { path, typeOf, exists } = obj;
|
|
7166
|
+
return {
|
|
7167
|
+
path: path.replace(
|
|
7168
|
+
/\.where\(resolve\(\)\s+is\s+([^)]+)\)/,
|
|
7169
|
+
(_, typeName) => {
|
|
7170
|
+
capturedType = typeName;
|
|
7171
|
+
return "";
|
|
7172
|
+
}
|
|
7173
|
+
),
|
|
7174
|
+
typeOf,
|
|
7175
|
+
reference: capturedType,
|
|
7176
|
+
exists
|
|
7177
|
+
};
|
|
7178
|
+
});
|
|
7179
|
+
let capturedWhere = void 0;
|
|
7180
|
+
expressions = expressions.map((obj) => {
|
|
7181
|
+
capturedWhere = void 0;
|
|
7182
|
+
const { path, reference, typeOf, exists } = obj;
|
|
7183
|
+
const retVal = {
|
|
7184
|
+
path: path.replace(/([^.]+)\.where\(([^=]+)='([^']+)'\)/g, (_, field, subfield, value) => {
|
|
7185
|
+
capturedWhere = { field, subfield, value };
|
|
7186
|
+
return field;
|
|
7187
|
+
}),
|
|
7188
|
+
typeOf,
|
|
7189
|
+
reference,
|
|
7190
|
+
exists
|
|
7191
|
+
};
|
|
7192
|
+
if (capturedWhere) {
|
|
7193
|
+
capturedWhere.full = `${capturedWhere.field}[*].${capturedWhere.subfield}=${capturedWhere.value}`;
|
|
7194
|
+
retVal.where = capturedWhere;
|
|
7195
|
+
}
|
|
7196
|
+
return retVal;
|
|
7197
|
+
});
|
|
7198
|
+
return {
|
|
7199
|
+
expressions,
|
|
7200
|
+
original_expressions
|
|
7201
|
+
};
|
|
7202
|
+
};
|
|
7203
|
+
_LoadSearchParameters = () => {
|
|
7204
|
+
for (const [key, val] of Object.entries(this.GetSearchParams())) {
|
|
7205
|
+
const { id, url, code, base, type, expression, component, target } = val;
|
|
7206
|
+
for (let i = 0; i < base.length; i++) {
|
|
7207
|
+
const resourceName = base[i];
|
|
7208
|
+
if (!this.#definitions?.searchParametersByResourceType[resourceName]) {
|
|
7209
|
+
this.#definitions.searchParametersByResourceType[resourceName] = {
|
|
7210
|
+
resourceName,
|
|
7211
|
+
params: []
|
|
7212
|
+
};
|
|
7213
|
+
}
|
|
7214
|
+
const SP_ID = id;
|
|
7215
|
+
const SP_NAME = code;
|
|
7216
|
+
const SP_TYPE = type;
|
|
7217
|
+
const SP_URL = url;
|
|
7218
|
+
const SP_TARGET = target;
|
|
7219
|
+
let SP_EXPRESSION = expression;
|
|
7220
|
+
let expressions = [];
|
|
7221
|
+
let original_expressions = [];
|
|
7222
|
+
if (SP_EXPRESSION) {
|
|
7223
|
+
const retVal = this.ProcessExpressions(resourceName, SP_EXPRESSION);
|
|
7224
|
+
expressions = retVal.expressions;
|
|
7225
|
+
original_expressions = retVal.original_expressions;
|
|
7226
|
+
}
|
|
7227
|
+
const record = {
|
|
7228
|
+
SP_ID,
|
|
7229
|
+
SP_NAME,
|
|
7230
|
+
SP_TYPE,
|
|
7231
|
+
SP_URL,
|
|
7232
|
+
SP_TARGET,
|
|
7233
|
+
expressions,
|
|
7234
|
+
original_expressions,
|
|
7235
|
+
SP_DEFINITION: this.GetSearchParam(SP_URL)
|
|
7236
|
+
};
|
|
7237
|
+
for (let i2 = 0; i2 < record.expressions.length; i2++) {
|
|
7238
|
+
const rf = this.GetResourceField(resourceName, record.expressions[i2].path);
|
|
7239
|
+
if (rf) {
|
|
7240
|
+
expressions[i2].RES_FIELD = rf;
|
|
7241
|
+
}
|
|
7242
|
+
}
|
|
7243
|
+
if (component) {
|
|
7244
|
+
record.component = [...component];
|
|
7245
|
+
record.component.forEach((c) => {
|
|
7246
|
+
const retVal = this.ProcessExpressions("", c.expression);
|
|
7247
|
+
c.expressions = retVal.expressions;
|
|
7248
|
+
c.original_expressions = retVal.original_expressions;
|
|
7249
|
+
const def = this.GetSearchParam(c.definition);
|
|
7250
|
+
if (def && def.type) {
|
|
7251
|
+
c.type = def.type;
|
|
7252
|
+
}
|
|
7253
|
+
});
|
|
7254
|
+
}
|
|
7255
|
+
this.#definitions.searchParametersByResourceType[resourceName].params.push(record);
|
|
7256
|
+
}
|
|
7257
|
+
}
|
|
7258
|
+
};
|
|
7259
|
+
GetSearchParamFromResourceTypeUrl = (resourceType, url) => {
|
|
7260
|
+
const filterByNameAndUrl = this.definitions.searchParametersByResourceType[resourceType].params.filter((rt) => rt.SP_URL.localeCompare(url) === 0);
|
|
7261
|
+
if (filterByNameAndUrl.length > 0) {
|
|
7262
|
+
return filterByNameAndUrl[0];
|
|
7263
|
+
}
|
|
7264
|
+
};
|
|
7265
|
+
/*
|
|
7266
|
+
GetSearchParamFromResourceType = (resourceType: string, name: string): ISearchParamRecord | undefined => {
|
|
7267
|
+
const filterByName = this.definitions.searchParametersByResourceType[resourceType].params.filter(rt => rt.SP_NAME.localeCompare(name) === 0);
|
|
7268
|
+
if (filterByName.length > 0) {
|
|
7269
|
+
return filterByName[0];
|
|
7270
|
+
}
|
|
7271
|
+
}
|
|
7272
|
+
|
|
7273
|
+
GetPathsFromResourceType = (resourceType: string, name: string): string[] => {
|
|
7274
|
+
const filterByName = this.definitions.searchParametersByResourceType[resourceType].params.filter(rt => rt.SP_NAME.localeCompare(name) === 0);
|
|
7275
|
+
if (filterByName.length > 0) {
|
|
7276
|
+
return filterByName[0].expressions.map(e => e.path)
|
|
7277
|
+
}
|
|
7278
|
+
return [ ];
|
|
7279
|
+
}
|
|
7280
|
+
*/
|
|
7281
|
+
GetSearchParamsFromResourceType = (resourceType) => {
|
|
7282
|
+
return this.definitions.searchParametersByResourceType[resourceType].params;
|
|
7093
7283
|
};
|
|
7094
7284
|
}
|
|
7095
7285
|
var ansiStyles = { exports: {} };
|
|
@@ -10567,7 +10757,7 @@ class DBSearchIndexComposite extends DBSearchIndexBase {
|
|
|
10567
10757
|
searchFieldRecord.component.forEach((searchParamComponentRecord) => {
|
|
10568
10758
|
components.push([]);
|
|
10569
10759
|
const url = searchParamComponentRecord.definition;
|
|
10570
|
-
const sp = searchIndex.GetSearchParamFromResourceTypeUrl(resource.resourceType, url);
|
|
10760
|
+
const sp = searchIndex.resourceHelper.GetSearchParamFromResourceTypeUrl(resource.resourceType, url);
|
|
10571
10761
|
if (this.IsDefined(sp)) {
|
|
10572
10762
|
const tir2 = {
|
|
10573
10763
|
PID: v4(),
|
|
@@ -11222,27 +11412,13 @@ class DBSearchIndex {
|
|
|
11222
11412
|
return [];
|
|
11223
11413
|
}
|
|
11224
11414
|
};
|
|
11225
|
-
ResolveFhirChoiceType = (path) => {
|
|
11226
|
-
const match2 = path.match(/^(.+?)\.ofType\((.+?)\)$/);
|
|
11227
|
-
if (!match2) {
|
|
11228
|
-
return path;
|
|
11229
|
-
}
|
|
11230
|
-
const base = match2[1];
|
|
11231
|
-
const fhirType = match2[2];
|
|
11232
|
-
const capitalizedType = fhirType.charAt(0).toUpperCase() + fhirType.slice(1);
|
|
11233
|
-
return `${base}${capitalizedType}`;
|
|
11234
|
-
};
|
|
11235
11415
|
GetSearchIndexData = (resource) => {
|
|
11236
11416
|
try {
|
|
11237
|
-
const
|
|
11238
|
-
if (!this.#searchParams) {
|
|
11239
|
-
this.LoadSearchParameters();
|
|
11240
|
-
}
|
|
11417
|
+
const searchParamRecords = this.resourceHelper.GetSearchParamsFromResourceType(resource.resourceType);
|
|
11241
11418
|
const searchIndexData = [];
|
|
11242
|
-
for (let i = 0; i <
|
|
11243
|
-
const searchRecord =
|
|
11419
|
+
for (let i = 0; i < searchParamRecords.length; i++) {
|
|
11420
|
+
const searchRecord = searchParamRecords[i];
|
|
11244
11421
|
try {
|
|
11245
|
-
const st2 = performance.now();
|
|
11246
11422
|
const retVal = this.UpdateIndex(resource, searchRecord);
|
|
11247
11423
|
if (retVal && retVal.length > 0) {
|
|
11248
11424
|
searchIndexData.push(...retVal);
|
|
@@ -11257,286 +11433,19 @@ class DBSearchIndex {
|
|
|
11257
11433
|
return [];
|
|
11258
11434
|
}
|
|
11259
11435
|
};
|
|
11260
|
-
GetSearchParamFromResourceTypeUrl = (resourceType, url) => {
|
|
11261
|
-
if (!this.#searchParams) {
|
|
11262
|
-
this.LoadSearchParameters();
|
|
11263
|
-
}
|
|
11264
|
-
const filterByNameAndUrl = this.#searchParams[resourceType].params.filter((rt) => rt.SP_URL.localeCompare(url) === 0);
|
|
11265
|
-
if (filterByNameAndUrl.length > 0) {
|
|
11266
|
-
return filterByNameAndUrl[0];
|
|
11267
|
-
}
|
|
11268
|
-
};
|
|
11269
|
-
GetSearchParamFromResourceType = (resourceType, name) => {
|
|
11270
|
-
if (!this.#searchParams) {
|
|
11271
|
-
this.LoadSearchParameters();
|
|
11272
|
-
}
|
|
11273
|
-
const filterByName = this.#searchParams[resourceType].params.filter((rt) => rt.SP_NAME.localeCompare(name) === 0);
|
|
11274
|
-
if (filterByName.length > 0) {
|
|
11275
|
-
return filterByName[0];
|
|
11276
|
-
}
|
|
11277
|
-
};
|
|
11278
|
-
GetPathsFromResourceType = (resourceType, name) => {
|
|
11279
|
-
if (!this.#searchParams) {
|
|
11280
|
-
this.LoadSearchParameters();
|
|
11281
|
-
}
|
|
11282
|
-
const filterByName = this.#searchParams[resourceType].params.filter((rt) => rt.SP_NAME.localeCompare(name) === 0);
|
|
11283
|
-
if (filterByName.length > 0) {
|
|
11284
|
-
return filterByName[0].expressions.map((e) => e.path);
|
|
11285
|
-
}
|
|
11286
|
-
return [];
|
|
11287
|
-
};
|
|
11288
|
-
// Remove ( ) when either are present
|
|
11289
|
-
#RemoveOuterParentheses = (input) => {
|
|
11290
|
-
return input.replace(/^\(|\)$/g, "");
|
|
11291
|
-
};
|
|
11292
|
-
// Remove ( ) only when both are present
|
|
11293
|
-
#RemoveSurroundingParentheses = (input) => {
|
|
11294
|
-
return input.replace(/^\((.*)\)$/, "$1").trim();
|
|
11295
|
-
};
|
|
11296
11436
|
/*
|
|
11297
|
-
|
|
11298
|
-
|
|
11299
|
-
|
|
11300
|
-
NamingSystem predecessor reference NamingSystem.relatedArtifact.where(type='predecessor').resource
|
|
11301
|
-
|
|
11302
|
-
ClinicalUseDefinition product reference ClinicalUseDefinition.subject.where(resolve() is MedicinalProductDefinition)
|
|
11303
|
-
|
|
11304
|
-
OrganizationAffiliation email token OrganizationAffiliation.contact.telecom.where(system='email')
|
|
11305
|
-
OrganizationAffiliation phone token OrganizationAffiliation.contact.telecom.where(system='phone')
|
|
11306
|
-
|
|
11307
|
-
PackagedProductDefinition biological reference PackagedProductDefinition.packaging.containedItem.item.reference
|
|
11308
|
-
PackagedProductDefinition contained-item reference PackagedProductDefinition.packaging.containedItem.item.reference
|
|
11309
|
-
|
|
11310
|
-
Patient deceased token Patient.deceased.exists() and Patient.deceased != false
|
|
11311
|
-
Practitioner deceased token Practitioner.deceased.exists() and Practitioner.deceased != false
|
|
11312
|
-
|
|
11313
|
-
Location contains special Location.extension('http://hl7.org/fhir/StructureDefinition/location-boundary-geojson').value
|
|
11314
|
-
|
|
11315
|
-
QuestionnaireResponse item-subject reference QuestionnaireResponse.item.where(extension('http://hl7.org/fhir/StructureDefinition/questionnaireresponse-isSubject').exists()).answer.valueReference
|
|
11316
|
-
*/
|
|
11317
|
-
ProcessExpressions = (resourceName, SP_EXPRESSION) => {
|
|
11318
|
-
let expressions = [];
|
|
11319
|
-
expressions = SP_EXPRESSION.split("|").map((e) => e.trim());
|
|
11320
|
-
expressions = expressions.map((e) => this.#RemoveSurroundingParentheses(e).trim());
|
|
11321
|
-
if (resourceName !== "") {
|
|
11322
|
-
expressions = expressions.filter((e) => e.split(".")[0].trim().localeCompare(resourceName) === 0);
|
|
11323
|
-
}
|
|
11324
|
-
let original_expressions = [...expressions];
|
|
11325
|
-
expressions = expressions.map((e) => {
|
|
11326
|
-
let capturedTypeOf = void 0;
|
|
11327
|
-
return {
|
|
11328
|
-
path: e.replace(
|
|
11329
|
-
/\.ofType\(([^)]+)\)/g,
|
|
11330
|
-
(_, typeName) => {
|
|
11331
|
-
capturedTypeOf = true;
|
|
11332
|
-
return typeName.charAt(0).toUpperCase() + typeName.slice(1);
|
|
11333
|
-
}
|
|
11334
|
-
),
|
|
11335
|
-
typeOf: capturedTypeOf
|
|
11336
|
-
};
|
|
11337
|
-
});
|
|
11338
|
-
expressions.forEach((expression) => {
|
|
11339
|
-
try {
|
|
11340
|
-
const sp = expression;
|
|
11341
|
-
if (sp.path.indexOf("exists()") >= 0) {
|
|
11342
|
-
const parts = sp.path.split(" ");
|
|
11343
|
-
const i = parts[0].indexOf("exists()");
|
|
11344
|
-
if (i >= 0) {
|
|
11345
|
-
let fieldExistsEx = parts[0].substring(0, i - 1);
|
|
11346
|
-
let op = parts[1];
|
|
11347
|
-
let fieldTestEx = parts[2];
|
|
11348
|
-
let comparator = parts[3];
|
|
11349
|
-
let value = parts[4];
|
|
11350
|
-
const fieldExistsParts = fieldExistsEx.split(".");
|
|
11351
|
-
let fieldExists = fieldExistsParts.slice(1).join(".");
|
|
11352
|
-
const fieldTestParts = fieldTestEx.split(".");
|
|
11353
|
-
let fieldTest = fieldTestParts.slice(1).join(".");
|
|
11354
|
-
sp.exists = {
|
|
11355
|
-
fieldExists: [`${fieldExists}Boolean`, `${fieldExists}DataTime`],
|
|
11356
|
-
// [x]Boolean or [x]DateTime
|
|
11357
|
-
op,
|
|
11358
|
-
fieldTest: [`${fieldTest}Boolean`, `${fieldTest}DataTime`],
|
|
11359
|
-
comparator,
|
|
11360
|
-
value: [value, void 0]
|
|
11361
|
-
};
|
|
11362
|
-
}
|
|
11363
|
-
}
|
|
11364
|
-
} catch (error) {
|
|
11437
|
+
GetSearchParamFromResourceTypeUrl = (resourceType: string, url: string): ISearchParamRecord | undefined => {
|
|
11438
|
+
return this.resourceHelper.GetSearchParamFromResourceTypeUrl(resourceType, url);
|
|
11365
11439
|
}
|
|
11366
|
-
});
|
|
11367
|
-
let capturedType;
|
|
11368
|
-
expressions = expressions.map((obj) => {
|
|
11369
|
-
capturedType = void 0;
|
|
11370
|
-
const { path, typeOf, exists } = obj;
|
|
11371
|
-
return {
|
|
11372
|
-
path: path.replace(
|
|
11373
|
-
/\.where\(resolve\(\)\s+is\s+([^)]+)\)/,
|
|
11374
|
-
(_, typeName) => {
|
|
11375
|
-
capturedType = typeName;
|
|
11376
|
-
return "";
|
|
11377
|
-
}
|
|
11378
|
-
),
|
|
11379
|
-
typeOf,
|
|
11380
|
-
reference: capturedType,
|
|
11381
|
-
exists
|
|
11382
|
-
};
|
|
11383
|
-
});
|
|
11384
|
-
let capturedWhere = void 0;
|
|
11385
|
-
expressions = expressions.map((obj) => {
|
|
11386
|
-
capturedWhere = void 0;
|
|
11387
|
-
const { path, reference, typeOf, exists } = obj;
|
|
11388
|
-
const retVal = {
|
|
11389
|
-
path: path.replace(/([^.]+)\.where\(([^=]+)='([^']+)'\)/g, (_, field, subfield, value) => {
|
|
11390
|
-
capturedWhere = { field, subfield, value };
|
|
11391
|
-
return field;
|
|
11392
|
-
}),
|
|
11393
|
-
typeOf,
|
|
11394
|
-
reference,
|
|
11395
|
-
exists
|
|
11396
|
-
};
|
|
11397
|
-
if (capturedWhere) {
|
|
11398
|
-
capturedWhere.full = `${capturedWhere.field}[*].${capturedWhere.subfield}=${capturedWhere.value}`;
|
|
11399
|
-
retVal.where = capturedWhere;
|
|
11400
|
-
}
|
|
11401
|
-
return retVal;
|
|
11402
|
-
});
|
|
11403
|
-
return {
|
|
11404
|
-
expressions,
|
|
11405
|
-
original_expressions
|
|
11406
|
-
};
|
|
11407
|
-
};
|
|
11408
|
-
LoadSearchParameters = () => {
|
|
11409
|
-
const searchParamData = {};
|
|
11410
|
-
for (const [key, val] of Object.entries(this.resourceHelper.GetSearchParams())) {
|
|
11411
|
-
const { id, url, code, base, type, expression, component, target } = val;
|
|
11412
|
-
for (let i = 0; i < base.length; i++) {
|
|
11413
|
-
const resourceName = base[i];
|
|
11414
|
-
if (!searchParamData[resourceName]) {
|
|
11415
|
-
searchParamData[resourceName] = {
|
|
11416
|
-
resourceName,
|
|
11417
|
-
params: []
|
|
11418
|
-
};
|
|
11419
|
-
}
|
|
11420
|
-
const SP_ID = id;
|
|
11421
|
-
const SP_NAME = code;
|
|
11422
|
-
const SP_TYPE = type;
|
|
11423
|
-
const SP_URL = url;
|
|
11424
|
-
const SP_TARGET = target;
|
|
11425
|
-
let SP_EXPRESSION = expression;
|
|
11426
|
-
let expressions = [];
|
|
11427
|
-
let original_expressions = [];
|
|
11428
|
-
if (SP_EXPRESSION) {
|
|
11429
|
-
const retVal = this.ProcessExpressions(resourceName, SP_EXPRESSION);
|
|
11430
|
-
expressions = retVal.expressions;
|
|
11431
|
-
original_expressions = retVal.original_expressions;
|
|
11432
|
-
}
|
|
11433
|
-
const record = {
|
|
11434
|
-
SP_ID,
|
|
11435
|
-
SP_NAME,
|
|
11436
|
-
SP_TYPE,
|
|
11437
|
-
SP_URL,
|
|
11438
|
-
SP_TARGET,
|
|
11439
|
-
expressions,
|
|
11440
|
-
original_expressions,
|
|
11441
|
-
SP_DEFINITION: this.resourceHelper.GetSearchParam(SP_URL)
|
|
11442
|
-
};
|
|
11443
|
-
for (let i2 = 0; i2 < record.expressions.length; i2++) {
|
|
11444
|
-
const rf = this.resourceHelper.GetResourceField(resourceName, record.expressions[i2].path);
|
|
11445
|
-
if (rf) {
|
|
11446
|
-
expressions[i2].RES_FIELD = rf;
|
|
11447
|
-
}
|
|
11448
|
-
}
|
|
11449
|
-
if (component) {
|
|
11450
|
-
record.component = [...component];
|
|
11451
|
-
record.component.forEach((c) => {
|
|
11452
|
-
const retVal = this.ProcessExpressions("", c.expression);
|
|
11453
|
-
c.expressions = retVal.expressions;
|
|
11454
|
-
c.original_expressions = retVal.original_expressions;
|
|
11455
|
-
const def = this.resourceHelper.GetSearchParam(c.definition);
|
|
11456
|
-
if (def && def.type) {
|
|
11457
|
-
c.type = def.type;
|
|
11458
|
-
}
|
|
11459
|
-
});
|
|
11460
|
-
}
|
|
11461
|
-
searchParamData[resourceName].params.push(record);
|
|
11462
|
-
}
|
|
11463
|
-
}
|
|
11464
|
-
this.#searchParams = searchParamData;
|
|
11465
|
-
return searchParamData;
|
|
11466
|
-
};
|
|
11467
|
-
/*
|
|
11468
|
-
|
|
11469
|
-
|
|
11470
|
-
for (const [resourceName,val] of Object.entries(searchParams)) {
|
|
11471
|
-
|
|
11472
|
-
const patientSearchList: Record<string, any> = (val as any).resourceSpecific;
|
|
11473
|
-
|
|
11474
|
-
for (const [key2,val2] of Object.entries(patientSearchList)) {
|
|
11475
|
-
|
|
11476
|
-
const SP_ID = val2.id;
|
|
11477
|
-
const SP_NAME = key2;
|
|
11478
|
-
const SP_TYPE = val2.type;
|
|
11479
|
-
const SP_URL = val2.url;
|
|
11480
|
-
let SP_EXPRESSION: string = val2.expression;
|
|
11481
|
-
let expressions: any[] = [];
|
|
11482
|
-
let original_expressions: any[] = [];
|
|
11483
|
-
if (SP_EXPRESSION) {
|
|
11484
|
-
const retVal = this.ProcessExpressions(resourceName, SP_EXPRESSION);
|
|
11485
|
-
expressions = retVal.expressions;
|
|
11486
|
-
original_expressions = retVal.original_expressions;
|
|
11487
|
-
}
|
|
11488
11440
|
|
|
11489
|
-
|
|
11490
|
-
|
|
11491
|
-
|
|
11492
|
-
params: [ ]
|
|
11493
|
-
}
|
|
11494
|
-
}
|
|
11495
|
-
|
|
11496
|
-
// GetResourceField
|
|
11497
|
-
|
|
11498
|
-
const record: ISearchParamRecord = {
|
|
11499
|
-
SP_ID,
|
|
11500
|
-
SP_NAME,
|
|
11501
|
-
SP_TYPE,
|
|
11502
|
-
SP_URL,
|
|
11503
|
-
expressions,
|
|
11504
|
-
original_expressions,
|
|
11505
|
-
SP_DEFINITION: this.resourceHelper.GetSearchParam(SP_URL)
|
|
11506
|
-
};
|
|
11507
|
-
|
|
11508
|
-
for (let i=0; i < record.expressions.length; i++) {
|
|
11509
|
-
//console.log(record.expressions[i]);
|
|
11510
|
-
const rf = this.resourceHelper.GetResourceField(resourceName, record.expressions[i].path);
|
|
11511
|
-
if (rf) {
|
|
11512
|
-
expressions[i].RES_FIELD = rf;
|
|
11513
|
-
}
|
|
11514
|
-
}
|
|
11515
|
-
|
|
11516
|
-
if (val2.component) {
|
|
11517
|
-
record.component = [ ...val2.component ];
|
|
11518
|
-
(record.component as any[]).forEach(c => {
|
|
11519
|
-
//c.SP_RAW_PATHS = (c.expression.split('|') as any[]).map(rp => rp.trim());
|
|
11520
|
-
//c.SP_PATHS = (c.SP_RAW_PATHS as any[]).map(rawPath => this.ResolveFhirChoiceType(rawPath));
|
|
11521
|
-
const retVal = this.ProcessExpressions('', c.expression);
|
|
11522
|
-
c.expressions = retVal.expressions;
|
|
11523
|
-
c.original_expressions = retVal.original_expressions;
|
|
11524
|
-
const def = this.resourceHelper.GetSearchParam(c.definition);
|
|
11525
|
-
if (def && def.type) {
|
|
11526
|
-
c.type = def.type
|
|
11527
|
-
}
|
|
11528
|
-
})
|
|
11529
|
-
}
|
|
11530
|
-
|
|
11531
|
-
searchParamData[resourceName].params.push(record);
|
|
11532
|
-
}
|
|
11533
|
-
}
|
|
11534
|
-
|
|
11535
|
-
this.#searchParams = searchParamData;
|
|
11441
|
+
GetSearchParamFromResourceType = (resourceType: string, name: string): ISearchParamRecord | undefined => {
|
|
11442
|
+
return this.resourceHelper.GetSearchParamFromResourceType(resourceType, name);
|
|
11443
|
+
}
|
|
11536
11444
|
|
|
11537
|
-
|
|
11445
|
+
GetPathsFromResourceType = (resourceType: string, name: string): string[] => {
|
|
11446
|
+
return this.resourceHelper.GetPathsFromResourceType(resourceType, name);
|
|
11538
11447
|
}
|
|
11539
|
-
|
|
11448
|
+
*/
|
|
11540
11449
|
}
|
|
11541
11450
|
var lib$1 = { exports: {} };
|
|
11542
11451
|
var defaults = { exports: {} };
|
|
@@ -18945,229 +18854,10 @@ class PGFhirAccessLayer extends tinyEmitterExports.TinyEmitter {
|
|
|
18945
18854
|
}
|
|
18946
18855
|
};
|
|
18947
18856
|
}
|
|
18948
|
-
const RELEASE_SCRIPT = `
|
|
18949
|
-
if redis.call("get", KEYS[1]) == ARGV[1] then
|
|
18950
|
-
return redis.call("del", KEYS[1])
|
|
18951
|
-
else
|
|
18952
|
-
return 0
|
|
18953
|
-
end
|
|
18954
|
-
`;
|
|
18955
|
-
const RENEW_SCRIPT = `
|
|
18956
|
-
if redis.call("get", KEYS[1]) == ARGV[1] then
|
|
18957
|
-
return redis.call("pexpire", KEYS[1], ARGV[2])
|
|
18958
|
-
else
|
|
18959
|
-
return 0
|
|
18960
|
-
end
|
|
18961
|
-
`;
|
|
18962
|
-
class RedisDistributedLock {
|
|
18963
|
-
client;
|
|
18964
|
-
ttlMs;
|
|
18965
|
-
heartbeatMs;
|
|
18966
|
-
keyPrefix;
|
|
18967
|
-
constructor(client2, options) {
|
|
18968
|
-
this.client = client2;
|
|
18969
|
-
this.ttlMs = options?.ttlMs ?? 3e4;
|
|
18970
|
-
this.heartbeatMs = options?.heartbeatMs ?? Math.floor(this.ttlMs / 3);
|
|
18971
|
-
this.keyPrefix = options?.keyPrefix ?? "lock:";
|
|
18972
|
-
if (this.ttlMs <= 0) {
|
|
18973
|
-
throw new Error("ttlMs must be > 0");
|
|
18974
|
-
}
|
|
18975
|
-
if (this.heartbeatMs <= 0) {
|
|
18976
|
-
throw new Error("heartbeatMs must be > 0");
|
|
18977
|
-
}
|
|
18978
|
-
if (this.heartbeatMs >= this.ttlMs) {
|
|
18979
|
-
throw new Error("heartbeatMs should be less than ttlMs");
|
|
18980
|
-
}
|
|
18981
|
-
}
|
|
18982
|
-
buildKey(name) {
|
|
18983
|
-
return `${this.keyPrefix}${name}`;
|
|
18984
|
-
}
|
|
18985
|
-
async acquire(name, ttlMs) {
|
|
18986
|
-
const key = this.buildKey(name);
|
|
18987
|
-
const token = require$$0.randomUUID();
|
|
18988
|
-
const effectiveTtlMs = ttlMs ?? this.ttlMs;
|
|
18989
|
-
const result2 = await this.client.set(key, token, {
|
|
18990
|
-
NX: true,
|
|
18991
|
-
PX: effectiveTtlMs
|
|
18992
|
-
});
|
|
18993
|
-
if (result2 !== "OK") {
|
|
18994
|
-
return null;
|
|
18995
|
-
}
|
|
18996
|
-
return {
|
|
18997
|
-
key,
|
|
18998
|
-
token,
|
|
18999
|
-
ttlMs: effectiveTtlMs
|
|
19000
|
-
};
|
|
19001
|
-
}
|
|
19002
|
-
async release(lock) {
|
|
19003
|
-
const result2 = await this.client.eval(RELEASE_SCRIPT, {
|
|
19004
|
-
keys: [lock.key],
|
|
19005
|
-
arguments: [lock.token]
|
|
19006
|
-
});
|
|
19007
|
-
return Number(result2) === 1;
|
|
19008
|
-
}
|
|
19009
|
-
async renew(lock, ttlMs) {
|
|
19010
|
-
const effectiveTtlMs = ttlMs ?? lock.ttlMs;
|
|
19011
|
-
const result2 = await this.client.eval(RENEW_SCRIPT, {
|
|
19012
|
-
keys: [lock.key],
|
|
19013
|
-
arguments: [lock.token, String(effectiveTtlMs)]
|
|
19014
|
-
});
|
|
19015
|
-
return Number(result2) === 1;
|
|
19016
|
-
}
|
|
19017
|
-
async isOwner(lock) {
|
|
19018
|
-
const currentValue = await this.client.get(lock.key);
|
|
19019
|
-
return currentValue === lock.token;
|
|
19020
|
-
}
|
|
19021
|
-
async runExclusive(name, task, options) {
|
|
19022
|
-
const lock = await this.acquire(name, options?.ttlMs);
|
|
19023
|
-
if (!lock) {
|
|
19024
|
-
if (options?.onLockNotAcquired) {
|
|
19025
|
-
await options.onLockNotAcquired();
|
|
19026
|
-
}
|
|
19027
|
-
return { acquired: false };
|
|
19028
|
-
}
|
|
19029
|
-
let timer = null;
|
|
19030
|
-
let stopped = false;
|
|
19031
|
-
let renewalError = null;
|
|
19032
|
-
const autoRenew = options?.autoRenew ?? false;
|
|
19033
|
-
const heartbeatMs = options?.heartbeatMs ?? this.heartbeatMs;
|
|
19034
|
-
const stopHeartbeat = () => {
|
|
19035
|
-
stopped = true;
|
|
19036
|
-
if (timer) {
|
|
19037
|
-
clearInterval(timer);
|
|
19038
|
-
timer = null;
|
|
19039
|
-
}
|
|
19040
|
-
};
|
|
19041
|
-
if (autoRenew) {
|
|
19042
|
-
timer = setInterval(async () => {
|
|
19043
|
-
if (stopped) {
|
|
19044
|
-
return;
|
|
19045
|
-
}
|
|
19046
|
-
try {
|
|
19047
|
-
const ok = await this.renew(lock, lock.ttlMs);
|
|
19048
|
-
if (!ok) {
|
|
19049
|
-
renewalError = new Error(
|
|
19050
|
-
`Lost lock ownership while renewing "${lock.key}"`
|
|
19051
|
-
);
|
|
19052
|
-
stopHeartbeat();
|
|
19053
|
-
}
|
|
19054
|
-
} catch (err) {
|
|
19055
|
-
renewalError = err instanceof Error ? err : new Error(String(err));
|
|
19056
|
-
stopHeartbeat();
|
|
19057
|
-
}
|
|
19058
|
-
}, heartbeatMs).unref();
|
|
19059
|
-
}
|
|
19060
|
-
try {
|
|
19061
|
-
const result2 = await task();
|
|
19062
|
-
if (renewalError) {
|
|
19063
|
-
throw renewalError;
|
|
19064
|
-
}
|
|
19065
|
-
return { acquired: true, result: result2 };
|
|
19066
|
-
} finally {
|
|
19067
|
-
stopHeartbeat();
|
|
19068
|
-
try {
|
|
19069
|
-
await this.release(lock);
|
|
19070
|
-
} catch {
|
|
19071
|
-
}
|
|
19072
|
-
}
|
|
19073
|
-
}
|
|
19074
|
-
}
|
|
19075
|
-
class SearchParameterManager {
|
|
19076
|
-
redis;
|
|
19077
|
-
EnsureSearchParameterDataLoaded = async (name, loadFn, options) => {
|
|
19078
|
-
if (!this.redis) {
|
|
19079
|
-
const redisUrl = stsconfig.goptions.imRedisMessageProcessorUrl;
|
|
19080
|
-
console.log(`SearchParameterManager(): redis trying to connect ...`);
|
|
19081
|
-
this.redis = redis.createClient({
|
|
19082
|
-
url: redisUrl
|
|
19083
|
-
});
|
|
19084
|
-
await this.redis.connect();
|
|
19085
|
-
console.log(`SearchParameterManager(): redis connected`);
|
|
19086
|
-
}
|
|
19087
|
-
try {
|
|
19088
|
-
const pollIntervalMs = options?.pollIntervalMs ?? 250;
|
|
19089
|
-
const lockTtlMs = options?.lockTtlMs ?? 3e4;
|
|
19090
|
-
const autoRenew = options?.autoRenew ?? true;
|
|
19091
|
-
const heartbeatMs = options?.heartbeatMs ?? 1e4;
|
|
19092
|
-
const completeTtlSeconds = options?.completeTtlSeconds;
|
|
19093
|
-
const timeoutMs = options?.timeoutMs;
|
|
19094
|
-
const completeKey = `fhir:searchparam:${name}:complete`;
|
|
19095
|
-
const startedAt = Date.now();
|
|
19096
|
-
const lockManager = new RedisDistributedLock(this.redis, {
|
|
19097
|
-
ttlMs: 3e4,
|
|
19098
|
-
heartbeatMs: 1e4,
|
|
19099
|
-
keyPrefix: "lock:"
|
|
19100
|
-
});
|
|
19101
|
-
while (true) {
|
|
19102
|
-
if (typeof timeoutMs === "number" && timeoutMs > 0) {
|
|
19103
|
-
const elapsedMs = Date.now() - startedAt;
|
|
19104
|
-
if (elapsedMs >= timeoutMs) {
|
|
19105
|
-
throw new Error(
|
|
19106
|
-
`Timed out waiting for search param "${name}" to be loaded`
|
|
19107
|
-
);
|
|
19108
|
-
}
|
|
19109
|
-
}
|
|
19110
|
-
try {
|
|
19111
|
-
const alreadyComplete = await this.redis.get(completeKey);
|
|
19112
|
-
if (alreadyComplete) {
|
|
19113
|
-
console.log(`ensureSearchParamLoaded():alreadyComplete: PID: [${process.pid}] data loaded: [${alreadyComplete}]`);
|
|
19114
|
-
return;
|
|
19115
|
-
}
|
|
19116
|
-
} catch (error) {
|
|
19117
|
-
console.error(error);
|
|
19118
|
-
throw error;
|
|
19119
|
-
}
|
|
19120
|
-
const runResult = await lockManager.runExclusive(
|
|
19121
|
-
`fhir:searchparam:${name}`,
|
|
19122
|
-
async () => {
|
|
19123
|
-
console.log(`ensureSearchParamLoaded(): PID: [${process.pid}] lock acquired`);
|
|
19124
|
-
const completeAfterLock = await this.redis.get(completeKey);
|
|
19125
|
-
if (completeAfterLock) {
|
|
19126
|
-
console.log(`ensureSearchParamLoaded():completeAfterLock: PID: [${process.pid}] data loaded: [${completeAfterLock}]`);
|
|
19127
|
-
return;
|
|
19128
|
-
}
|
|
19129
|
-
await loadFn();
|
|
19130
|
-
const completeValue = JSON.stringify({
|
|
19131
|
-
loaded: true,
|
|
19132
|
-
loadedAt: (/* @__PURE__ */ new Date()).toLocaleString(),
|
|
19133
|
-
name,
|
|
19134
|
-
workerPid: process.pid
|
|
19135
|
-
});
|
|
19136
|
-
console.log(`ensureSearchParamLoaded(): PID: [${process.pid}] data loaded: [${completeValue}]`);
|
|
19137
|
-
if (typeof completeTtlSeconds === "number" && completeTtlSeconds > 0) {
|
|
19138
|
-
await this.redis.set(completeKey, completeValue, {
|
|
19139
|
-
EX: completeTtlSeconds
|
|
19140
|
-
});
|
|
19141
|
-
} else {
|
|
19142
|
-
await this.redis.set(completeKey, completeValue);
|
|
19143
|
-
}
|
|
19144
|
-
},
|
|
19145
|
-
{
|
|
19146
|
-
ttlMs: lockTtlMs,
|
|
19147
|
-
autoRenew,
|
|
19148
|
-
heartbeatMs
|
|
19149
|
-
}
|
|
19150
|
-
);
|
|
19151
|
-
if (runResult.acquired) {
|
|
19152
|
-
return;
|
|
19153
|
-
}
|
|
19154
|
-
console.log(`ensureSearchParamLoaded(): PID: [${process.pid}] Did not get lock`);
|
|
19155
|
-
await stsutils.Sleep(pollIntervalMs);
|
|
19156
|
-
}
|
|
19157
|
-
} finally {
|
|
19158
|
-
if (this.redis) {
|
|
19159
|
-
this.redis.close();
|
|
19160
|
-
console.log(`SearchParameterManager(): redis closed`);
|
|
19161
|
-
}
|
|
19162
|
-
}
|
|
19163
|
-
};
|
|
19164
|
-
}
|
|
19165
18857
|
exports.DBSearchIndex = DBSearchIndex;
|
|
19166
18858
|
exports.FHIRDateUtils = FHIRDateUtils;
|
|
19167
18859
|
exports.PGFhirAccessLayer = PGFhirAccessLayer;
|
|
19168
|
-
exports.RedisDistributedLock = RedisDistributedLock;
|
|
19169
18860
|
exports.ResourceHelper = ResourceHelper;
|
|
19170
|
-
exports.SearchParameterManager = SearchParameterManager;
|
|
19171
18861
|
exports.hashReferenceParam = hashReferenceParam;
|
|
19172
18862
|
exports.hashStringParam = hashStringParam;
|
|
19173
18863
|
exports.hashTokenParam = hashTokenParam;
|