@phema/cql-execution
Version:
An execution framework for the Clinical Quality Language (CQL)
1,222 lines (936 loc) • 33.3 kB
JavaScript
"use strict";
function _typeof(obj) { "@babel/helpers - typeof"; if (typeof Symbol === "function" && typeof Symbol.iterator === "symbol") { _typeof = function _typeof(obj) { return typeof obj; }; } else { _typeof = function _typeof(obj) { return obj && typeof Symbol === "function" && obj.constructor === Symbol && obj !== Symbol.prototype ? "symbol" : typeof obj; }; } return _typeof(obj); }
function _slicedToArray(arr, i) { return _arrayWithHoles(arr) || _iterableToArrayLimit(arr, i) || _unsupportedIterableToArray(arr, i) || _nonIterableRest(); }
function _nonIterableRest() { throw new TypeError("Invalid attempt to destructure non-iterable instance.\nIn order to be iterable, non-array objects must have a [Symbol.iterator]() method."); }
function _unsupportedIterableToArray(o, minLen) { if (!o) return; if (typeof o === "string") return _arrayLikeToArray(o, minLen); var n = Object.prototype.toString.call(o).slice(8, -1); if (n === "Object" && o.constructor) n = o.constructor.name; if (n === "Map" || n === "Set") return Array.from(o); if (n === "Arguments" || /^(?:Ui|I)nt(?:8|16|32)(?:Clamped)?Array$/.test(n)) return _arrayLikeToArray(o, minLen); }
function _arrayLikeToArray(arr, len) { if (len == null || len > arr.length) len = arr.length; for (var i = 0, arr2 = new Array(len); i < len; i++) { arr2[i] = arr[i]; } return arr2; }
function _iterableToArrayLimit(arr, i) { if (typeof Symbol === "undefined" || !(Symbol.iterator in Object(arr))) return; var _arr = []; var _n = true; var _d = false; var _e = undefined; try { for (var _i = arr[Symbol.iterator](), _s; !(_n = (_s = _i.next()).done); _n = true) { _arr.push(_s.value); if (i && _arr.length === i) break; } } catch (err) { _d = true; _e = err; } finally { try { if (!_n && _i["return"] != null) _i["return"](); } finally { if (_d) throw _e; } } return _arr; }
function _arrayWithHoles(arr) { if (Array.isArray(arr)) return arr; }
function _classCallCheck(instance, Constructor) { if (!(instance instanceof Constructor)) { throw new TypeError("Cannot call a class as a function"); } }
function _defineProperties(target, props) { for (var i = 0; i < props.length; i++) { var descriptor = props[i]; descriptor.enumerable = descriptor.enumerable || false; descriptor.configurable = true; if ("value" in descriptor) descriptor.writable = true; Object.defineProperty(target, descriptor.key, descriptor); } }
function _createClass(Constructor, protoProps, staticProps) { if (protoProps) _defineProperties(Constructor.prototype, protoProps); if (staticProps) _defineProperties(Constructor, staticProps); return Constructor; }
function _inherits(subClass, superClass) { if (typeof superClass !== "function" && superClass !== null) { throw new TypeError("Super expression must either be null or a function"); } subClass.prototype = Object.create(superClass && superClass.prototype, { constructor: { value: subClass, writable: true, configurable: true } }); if (superClass) _setPrototypeOf(subClass, superClass); }
function _setPrototypeOf(o, p) { _setPrototypeOf = Object.setPrototypeOf || function _setPrototypeOf(o, p) { o.__proto__ = p; return o; }; return _setPrototypeOf(o, p); }
function _createSuper(Derived) { var hasNativeReflectConstruct = _isNativeReflectConstruct(); return function _createSuperInternal() { var Super = _getPrototypeOf(Derived), result; if (hasNativeReflectConstruct) { var NewTarget = _getPrototypeOf(this).constructor; result = Reflect.construct(Super, arguments, NewTarget); } else { result = Super.apply(this, arguments); } return _possibleConstructorReturn(this, result); }; }
function _possibleConstructorReturn(self, call) { if (call && (_typeof(call) === "object" || typeof call === "function")) { return call; } return _assertThisInitialized(self); }
function _assertThisInitialized(self) { if (self === void 0) { throw new ReferenceError("this hasn't been initialised - super() hasn't been called"); } return self; }
function _isNativeReflectConstruct() { if (typeof Reflect === "undefined" || !Reflect.construct) return false; if (Reflect.construct.sham) return false; if (typeof Proxy === "function") return true; try { Date.prototype.toString.call(Reflect.construct(Date, [], function () {})); return true; } catch (e) { return false; } }
function _getPrototypeOf(o) { _getPrototypeOf = Object.setPrototypeOf ? Object.getPrototypeOf : function _getPrototypeOf(o) { return o.__proto__ || Object.getPrototypeOf(o); }; return _getPrototypeOf(o); }
var _require = require('./expression'),
Expression = _require.Expression,
UnimplementedExpression = _require.UnimplementedExpression;
var _require2 = require('../datatypes/datetime'),
DateTime = _require2.DateTime,
_Date = _require2.Date;
var _require3 = require('../datatypes/clinical'),
Concept = _require3.Concept;
var _require4 = require('../datatypes/quantity'),
Quantity = _require4.Quantity,
parseQuantity = _require4.parseQuantity;
var _require5 = require('../util/math'),
isValidDecimal = _require5.isValidDecimal,
isValidInteger = _require5.isValidInteger,
limitDecimalPrecision = _require5.limitDecimalPrecision;
var _require6 = require('../util/util'),
normalizeMillisecondsField = _require6.normalizeMillisecondsField;
var _require7 = require('../datatypes/ratio'),
Ratio = _require7.Ratio;
var _require8 = require('../datatypes/uncertainty'),
Uncertainty = _require8.Uncertainty; // TODO: Casting and Conversion needs unit tests!
var As = /*#__PURE__*/function (_Expression) {
_inherits(As, _Expression);
var _super = _createSuper(As);
function As(json) {
var _this;
_classCallCheck(this, As);
_this = _super.call(this, json);
if (json.asTypeSpecifier) {
_this.asTypeSpecifier = json.asTypeSpecifier;
} else if (json.asType) {
// convert it to a NamedTypedSpecifier
_this.asTypeSpecifier = {
name: json.asType,
type: 'NamedTypeSpecifier'
};
}
_this.strict = json.strict != null ? json.strict : false;
return _this;
}
_createClass(As, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx); // If it is null, return null
if (arg == null) {
return null;
}
if (ctx.matchesTypeSpecifier(arg, this.asTypeSpecifier)) {
// TODO: request patient source to change type identification
return arg;
} else if (this.strict) {
var argTypeString = specifierToString(guessSpecifierType(arg));
var asTypeString = specifierToString(this.asTypeSpecifier);
throw new Error("Cannot cast ".concat(argTypeString, " as ").concat(asTypeString));
} else {
return null;
}
}
}]);
return As;
}(Expression);
var ToBoolean = /*#__PURE__*/function (_Expression2) {
_inherits(ToBoolean, _Expression2);
var _super2 = _createSuper(ToBoolean);
function ToBoolean(json) {
_classCallCheck(this, ToBoolean);
return _super2.call(this, json);
}
_createClass(ToBoolean, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
var strArg = arg.toString().toLowerCase();
if (['true', 't', 'yes', 'y', '1'].includes(strArg)) {
return true;
} else if (['false', 'f', 'no', 'n', '0'].includes(strArg)) {
return false;
}
}
return null;
}
}]);
return ToBoolean;
}(Expression);
var ToConcept = /*#__PURE__*/function (_Expression3) {
_inherits(ToConcept, _Expression3);
var _super3 = _createSuper(ToConcept);
function ToConcept(json) {
_classCallCheck(this, ToConcept);
return _super3.call(this, json);
}
_createClass(ToConcept, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
return new Concept([arg], arg.display);
} else {
return null;
}
}
}]);
return ToConcept;
}(Expression);
var ToDate = /*#__PURE__*/function (_Expression4) {
_inherits(ToDate, _Expression4);
var _super4 = _createSuper(ToDate);
function ToDate(json) {
_classCallCheck(this, ToDate);
return _super4.call(this, json);
}
_createClass(ToDate, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg == null) {
return null;
} else if (arg.isDateTime) {
return arg.getDate();
} else {
return _Date.parse(arg.toString());
}
}
}]);
return ToDate;
}(Expression);
var ToDateTime = /*#__PURE__*/function (_Expression5) {
_inherits(ToDateTime, _Expression5);
var _super5 = _createSuper(ToDateTime);
function ToDateTime(json) {
_classCallCheck(this, ToDateTime);
return _super5.call(this, json);
}
_createClass(ToDateTime, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg == null) {
return null;
} else if (arg.isDate) {
return arg.getDateTime();
} else {
return DateTime.parse(arg.toString());
}
}
}]);
return ToDateTime;
}(Expression);
var ToDecimal = /*#__PURE__*/function (_Expression6) {
_inherits(ToDecimal, _Expression6);
var _super6 = _createSuper(ToDecimal);
function ToDecimal(json) {
_classCallCheck(this, ToDecimal);
return _super6.call(this, json);
}
_createClass(ToDecimal, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
if (arg.isUncertainty) {
var low = limitDecimalPrecision(parseFloat(arg.low.toString()));
var high = limitDecimalPrecision(parseFloat(arg.high.toString()));
return new Uncertainty(low, high);
} else {
var decimal = limitDecimalPrecision(parseFloat(arg.toString()));
if (isValidDecimal(decimal)) {
return decimal;
}
}
}
return null;
}
}]);
return ToDecimal;
}(Expression);
var ToInteger = /*#__PURE__*/function (_Expression7) {
_inherits(ToInteger, _Expression7);
var _super7 = _createSuper(ToInteger);
function ToInteger(json) {
_classCallCheck(this, ToInteger);
return _super7.call(this, json);
}
_createClass(ToInteger, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
var integer = parseInt(arg.toString());
if (isValidInteger(integer)) {
return integer;
}
}
return null;
}
}]);
return ToInteger;
}(Expression);
var ToQuantity = /*#__PURE__*/function (_Expression8) {
_inherits(ToQuantity, _Expression8);
var _super8 = _createSuper(ToQuantity);
function ToQuantity(json) {
_classCallCheck(this, ToQuantity);
return _super8.call(this, json);
}
_createClass(ToQuantity, [{
key: "exec",
value: function exec(ctx) {
return this.convertValue(this.execArgs(ctx));
}
}, {
key: "convertValue",
value: function convertValue(val) {
if (val == null) {
return null;
} else if (typeof val === 'number') {
return new Quantity(val, '1');
} else if (val.isRatio) {
// numerator and denominator are guaranteed non-null
return val.numerator.dividedBy(val.denominator);
} else if (val.isUncertainty) {
return new Uncertainty(this.convertValue(val.low), this.convertValue(val.high));
} else {
// it's a string or something else we'll try to parse as a string
return parseQuantity(val.toString());
}
}
}]);
return ToQuantity;
}(Expression);
var ToRatio = /*#__PURE__*/function (_Expression9) {
_inherits(ToRatio, _Expression9);
var _super9 = _createSuper(ToRatio);
function ToRatio(json) {
_classCallCheck(this, ToRatio);
return _super9.call(this, json);
}
_createClass(ToRatio, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
// Argument will be of form '<quantity>:<quantity>'
var denominator, numerator;
try {
// String will be split into an array. Numerator will be at index 1, Denominator will be at index 4
var splitRatioString = arg.toString().match(/^(\d+(\.\d+)?\s*('.+')?)\s*:\s*(\d+(\.\d+)?\s*('.+')?)$/);
if (splitRatioString == null) {
return null;
}
numerator = parseQuantity(splitRatioString[1]);
denominator = parseQuantity(splitRatioString[4]);
} catch (error) {
// If the input string is not formatted correctly, or cannot be
// interpreted as a valid Quantity value, the result is null.
return null;
} // The value element of a Quantity must be present.
if (numerator == null || denominator == null) {
return null;
}
return new Ratio(numerator, denominator);
} else {
return null;
}
}
}]);
return ToRatio;
}(Expression);
var ToString = /*#__PURE__*/function (_Expression10) {
_inherits(ToString, _Expression10);
var _super10 = _createSuper(ToString);
function ToString(json) {
_classCallCheck(this, ToString);
return _super10.call(this, json);
}
_createClass(ToString, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
return arg.toString();
} else {
return null;
}
}
}]);
return ToString;
}(Expression);
var ToTime = /*#__PURE__*/function (_Expression11) {
_inherits(ToTime, _Expression11);
var _super11 = _createSuper(ToTime);
function ToTime(json) {
_classCallCheck(this, ToTime);
return _super11.call(this, json);
}
_createClass(ToTime, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg != null) {
var timeString = arg.toString(); // Return null if string doesn't represent a valid ISO-8601 Time
// hh:mm:ss.fff or hh:mm:ss.fff
var matches = /^T?((\d{2})(:(\d{2})(:(\d{2})(\.(\d+))?)?)?)?(Z|(([+-])(\d{2})(:?(\d{2}))?))?$/.exec(timeString);
if (matches == null) {
return null;
}
var hours = matches[2];
var minutes = matches[4];
var seconds = matches[6]; // Validate h/m/s if they exist, but allow null
if (hours != null) {
if (hours < 0 || hours > 23) {
return null;
}
hours = parseInt(hours, 10);
}
if (minutes != null) {
if (minutes < 0 || minutes > 59) {
return null;
}
minutes = parseInt(minutes, 10);
}
if (seconds != null) {
if (seconds < 0 || seconds > 59) {
return null;
}
seconds = parseInt(seconds, 10);
}
var milliseconds = matches[8];
if (milliseconds != null) {
milliseconds = parseInt(normalizeMillisecondsField(milliseconds));
} // Time is implemented as Datetime with year 0, month 1, day 1 and null timezoneOffset
return new DateTime(0, 1, 1, hours, minutes, seconds, milliseconds, null);
} else {
return null;
}
}
}]);
return ToTime;
}(Expression);
var Convert = /*#__PURE__*/function (_Expression12) {
_inherits(Convert, _Expression12);
var _super12 = _createSuper(Convert);
function Convert(json) {
var _this2;
_classCallCheck(this, Convert);
_this2 = _super12.call(this, json);
_this2.operand = json.operand;
_this2.toType = json.toType;
return _this2;
}
_createClass(Convert, [{
key: "exec",
value: function exec(ctx) {
switch (this.toType) {
case '{urn:hl7-org:elm-types:r1}Boolean':
return new ToBoolean({
type: 'ToBoolean',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}Concept':
return new ToConcept({
type: 'ToConcept',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}Decimal':
return new ToDecimal({
type: 'ToDecimal',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}Integer':
return new ToInteger({
type: 'ToInteger',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}String':
return new ToString({
type: 'ToString',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}Quantity':
return new ToQuantity({
type: 'ToQuantity',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}DateTime':
return new ToDateTime({
type: 'ToDateTime',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}Date':
return new ToDate({
type: 'ToDate',
operand: this.operand
}).execute(ctx);
case '{urn:hl7-org:elm-types:r1}Time':
return new ToTime({
type: 'ToTime',
operand: this.operand
}).execute(ctx);
default:
return this.execArgs(ctx);
}
}
}]);
return Convert;
}(Expression);
var ConvertsToBoolean = /*#__PURE__*/function (_Expression13) {
_inherits(ConvertsToBoolean, _Expression13);
var _super13 = _createSuper(ConvertsToBoolean);
function ConvertsToBoolean(json) {
var _this3;
_classCallCheck(this, ConvertsToBoolean);
_this3 = _super13.call(this, json);
_this3.operand = json.operand;
return _this3;
}
_createClass(ConvertsToBoolean, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToBoolean, this.operand, ctx);
}
}
}]);
return ConvertsToBoolean;
}(Expression);
var ConvertsToDate = /*#__PURE__*/function (_Expression14) {
_inherits(ConvertsToDate, _Expression14);
var _super14 = _createSuper(ConvertsToDate);
function ConvertsToDate(json) {
var _this4;
_classCallCheck(this, ConvertsToDate);
_this4 = _super14.call(this, json);
_this4.operand = json.operand;
return _this4;
}
_createClass(ConvertsToDate, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToDate, this.operand, ctx);
}
}
}]);
return ConvertsToDate;
}(Expression);
var ConvertsToDateTime = /*#__PURE__*/function (_Expression15) {
_inherits(ConvertsToDateTime, _Expression15);
var _super15 = _createSuper(ConvertsToDateTime);
function ConvertsToDateTime(json) {
var _this5;
_classCallCheck(this, ConvertsToDateTime);
_this5 = _super15.call(this, json);
_this5.operand = json.operand;
return _this5;
}
_createClass(ConvertsToDateTime, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToDateTime, this.operand, ctx);
}
}
}]);
return ConvertsToDateTime;
}(Expression);
var ConvertsToDecimal = /*#__PURE__*/function (_Expression16) {
_inherits(ConvertsToDecimal, _Expression16);
var _super16 = _createSuper(ConvertsToDecimal);
function ConvertsToDecimal(json) {
var _this6;
_classCallCheck(this, ConvertsToDecimal);
_this6 = _super16.call(this, json);
_this6.operand = json.operand;
return _this6;
}
_createClass(ConvertsToDecimal, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToDecimal, this.operand, ctx);
}
}
}]);
return ConvertsToDecimal;
}(Expression);
var ConvertsToInteger = /*#__PURE__*/function (_Expression17) {
_inherits(ConvertsToInteger, _Expression17);
var _super17 = _createSuper(ConvertsToInteger);
function ConvertsToInteger(json) {
var _this7;
_classCallCheck(this, ConvertsToInteger);
_this7 = _super17.call(this, json);
_this7.operand = json.operand;
return _this7;
}
_createClass(ConvertsToInteger, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToInteger, this.operand, ctx);
}
}
}]);
return ConvertsToInteger;
}(Expression);
var ConvertsToQuantity = /*#__PURE__*/function (_Expression18) {
_inherits(ConvertsToQuantity, _Expression18);
var _super18 = _createSuper(ConvertsToQuantity);
function ConvertsToQuantity(json) {
var _this8;
_classCallCheck(this, ConvertsToQuantity);
_this8 = _super18.call(this, json);
_this8.operand = json.operand;
return _this8;
}
_createClass(ConvertsToQuantity, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToQuantity, this.operand, ctx);
}
}
}]);
return ConvertsToQuantity;
}(Expression);
var ConvertsToRatio = /*#__PURE__*/function (_Expression19) {
_inherits(ConvertsToRatio, _Expression19);
var _super19 = _createSuper(ConvertsToRatio);
function ConvertsToRatio(json) {
var _this9;
_classCallCheck(this, ConvertsToRatio);
_this9 = _super19.call(this, json);
_this9.operand = json.operand;
return _this9;
}
_createClass(ConvertsToRatio, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToRatio, this.operand, ctx);
}
}
}]);
return ConvertsToRatio;
}(Expression);
var ConvertsToString = /*#__PURE__*/function (_Expression20) {
_inherits(ConvertsToString, _Expression20);
var _super20 = _createSuper(ConvertsToString);
function ConvertsToString(json) {
var _this10;
_classCallCheck(this, ConvertsToString);
_this10 = _super20.call(this, json);
_this10.operand = json.operand;
return _this10;
}
_createClass(ConvertsToString, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToString, this.operand, ctx);
}
}
}]);
return ConvertsToString;
}(Expression);
var ConvertsToTime = /*#__PURE__*/function (_Expression21) {
_inherits(ConvertsToTime, _Expression21);
var _super21 = _createSuper(ConvertsToTime);
function ConvertsToTime(json) {
var _this11;
_classCallCheck(this, ConvertsToTime);
_this11 = _super21.call(this, json);
_this11.operand = json.operand;
return _this11;
}
_createClass(ConvertsToTime, [{
key: "exec",
value: function exec(ctx) {
var operatorValue = this.execArgs(ctx);
if (operatorValue === null) {
return null;
} else {
return canConvertToType(ToTime, this.operand, ctx);
}
}
}]);
return ConvertsToTime;
}(Expression);
function canConvertToType(toFunction, operand, ctx) {
try {
var value = new toFunction({
type: toFunction.name,
operand: operand
}).execute(ctx);
if (value != null) {
return true;
} else {
return false;
}
} catch (error) {
return false;
}
}
var ConvertQuantity = /*#__PURE__*/function (_Expression22) {
_inherits(ConvertQuantity, _Expression22);
var _super22 = _createSuper(ConvertQuantity);
function ConvertQuantity(json) {
_classCallCheck(this, ConvertQuantity);
return _super22.call(this, json);
}
_createClass(ConvertQuantity, [{
key: "exec",
value: function exec(ctx) {
var _this$execArgs = this.execArgs(ctx),
_this$execArgs2 = _slicedToArray(_this$execArgs, 2),
quantity = _this$execArgs2[0],
newUnit = _this$execArgs2[1];
if (quantity != null && newUnit != null) {
try {
return quantity.convertUnit(newUnit);
} catch (error) {
// Cannot convert input to target unit, spec says to return null
return null;
}
}
}
}]);
return ConvertQuantity;
}(Expression);
var CanConvertQuantity = /*#__PURE__*/function (_Expression23) {
_inherits(CanConvertQuantity, _Expression23);
var _super23 = _createSuper(CanConvertQuantity);
function CanConvertQuantity(json) {
_classCallCheck(this, CanConvertQuantity);
return _super23.call(this, json);
}
_createClass(CanConvertQuantity, [{
key: "exec",
value: function exec(ctx) {
var _this$execArgs3 = this.execArgs(ctx),
_this$execArgs4 = _slicedToArray(_this$execArgs3, 2),
quantity = _this$execArgs4[0],
newUnit = _this$execArgs4[1];
if (quantity != null && newUnit != null) {
try {
quantity.convertUnit(newUnit);
return true;
} catch (error) {
return false;
}
}
return null;
}
}]);
return CanConvertQuantity;
}(Expression);
var Is = /*#__PURE__*/function (_Expression24) {
_inherits(Is, _Expression24);
var _super24 = _createSuper(Is);
function Is(json) {
var _this12;
_classCallCheck(this, Is);
_this12 = _super24.call(this, json);
if (json.isTypeSpecifier) {
_this12.isTypeSpecifier = json.isTypeSpecifier;
} else if (json.isType) {
// Convert it to a NamedTypeSpecifier
_this12.isTypeSpecifier = {
name: json.isType,
type: 'NamedTypeSpecifier'
};
}
return _this12;
}
_createClass(Is, [{
key: "exec",
value: function exec(ctx) {
var arg = this.execArgs(ctx);
if (arg === null) {
return false;
}
if (typeof arg._is !== 'function' && !isSystemType(this.isTypeSpecifier)) {
// We need an _is implementation in order to check non System types
throw new Error("Patient Source does not support Is operation for localId: ".concat(this.localId));
}
return ctx.matchesTypeSpecifier(arg, this.isTypeSpecifier);
}
}]);
return Is;
}(Expression);
function isSystemType(spec) {
switch (spec.type) {
case 'NamedTypeSpecifier':
return spec.name.startsWith('{urn:hl7-org:elm-types:r1}');
case 'ListTypeSpecifier':
return isSystemType(spec.elementType);
case 'TupleTypeSpecifier':
return spec.element.every(function (e) {
return isSystemType(e.elementType);
});
case 'IntervalTypeSpecifier':
return isSystemType(spec.pointType);
case 'ChoiceTypeSpecifier':
return spec.choice.every(function (c) {
return isSystemType(c);
});
default:
return false;
}
}
function specifierToString(spec) {
if (typeof spec === 'string') {
return spec;
} else if (spec == null || spec.type == null) {
return '';
}
switch (spec.type) {
case 'NamedTypeSpecifier':
return spec.name;
case 'ListTypeSpecifier':
return "List<".concat(specifierToString(spec.elementType), ">");
case 'TupleTypeSpecifier':
return "Tuple<".concat(spec.element.map(function (e) {
return "".concat(e.name, " ").concat(specifierToString(e.elementType));
}).join(', '), ">");
case 'IntervalTypeSpecifier':
return "Interval<".concat(specifierToString(spec.pointType), ">");
case 'ChoiceTypeSpecifier':
return "Choice<".concat(spec.choice.map(function (c) {
return specifierToString(c);
}).join(', '), ">");
default:
return JSON.stringify(spec);
}
}
function guessSpecifierType(val) {
if (val == null) {
return 'Null';
}
var typeHierarchy = typeof val._typeHierarchy === 'function' && val._typeHierarchy();
if (typeHierarchy && typeHierarchy.length > 0) {
return typeHierarchy[0];
} else if (typeof val === 'boolean') {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Boolean'
};
} else if (typeof val === 'number' && Math.floor(val) === val) {
// it could still be a decimal, but we have to just take our best guess!
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Integer'
};
} else if (typeof val === 'number') {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Decimal'
};
} else if (typeof val === 'string') {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}String'
};
} else if (val.isConcept) {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Concept'
};
} else if (val.isCode) {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Code'
};
} else if (val.isDate) {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Date'
};
} else if (val.isTime && val.isTime()) {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}Time'
};
} else if (val.isDateTime) {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}DateTime'
};
} else if (val.isQuantity) {
return {
type: 'NamedTypeSpecifier',
name: '{urn:hl7-org:elm-types:r1}DateTime'
};
} else if (Array.isArray(val)) {
// Get unique types from the array (by converting to string and putting in a Set)
var typesAsStrings = Array.from(new Set(val.map(function (v) {
return JSON.stringify(guessSpecifierType(v));
})));
var types = typesAsStrings.map(function (ts) {
return /^{/.test(ts) ? JSON.parse(ts) : ts;
});
return {
type: 'ListTypeSpecifier',
elementType: types.length == 1 ? types[0] : {
type: 'ChoiceTypeSpecifier',
choice: types
}
};
} else if (val.isInterval) {
return {
type: 'IntervalTypeSpecifier',
pointType: val.pointType
};
} else if (_typeof(val) === 'object' && Object.keys(val).length > 0) {
return {
type: 'TupleTypeSpecifier',
element: Object.keys(val).map(function (k) {
return {
name: k,
elementType: guessSpecifierType(val[k])
};
})
};
}
return 'Unknown';
}
var IntervalTypeSpecifier = /*#__PURE__*/function (_UnimplementedExpress) {
_inherits(IntervalTypeSpecifier, _UnimplementedExpress);
var _super25 = _createSuper(IntervalTypeSpecifier);
function IntervalTypeSpecifier() {
_classCallCheck(this, IntervalTypeSpecifier);
return _super25.apply(this, arguments);
}
return IntervalTypeSpecifier;
}(UnimplementedExpression);
var ListTypeSpecifier = /*#__PURE__*/function (_UnimplementedExpress2) {
_inherits(ListTypeSpecifier, _UnimplementedExpress2);
var _super26 = _createSuper(ListTypeSpecifier);
function ListTypeSpecifier() {
_classCallCheck(this, ListTypeSpecifier);
return _super26.apply(this, arguments);
}
return ListTypeSpecifier;
}(UnimplementedExpression);
var NamedTypeSpecifier = /*#__PURE__*/function (_UnimplementedExpress3) {
_inherits(NamedTypeSpecifier, _UnimplementedExpress3);
var _super27 = _createSuper(NamedTypeSpecifier);
function NamedTypeSpecifier() {
_classCallCheck(this, NamedTypeSpecifier);
return _super27.apply(this, arguments);
}
return NamedTypeSpecifier;
}(UnimplementedExpression);
var TupleTypeSpecifier = /*#__PURE__*/function (_UnimplementedExpress4) {
_inherits(TupleTypeSpecifier, _UnimplementedExpress4);
var _super28 = _createSuper(TupleTypeSpecifier);
function TupleTypeSpecifier() {
_classCallCheck(this, TupleTypeSpecifier);
return _super28.apply(this, arguments);
}
return TupleTypeSpecifier;
}(UnimplementedExpression);
module.exports = {
As: As,
CanConvertQuantity: CanConvertQuantity,
Convert: Convert,
ConvertQuantity: ConvertQuantity,
ConvertsToBoolean: ConvertsToBoolean,
ConvertsToDate: ConvertsToDate,
ConvertsToDateTime: ConvertsToDateTime,
ConvertsToDecimal: ConvertsToDecimal,
ConvertsToInteger: ConvertsToInteger,
ConvertsToQuantity: ConvertsToQuantity,
ConvertsToRatio: ConvertsToRatio,
ConvertsToString: ConvertsToString,
ConvertsToTime: ConvertsToTime,
IntervalTypeSpecifier: IntervalTypeSpecifier,
Is: Is,
ListTypeSpecifier: ListTypeSpecifier,
NamedTypeSpecifier: NamedTypeSpecifier,
ToBoolean: ToBoolean,
ToConcept: ToConcept,
ToDate: ToDate,
ToDateTime: ToDateTime,
ToDecimal: ToDecimal,
ToInteger: ToInteger,
ToQuantity: ToQuantity,
ToRatio: ToRatio,
ToString: ToString,
ToTime: ToTime,
TupleTypeSpecifier: TupleTypeSpecifier
};