use of org.hl7.fhir.r4b.model.IdType in project beneficiary-fhir-data by CMSgov.
the class PatientResourceProvider method read.
/**
* Adds support for the FHIR "read" operation, for {@link Patient}s. The {@link Read} annotation
* indicates that this method supports the read operation.
*
* <p>Read operations take a single parameter annotated with {@link IdParam}, and should return a
* single resource instance.
*
* @param patientId The read operation takes one parameter, which must be of type {@link IdType}
* and must be annotated with the {@link IdParam} annotation.
* @param requestDetails a {@link RequestDetails} containing the details of the request URL, used
* to parse out pagination values
* @return Returns a resource matching the specified {@link IdDt}, or <code>null</code> if none
* exists.
*/
@Read(version = false)
@Trace
public Patient read(@IdParam IdType patientId, RequestDetails requestDetails) {
if (patientId == null)
throw new IllegalArgumentException();
if (patientId.getVersionIdPartAsLong() != null)
throw new IllegalArgumentException();
String beneIdText = patientId.getIdPart();
if (beneIdText == null || beneIdText.trim().isEmpty())
throw new IllegalArgumentException();
RequestHeaders requestHeader = RequestHeaders.getHeaderWrapper(requestDetails);
Operation operation = new Operation(Operation.Endpoint.V1_PATIENT);
operation.setOption("by", "id");
// there is another method with exclude list: requestHeader.getNVPairs(<excludeHeaders>)
requestHeader.getNVPairs().forEach((n, v) -> operation.setOption(n, v.toString()));
operation.publishOperationName();
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
CriteriaQuery<Beneficiary> criteria = builder.createQuery(Beneficiary.class);
Root<Beneficiary> root = criteria.from(Beneficiary.class);
root.fetch(Beneficiary_.skippedRifRecords, JoinType.LEFT);
if (requestHeader.isHICNinIncludeIdentifiers())
root.fetch(Beneficiary_.beneficiaryHistories, JoinType.LEFT);
if (requestHeader.isMBIinIncludeIdentifiers())
root.fetch(Beneficiary_.medicareBeneficiaryIdHistories, JoinType.LEFT);
criteria.select(root);
criteria.where(builder.equal(root.get(Beneficiary_.beneficiaryId), beneIdText));
Beneficiary beneficiary = null;
Long beneByIdQueryNanoSeconds = null;
Timer.Context timerBeneQuery = metricRegistry.timer(MetricRegistry.name(getClass().getSimpleName(), "query", "bene_by_id")).time();
try {
beneficiary = entityManager.createQuery(criteria).getSingleResult();
} catch (NoResultException e) {
throw new ResourceNotFoundException(patientId);
} finally {
beneByIdQueryNanoSeconds = timerBeneQuery.stop();
TransformerUtils.recordQueryInMdc(String.format("bene_by_id.include_%s", String.join("_", (List<String>) requestHeader.getValue(HEADER_NAME_INCLUDE_IDENTIFIERS))), beneByIdQueryNanoSeconds, beneficiary == null ? 0 : 1);
}
// Null out the unhashed HICNs if we're not supposed to be returning them
if (!requestHeader.isHICNinIncludeIdentifiers()) {
beneficiary.setHicnUnhashed(Optional.empty());
}
// Null out the unhashed MBIs if we're not supposed to be returning
if (!requestHeader.isMBIinIncludeIdentifiers()) {
beneficiary.setMedicareBeneficiaryId(Optional.empty());
}
// Add bene_id to MDC logs
TransformerUtils.logBeneIdToMdc(Arrays.asList(beneIdText));
Patient patient = BeneficiaryTransformer.transform(metricRegistry, beneficiary, requestHeader);
return patient;
}
use of org.hl7.fhir.r4b.model.IdType in project beneficiary-fhir-data by CMSgov.
the class R4CoverageResourceProvider method read.
/**
* Adds support for the FHIR "read" operation, for {@link Coverage}s. The {@link Read} annotation
* indicates that this method supports the read operation.
*
* <p>Read operations take a single parameter annotated with {@link IdParam}, and should return a
* single resource instance.
*
* @param coverageId The read operation takes one parameter, which must be of type {@link IdType}
* and must be annotated with the {@link IdParam} annotation.
* @return Returns a resource matching the specified {@link IdDt}, or <code>null</code> if none
* exists.
*/
@Read(version = false)
@Trace
public Coverage read(@IdParam IdType coverageId) {
if (coverageId == null)
throw new IllegalArgumentException();
if (coverageId.getVersionIdPartAsLong() != null)
throw new IllegalArgumentException();
String coverageIdText = coverageId.getIdPart();
if (coverageIdText == null || coverageIdText.trim().isEmpty())
throw new IllegalArgumentException();
Operation operation = new Operation(Operation.Endpoint.V2_COVERAGE);
operation.setOption("by", "id");
operation.publishOperationName();
Matcher coverageIdMatcher = COVERAGE_ID_PATTERN.matcher(coverageIdText);
if (!coverageIdMatcher.matches())
throw new IllegalArgumentException("Unsupported ID pattern: " + coverageIdText);
String coverageIdSegmentText = coverageIdMatcher.group(1);
Optional<MedicareSegment> coverageIdSegment = MedicareSegment.selectByUrlPrefix(coverageIdSegmentText);
if (!coverageIdSegment.isPresent())
throw new ResourceNotFoundException(coverageId);
String coverageIdBeneficiaryIdText = coverageIdMatcher.group(2);
Beneficiary beneficiaryEntity;
try {
beneficiaryEntity = findBeneficiaryById(coverageIdBeneficiaryIdText, null);
if (!beneficiaryEntity.getBeneEnrollmentReferenceYear().isPresent()) {
throw new ResourceNotFoundException("Cannot find coverage for non present enrollment year");
}
} catch (NoResultException e) {
throw new ResourceNotFoundException(new IdDt(Beneficiary.class.getSimpleName(), coverageIdBeneficiaryIdText));
}
Coverage coverage = CoverageTransformerV2.transform(metricRegistry, coverageIdSegment.get(), beneficiaryEntity);
return coverage;
}
use of org.hl7.fhir.r4b.model.IdType in project beneficiary-fhir-data by CMSgov.
the class R4ExplanationOfBenefitResourceProvider method read.
/**
* Adds support for the FHIR "read" operation, for {@link ExplanationOfBenefit}s. The {@link Read}
* annotation indicates that this method supports the read operation.
*
* <p>Read operations take a single parameter annotated with {@link IdParam}, and should return a
* single resource instance.
*
* @param eobId The read operation takes one parameter, which must be of type {@link IdType} and
* must be annotated with the {@link IdParam} annotation.
* @param requestDetails the request details for the read
* @return Returns a resource matching the specified {@link IdDt}, or <code>null</code> if none
* exists.
*/
@SuppressWarnings({ "rawtypes", "unchecked" })
@Read(version = false)
@Trace
public ExplanationOfBenefit read(@IdParam IdType eobId, RequestDetails requestDetails) {
if (eobId == null)
throw new IllegalArgumentException();
if (eobId.getVersionIdPartAsLong() != null)
throw new IllegalArgumentException();
String eobIdText = eobId.getIdPart();
if (eobIdText == null || eobIdText.trim().isEmpty())
throw new IllegalArgumentException();
Matcher eobIdMatcher = EOB_ID_PATTERN.matcher(eobIdText);
if (!eobIdMatcher.matches())
throw new IllegalArgumentException("Unsupported ID pattern: " + eobIdText);
String eobIdTypeText = eobIdMatcher.group(1);
Optional<ClaimTypeV2> eobIdType = ClaimTypeV2.parse(eobIdTypeText);
if (!eobIdType.isPresent())
throw new ResourceNotFoundException(eobId);
String eobIdClaimIdText = eobIdMatcher.group(2);
boolean includeTaxNumbers = returnIncludeTaxNumbers(requestDetails);
Operation operation = new Operation(Operation.Endpoint.V2_EOB);
operation.setOption("IncludeTaxNumbers", "" + includeTaxNumbers);
operation.setOption("by", "id");
operation.publishOperationName();
Class<?> entityClass = eobIdType.get().getEntityClass();
CriteriaBuilder builder = entityManager.getCriteriaBuilder();
CriteriaQuery criteria = builder.createQuery(entityClass);
Root root = criteria.from(entityClass);
eobIdType.get().getEntityLazyAttributes().stream().forEach(a -> root.fetch(a));
criteria.select(root);
criteria.where(builder.equal(root.get(eobIdType.get().getEntityIdAttribute()), eobIdClaimIdText));
Object claimEntity = null;
Long eobByIdQueryNanoSeconds = null;
Timer.Context timerEobQuery = metricRegistry.timer(MetricRegistry.name(getClass().getSimpleName(), "query", "eob_by_id")).time();
try {
claimEntity = entityManager.createQuery(criteria).getSingleResult();
} catch (NoResultException e) {
throw new ResourceNotFoundException(eobId);
} finally {
eobByIdQueryNanoSeconds = timerEobQuery.stop();
TransformerUtilsV2.recordQueryInMdc("eob_by_id", eobByIdQueryNanoSeconds, claimEntity == null ? 0 : 1);
}
ExplanationOfBenefit eob = eobIdType.get().getTransformer().transform(metricRegistry, claimEntity, Optional.of(includeTaxNumbers));
return eob;
}
use of org.hl7.fhir.r4b.model.IdType in project beneficiary-fhir-data by CMSgov.
the class R4PatientResourceProvider method searchByLogicalId.
/**
* Adds support for the FHIR "search" operation for {@link Patient}s, allowing users to search by
* {@link Patient#getId()}.
*
* <p>The {@link Search} annotation indicates that this method supports the search operation.
* There may be many different methods annotated with this {@link Search} annotation, to support
* many different search criteria.
*
* @param logicalId a {@link TokenParam} (with no system, per the spec) for the {@link
* Patient#getId()} to try and find a matching {@link Patient} for
* @param startIndex an {@link OptionalParam} for the startIndex (or offset) used to determine
* pagination
* @param lastUpdated an {@link OptionalParam} to filter the results based on the passed date
* range
* @param requestDetails a {@link RequestDetails} containing the details of the request URL, used
* to parse out pagination values
* @return Returns a {@link List} of {@link Patient}s, which may contain multiple matching
* resources, or may also be empty.
*/
@Search
@Trace
public Bundle searchByLogicalId(@RequiredParam(name = Patient.SP_RES_ID) @Description(shortDefinition = "The patient identifier to search for") TokenParam logicalId, @OptionalParam(name = "startIndex") @Description(shortDefinition = "The offset used for result pagination") String startIndex, @OptionalParam(name = "_lastUpdated") @Description(shortDefinition = "Include resources last updated in the given range") DateRangeParam lastUpdated, RequestDetails requestDetails) {
if (logicalId.getQueryParameterQualifier() != null)
throw new InvalidRequestException("Unsupported query parameter qualifier: " + logicalId.getQueryParameterQualifier());
if (logicalId.getSystem() != null && !logicalId.getSystem().isEmpty())
throw new InvalidRequestException("Unsupported query parameter system: " + logicalId.getSystem());
if (logicalId.getValueNotNull().isEmpty())
throw new InvalidRequestException("Unsupported query parameter value: " + logicalId.getValue());
List<IBaseResource> patients;
if (loadedFilterManager.isResultSetEmpty(logicalId.getValue(), lastUpdated)) {
patients = Collections.emptyList();
} else {
try {
patients = Optional.of(read(new IdType(logicalId.getValue()), requestDetails)).filter(p -> QueryUtils.isInRange(p.getMeta().getLastUpdated().toInstant(), lastUpdated)).map(p -> Collections.singletonList((IBaseResource) p)).orElse(Collections.emptyList());
} catch (ResourceNotFoundException e) {
patients = Collections.emptyList();
}
}
/*
* Publish the operation name. Note: This is a bit later than we'd normally do this, as we need
* to override the operation name that was published by the possible call to read(...), above.
*/
RequestHeaders requestHeader = RequestHeaders.getHeaderWrapper(requestDetails);
Operation operation = new Operation(Operation.Endpoint.V2_PATIENT);
operation.setOption("by", "id");
// track all api hdrs
requestHeader.getNVPairs().forEach((n, v) -> operation.setOption(n, v.toString()));
operation.setOption("_lastUpdated", Boolean.toString(lastUpdated != null && !lastUpdated.isEmpty()));
operation.publishOperationName();
OffsetLinkBuilder paging = new OffsetLinkBuilder(requestDetails, "/Patient?");
Bundle bundle = TransformerUtilsV2.createBundle(paging, patients, loadedFilterManager.getTransactionTime());
return bundle;
}
use of org.hl7.fhir.r4b.model.IdType in project beneficiary-fhir-data by CMSgov.
the class ExplanationOfBenefitResourceProviderIT method readEobForExistingOutpatientClaim.
/**
* Verifies that {link ExplanationOfBenefitResourceProvider#read(IdType, RequestDetails)} works as
* expected for an {@link OutpatientClaim}-derived {@link ExplanationOfBenefit} that does exist in
* the DB.
*
* @throws FHIRException (indicates test failure)
*/
@Test
public void readEobForExistingOutpatientClaim() throws FHIRException {
List<Object> loadedRecords = ServerTestUtils.get().loadData(Arrays.asList(StaticRifResourceGroup.SAMPLE_A.getResources()));
IGenericClient fhirClient = ServerTestUtils.get().createFhirClient();
OutpatientClaim claim = loadedRecords.stream().filter(r -> r instanceof OutpatientClaim).map(r -> (OutpatientClaim) r).findFirst().get();
ExplanationOfBenefit eob = fhirClient.read().resource(ExplanationOfBenefit.class).withId(TransformerUtils.buildEobId(ClaimType.OUTPATIENT, claim.getClaimId())).execute();
assertNotNull(eob);
OutpatientClaimTransformerTest.assertMatches(claim, eob);
}
Aggregations