FHIRPath functions

This commit is contained in:
Grahame Grieve 2020-06-03 05:06:25 +10:00
parent f169a4315f
commit 8658047c16

View File

@ -2,6 +2,7 @@ package org.hl7.fhir.r5.utils;
import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.Base64;
import java.util.Date;
import java.util.EnumSet;
import java.util.HashMap;
@ -10,7 +11,6 @@ import java.util.List;
import java.util.Map;
import java.util.Set;
import org.apache.commons.codec.binary.Base64;
import org.apache.commons.lang3.NotImplementedException;
import org.fhir.ucum.Decimal;
import org.fhir.ucum.Pair;
@ -51,6 +51,7 @@ import org.hl7.fhir.r5.model.TypeDetails.ProfiledType;
import org.hl7.fhir.r5.model.ValueSet;
import org.hl7.fhir.r5.utils.FHIRLexer.FHIRLexerException;
import org.hl7.fhir.r5.utils.FHIRPathEngine.IEvaluationContext.FunctionDetails;
import org.hl7.fhir.utilities.CommaSeparatedStringBuilder;
import org.hl7.fhir.utilities.Utilities;
import org.hl7.fhir.utilities.validation.ValidationOptions;
@ -2876,39 +2877,120 @@ public class FHIRPathEngine {
}
}
private static final char[] HEX_ARRAY = "0123456789ABCDEF".toCharArray();
public static String bytesToHex(byte[] bytes) {
char[] hexChars = new char[bytes.length * 2];
for (int j = 0; j < bytes.length; j++) {
int v = bytes[j] & 0xFF;
hexChars[j * 2] = HEX_ARRAY[v >>> 4];
hexChars[j * 2 + 1] = HEX_ARRAY[v & 0x0F];
}
return new String(hexChars);
}
public static byte[] hexStringToByteArray(String s) {
int len = s.length();
byte[] data = new byte[len / 2];
for (int i = 0; i < len; i += 2) {
data[i / 2] = (byte) ((Character.digit(s.charAt(i), 16) << 4)
+ Character.digit(s.charAt(i+1), 16));
}
return data;
}
private List<Base> funcEncode(ExecutionContext context, List<Base> focus, ExpressionNode exp) {
List<Base> nl = execute(context, focus, exp.getParameters().get(0), true);
String param = nl.get(0).primitiveValue();
List<Base> result = new ArrayList<Base>();
if (focus.size() == 1) {
String cnt = focus.get(0).primitiveValue();
if ("hex".equals(param)) {
result.add(new StringType(bytesToHex(cnt.getBytes())));
} else if ("base64".equals(param)) {
Base64.Encoder enc = Base64.getEncoder();
result.add(new StringType(enc.encodeToString(cnt.getBytes())));
} else if ("urlbase64".equals(param)) {
Base64.Encoder enc = Base64.getUrlEncoder();
result.add(new StringType(enc.encodeToString(cnt.getBytes())));
}
}
return result;
}
private List<Base> funcDecode(ExecutionContext context, List<Base> focus, ExpressionNode exp) {
List<Base> nl = execute(context, focus, exp.getParameters().get(0), true);
String param = nl.get(0).primitiveValue();
List<Base> result = new ArrayList<Base>();
if (focus.size() == 1) {
String cnt = focus.get(0).primitiveValue();
if ("hex".equals(param)) {
result.add(new StringType(new String(hexStringToByteArray(cnt))));
} else if ("base64".equals(param)) {
Base64.Decoder enc = Base64.getDecoder();
result.add(new StringType(new String(enc.decode(cnt))));
} else if ("urlbase64".equals(param)) {
Base64.Decoder enc = Base64.getUrlDecoder();
result.add(new StringType(new String(enc.decode(cnt))));
}
}
return result;
}
private List<Base> funcEscape(ExecutionContext context, List<Base> focus, ExpressionNode exp) {
List<Base> nl = execute(context, focus, exp.getParameters().get(0), true);
String param = nl.get(0).primitiveValue();
List<Base> result = new ArrayList<Base>();
if (focus.size() == 1) {
String cnt = focus.get(0).primitiveValue();
if ("html".equals(param)) {
result.add(new StringType(Utilities.escapeXml(cnt)));
} else if ("json".equals(param)) {
result.add(new StringType(Utilities.escapeJson(cnt)));
}
}
return result;
}
private List<Base> funcTrim(ExecutionContext context, List<Base> focus, ExpressionNode exp) {
List<Base> result = new ArrayList<Base>();
if (focus.size() == 1) {
String cnt = focus.get(0).primitiveValue();
result.add(new StringType(cnt.trim()));
}
return result;
}
private List<Base> funcSplit(ExecutionContext context, List<Base> focus, ExpressionNode exp) {
List<Base> nl = execute(context, focus, exp.getParameters().get(0), true);
String param = nl.get(0).primitiveValue();
List<Base> result = new ArrayList<Base>();
if (focus.size() == 1) {
String cnt = focus.get(0).primitiveValue();
for (String s : cnt.split(param)) {
result.add(new StringType(s));
}
}
return result;
}
private List<Base> funcJoin(ExecutionContext context, List<Base> focus, ExpressionNode exp) {
List<Base> nl = execute(context, focus, exp.getParameters().get(0), true);
String param = nl.get(0).primitiveValue();
List<Base> result = new ArrayList<Base>();
CommaSeparatedStringBuilder b = new CommaSeparatedStringBuilder(param);
for (Base i : focus) {
b.append(i.primitiveValue());
}
result.add(new StringType(b.toString()));
return result;
}