Search in sources :

Example 6 with ComplexData

use of org.openmrs.obs.ComplexData in project openmrs-core by openmrs.

the class ObsServiceTest method saveObs_shouldCreateNewFileFromComplexDataForNewObs.

/**
 * @see ObsService#saveObs(Obs,String)
 */
@Test
public void saveObs_shouldCreateNewFileFromComplexDataForNewObs() {
    executeDataSet(COMPLEX_OBS_XML);
    ObsService os = Context.getObsService();
    ConceptService cs = Context.getConceptService();
    AdministrationService as = Context.getAdministrationService();
    // make sure the file isn't there to begin with
    File complexObsDir = OpenmrsUtil.getDirectoryInApplicationDataDirectory(as.getGlobalProperty(OpenmrsConstants.GLOBAL_PROPERTY_COMPLEX_OBS_DIR));
    File createdFile = new File(complexObsDir, "nameOfFile.txt");
    if (createdFile.exists())
        createdFile.delete();
    // the complex data to put onto an obs that will be saved
    Reader input = new CharArrayReader("This is a string to save to a file".toCharArray());
    ComplexData complexData = new ComplexData("nameOfFile.txt", input);
    // must fetch the concept instead of just new Concept(8473) because the attributes on concept are checked
    // this is a concept mapped to the text handler
    Concept questionConcept = cs.getConcept(8474);
    Obs obsToSave = new Obs(new Person(1), questionConcept, new Date(), new Location(1));
    obsToSave.setComplexData(complexData);
    try {
        os.saveObs(obsToSave, null);
        // make sure the file appears now after the save
        Assert.assertTrue(createdFile.exists());
    } finally {
        // we always have to delete this inside the same unit test because it is outside the
        // database and hence can't be "rolled back" like everything else
        createdFile.delete();
    }
}
Also used : Concept(org.openmrs.Concept) Obs(org.openmrs.Obs) CharArrayReader(java.io.CharArrayReader) ComplexData(org.openmrs.obs.ComplexData) CharArrayReader(java.io.CharArrayReader) Reader(java.io.Reader) File(java.io.File) Person(org.openmrs.Person) Date(java.util.Date) Location(org.openmrs.Location) BaseContextSensitiveTest(org.openmrs.test.BaseContextSensitiveTest) Test(org.junit.Test)

Example 7 with ComplexData

use of org.openmrs.obs.ComplexData in project openmrs-core by openmrs.

the class ObsServiceImpl method handleExistingObsWithComplexConcept.

private void handleExistingObsWithComplexConcept(Obs obs) {
    ComplexData complexData = obs.getComplexData();
    Concept concept = obs.getConcept();
    if (null != concept && concept.isComplex() && null != complexData && null != complexData.getData()) {
        // save or update complexData object on this obs
        // this is done before the database save so that the obs.valueComplex
        // can be filled in by the handler.
        ComplexObsHandler handler = getHandler(obs);
        if (null != handler) {
            handler.saveObs(obs);
        } else {
            throw new APIException("unknown.handler", new Object[] { concept });
        }
    }
}
Also used : Concept(org.openmrs.Concept) APIException(org.openmrs.api.APIException) ComplexData(org.openmrs.obs.ComplexData) ComplexObsHandler(org.openmrs.obs.ComplexObsHandler)

Example 8 with ComplexData

use of org.openmrs.obs.ComplexData in project openmrs-core by openmrs.

the class ORUR01Handler method parseObs.

/**
 * Creates the Obs pojo from the OBX message
 *
 * @param encounter The Encounter object this Obs is a member of
 * @param obx The hl7 obx message
 * @param obr The parent hl7 or message
 * @param uid unique string for this message for any error reporting purposes
 * @return Obs pojo with all values filled in
 * @throws HL7Exception if there is a parsing exception
 * @throws ProposingConceptException if the answer to this obs is a proposed concept
 * @should add comments to an observation from NTE segments
 * @should add multiple comments for an observation as one comment
 * @should add comments to an observation group
 */
private Obs parseObs(Encounter encounter, OBX obx, OBR obr, String uid) throws HL7Exception, ProposingConceptException {
    if (log.isDebugEnabled()) {
        log.debug("parsing observation: " + obx);
    }
    Varies[] values = obx.getObservationValue();
    // bail out if no values were found
    if (values == null || values.length < 1) {
        return null;
    }
    String hl7Datatype = values[0].getName();
    if (log.isDebugEnabled()) {
        log.debug("  datatype = " + hl7Datatype);
    }
    Concept concept = getConcept(obx.getObservationIdentifier(), uid);
    if (log.isDebugEnabled()) {
        log.debug("  concept = " + concept.getConceptId());
    }
    ConceptName conceptName = getConceptName(obx.getObservationIdentifier());
    if (log.isDebugEnabled()) {
        log.debug("  concept-name = " + conceptName);
    }
    Date datetime = getDatetime(obx);
    if (log.isDebugEnabled()) {
        log.debug("  timestamp = " + datetime);
    }
    if (datetime == null) {
        datetime = encounter.getEncounterDatetime();
    }
    Obs obs = new Obs();
    obs.setPerson(encounter.getPatient());
    obs.setConcept(concept);
    obs.setEncounter(encounter);
    obs.setObsDatetime(datetime);
    obs.setLocation(encounter.getLocation());
    obs.setCreator(encounter.getCreator());
    obs.setDateCreated(encounter.getDateCreated());
    // set comments if there are any
    StringBuilder comments = new StringBuilder();
    ORU_R01_OBSERVATION parent = (ORU_R01_OBSERVATION) obx.getParent();
    // iterate over all OBX NTEs
    for (int i = 0; i < parent.getNTEReps(); i++) {
        for (FT obxComment : parent.getNTE(i).getComment()) {
            if (comments.length() > 0) {
                comments.append(" ");
            }
            comments = comments.append(obxComment.getValue());
        }
    }
    // only set comments if there are any
    if (StringUtils.hasText(comments.toString())) {
        obs.setComment(comments.toString());
    }
    Type obx5 = values[0].getData();
    if ("NM".equals(hl7Datatype)) {
        String value = ((NM) obx5).getValue();
        if (value == null || value.length() == 0) {
            log.warn("Not creating null valued obs for concept " + concept);
            return null;
        } else if ("0".equals(value) || "1".equals(value)) {
            concept = concept.hydrate(concept.getConceptId().toString());
            obs.setConcept(concept);
            if (concept.getDatatype().isBoolean()) {
                obs.setValueBoolean("1".equals(value));
            } else if (concept.getDatatype().isNumeric()) {
                try {
                    obs.setValueNumeric(Double.valueOf(value));
                } catch (NumberFormatException e) {
                    throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.notnumericConcept", new Object[] { value, concept.getConceptId(), conceptName.getName(), uid }, null), e);
                }
            } else if (concept.getDatatype().isCoded()) {
                Concept answer = "1".equals(value) ? Context.getConceptService().getTrueConcept() : Context.getConceptService().getFalseConcept();
                boolean isValidAnswer = false;
                Collection<ConceptAnswer> conceptAnswers = concept.getAnswers();
                if (conceptAnswers != null && !conceptAnswers.isEmpty()) {
                    for (ConceptAnswer conceptAnswer : conceptAnswers) {
                        if (conceptAnswer.getAnswerConcept().getId().equals(answer.getId())) {
                            obs.setValueCoded(answer);
                            isValidAnswer = true;
                            break;
                        }
                    }
                }
                // answer the boolean answer concept was't found
                if (!isValidAnswer) {
                    throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.invalidAnswer", new Object[] { answer.toString(), uid }, null));
                }
            } else {
                // throw this exception to make sure that the handler doesn't silently ignore bad hl7 message
                throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.CannotSetBoolean", new Object[] { obs.getConcept().getConceptId() }, null));
            }
        } else {
            try {
                obs.setValueNumeric(Double.valueOf(value));
            } catch (NumberFormatException e) {
                throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.notnumericConcept", new Object[] { value, concept.getConceptId(), conceptName.getName(), uid }, null), e);
            }
        }
    } else if ("CWE".equals(hl7Datatype)) {
        log.debug("  CWE observation");
        CWE value = (CWE) obx5;
        String valueIdentifier = value.getIdentifier().getValue();
        log.debug("    value id = " + valueIdentifier);
        String valueName = value.getText().getValue();
        log.debug("    value name = " + valueName);
        if (isConceptProposal(valueIdentifier)) {
            if (log.isDebugEnabled()) {
                log.debug("Proposing concept");
            }
            throw new ProposingConceptException(concept, valueName);
        } else {
            log.debug("    not proposal");
            try {
                Concept valueConcept = getConcept(value, uid);
                obs.setValueCoded(valueConcept);
                if (HL7Constants.HL7_LOCAL_DRUG.equals(value.getNameOfAlternateCodingSystem().getValue())) {
                    Drug valueDrug = new Drug();
                    valueDrug.setDrugId(Integer.valueOf(value.getAlternateIdentifier().getValue()));
                    obs.setValueDrug(valueDrug);
                } else {
                    ConceptName valueConceptName = getConceptName(value);
                    if (valueConceptName != null) {
                        if (log.isDebugEnabled()) {
                            log.debug("    value concept-name-id = " + valueConceptName.getConceptNameId());
                            log.debug("    value concept-name = " + valueConceptName.getName());
                        }
                        obs.setValueCodedName(valueConceptName);
                    }
                }
            } catch (NumberFormatException e) {
                throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.InvalidConceptId", new Object[] { valueIdentifier, valueName }, null));
            }
        }
        if (log.isDebugEnabled()) {
            log.debug("  Done with CWE");
        }
    } else if ("CE".equals(hl7Datatype)) {
        CE value = (CE) obx5;
        String valueIdentifier = value.getIdentifier().getValue();
        String valueName = value.getText().getValue();
        if (isConceptProposal(valueIdentifier)) {
            throw new ProposingConceptException(concept, valueName);
        } else {
            try {
                obs.setValueCoded(getConcept(value, uid));
                obs.setValueCodedName(getConceptName(value));
            } catch (NumberFormatException e) {
                throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.InvalidConceptId", new Object[] { valueIdentifier, valueName }, null));
            }
        }
    } else if ("DT".equals(hl7Datatype)) {
        DT value = (DT) obx5;
        if (value != null) {
            Date valueDate = getDate(value.getYear(), value.getMonth(), value.getDay(), 0, 0, 0);
            obs.setValueDatetime(valueDate);
        } else {
            log.warn("Not creating null valued obs for concept " + concept);
            return null;
        }
    } else if ("TS".equals(hl7Datatype)) {
        DTM value = ((TS) obx5).getTime();
        if (value != null) {
            Date valueDate = getDate(value.getYear(), value.getMonth(), value.getDay(), value.getHour(), value.getMinute(), value.getSecond());
            obs.setValueDatetime(valueDate);
        } else {
            log.warn("Not creating null valued obs for concept " + concept);
            return null;
        }
    } else if ("TM".equals(hl7Datatype)) {
        TM value = (TM) obx5;
        if (value != null) {
            Date valueTime = getDate(0, 0, 0, value.getHour(), value.getMinute(), value.getSecond());
            obs.setValueDatetime(valueTime);
        } else {
            log.warn("Not creating null valued obs for concept " + concept);
            return null;
        }
    } else if ("ST".equals(hl7Datatype)) {
        ST value = (ST) obx5;
        if (value == null || value.getValue() == null || value.getValue().trim().length() == 0) {
            log.warn("Not creating null valued obs for concept " + concept);
            return null;
        }
        obs.setValueText(value.getValue());
    } else if ("ED".equals(hl7Datatype)) {
        ED value = (ED) obx5;
        if (value == null || value.getData() == null || !StringUtils.hasText(value.getData().getValue())) {
            log.warn("Not creating null valued obs for concept " + concept);
            return null;
        }
        // we need to hydrate the concept so that the EncounterSaveHandler
        // doesn't fail since it needs to check if it is a concept numeric
        Concept c = Context.getConceptService().getConcept(obs.getConcept().getConceptId());
        obs.setConcept(c);
        String title = null;
        if (obs.getValueCodedName() != null) {
            title = obs.getValueCodedName().getName();
        }
        if (!StringUtils.hasText(title)) {
            title = c.getName().getName();
        }
        obs.setComplexData(new ComplexData(title, value.getData().getValue()));
    } else {
        // do we need to support BIT just in case it slips thru?
        throw new HL7Exception(Context.getMessageSourceService().getMessage("ORUR01.error.UpsupportedObsType", new Object[] { hl7Datatype }, null));
    }
    return obs;
}
Also used : FT(ca.uhn.hl7v2.model.v25.datatype.FT) CWE(ca.uhn.hl7v2.model.v25.datatype.CWE) DT(ca.uhn.hl7v2.model.v25.datatype.DT) ComplexData(org.openmrs.obs.ComplexData) ConceptName(org.openmrs.ConceptName) ED(ca.uhn.hl7v2.model.v25.datatype.ED) Concept(org.openmrs.Concept) ORU_R01_OBSERVATION(ca.uhn.hl7v2.model.v25.group.ORU_R01_OBSERVATION) Drug(org.openmrs.Drug) Obs(org.openmrs.Obs) ST(ca.uhn.hl7v2.model.v25.datatype.ST) CE(ca.uhn.hl7v2.model.v25.datatype.CE) ConceptAnswer(org.openmrs.ConceptAnswer) Date(java.util.Date) RelationshipType(org.openmrs.RelationshipType) EncounterType(org.openmrs.EncounterType) Type(ca.uhn.hl7v2.model.Type) PersonAttributeType(org.openmrs.PersonAttributeType) HL7Exception(ca.uhn.hl7v2.HL7Exception) Collection(java.util.Collection) TM(ca.uhn.hl7v2.model.v25.datatype.TM) DTM(ca.uhn.hl7v2.model.v25.datatype.DTM) DTM(ca.uhn.hl7v2.model.v25.datatype.DTM) Varies(ca.uhn.hl7v2.model.Varies) NM(ca.uhn.hl7v2.model.v25.datatype.NM) TS(ca.uhn.hl7v2.model.v25.datatype.TS)

Example 9 with ComplexData

use of org.openmrs.obs.ComplexData in project openmrs-core by openmrs.

the class ImageHandler method getObs.

/**
 * Currently supports all views and puts the Image file data into the ComplexData object
 *
 * @see org.openmrs.obs.ComplexObsHandler#getObs(org.openmrs.Obs, java.lang.String)
 */
@Override
public Obs getObs(Obs obs, String view) {
    File file = getComplexDataFile(obs);
    // Raw image
    if (ComplexObsHandler.RAW_VIEW.equals(view)) {
        BufferedImage img = null;
        try {
            img = ImageIO.read(file);
        } catch (IOException e) {
            log.error("Trying to read file: " + file.getAbsolutePath(), e);
        }
        ComplexData complexData = new ComplexData(file.getName(), img);
        String mimeType = null;
        // Image MIME type
        try {
            FileImageInputStream imgStream = new FileImageInputStream(file);
            Iterator<ImageReader> imgReader = ImageIO.getImageReaders(imgStream);
            imgStream.close();
            if (imgReader.hasNext()) {
                mimeType = "image/" + imgReader.next().getFormatName().toLowerCase();
            } else {
                log.warn("MIME type of " + file.getAbsolutePath() + " is not known");
            }
        } catch (FileNotFoundException e) {
            log.error("Image " + file.getAbsolutePath() + " was not found", e);
        } catch (IOException e) {
            log.error("Trying to determine MIME type of " + file.getAbsolutePath(), e);
        }
        // If the mimetype is still null, determine it via getFileMimeType()
        mimeType = mimeType != null ? mimeType : OpenmrsUtil.getFileMimeType(file);
        complexData.setMimeType(mimeType);
        obs.setComplexData(complexData);
    } else {
        // NOTE: if adding support for another view, don't forget to update supportedViews list above
        return null;
    }
    return obs;
}
Also used : FileImageInputStream(javax.imageio.stream.FileImageInputStream) ComplexData(org.openmrs.obs.ComplexData) FileNotFoundException(java.io.FileNotFoundException) IOException(java.io.IOException) ImageReader(javax.imageio.ImageReader) File(java.io.File) BufferedImage(java.awt.image.BufferedImage)

Example 10 with ComplexData

use of org.openmrs.obs.ComplexData in project openmrs-core by openmrs.

the class BinaryStreamHandler method getObs.

/**
 * Returns the same ComplexData for all views. The title is the original filename, and the data
 * is the raw byte[] of data (If the view is set to "download", all commas and whitespace are
 * stripped out of the filename to fix an issue where the browser wasn't handling a filename
 * with whitespace properly) Note that if the method cannot find the file associated with the
 * obs, it returns the obs with the ComplexData = null
 *
 * @see ComplexObsHandler#getObs(Obs, String)
 */
@Override
public Obs getObs(Obs obs, String view) {
    ComplexData complexData = null;
    File file = null;
    // Raw stream
    if (ComplexObsHandler.RAW_VIEW.equals(view)) {
        try {
            file = getComplexDataFile(obs);
            String[] names = obs.getValueComplex().split("\\|");
            String originalFilename = names[0];
            originalFilename = originalFilename.replace(",", "").replace(" ", "");
            if (file.exists()) {
                FileInputStream fileInputStream = new FileInputStream(file);
                complexData = new ComplexData(originalFilename, fileInputStream);
            } else {
                log.error("Unable to find file associated with complex obs " + obs.getId());
            }
        } catch (Exception e) {
            throw new APIException("Obs.error.while.trying.get.binary.complex", null, e);
        }
    } else {
        // NOTE: if adding support for another view, don't forget to update supportedViews list above
        return null;
    }
    Assert.notNull(complexData, "Complex data must not be null");
    // Get the Mime Type and set it
    String mimeType = OpenmrsUtil.getFileMimeType(file);
    complexData.setMimeType(mimeType);
    obs.setComplexData(complexData);
    return obs;
}
Also used : APIException(org.openmrs.api.APIException) ComplexData(org.openmrs.obs.ComplexData) File(java.io.File) FileInputStream(java.io.FileInputStream) APIException(org.openmrs.api.APIException)

Aggregations

ComplexData (org.openmrs.obs.ComplexData)14 File (java.io.File)11 IOException (java.io.IOException)7 Date (java.util.Date)5 Concept (org.openmrs.Concept)5 Reader (java.io.Reader)4 Obs (org.openmrs.Obs)4 APIException (org.openmrs.api.APIException)4 CharArrayReader (java.io.CharArrayReader)3 Test (org.junit.Test)3 Location (org.openmrs.Location)3 Person (org.openmrs.Person)3 BaseContextSensitiveTest (org.openmrs.test.BaseContextSensitiveTest)3 FileInputStream (java.io.FileInputStream)2 FileNotFoundException (java.io.FileNotFoundException)2 FileOutputStream (java.io.FileOutputStream)2 HL7Exception (ca.uhn.hl7v2.HL7Exception)1 Type (ca.uhn.hl7v2.model.Type)1 Varies (ca.uhn.hl7v2.model.Varies)1 CE (ca.uhn.hl7v2.model.v25.datatype.CE)1