edu.harvard.i2b2.crc.ejb.QueryManagerBean.java Source code

Java tutorial

Introduction

Here is the source code for edu.harvard.i2b2.crc.ejb.QueryManagerBean.java

Source

/*
 * Copyright (c) 2006-2007 Massachusetts General Hospital 
 * All rights reserved. This program and the accompanying materials 
 * are made available under the terms of the i2b2 Software License v1.0 
 * which accompanies this distribution. 
 * 
 * Contributors: 
 *     Rajesh Kuttan
 */
package edu.harvard.i2b2.crc.ejb;

import java.io.StringWriter;
import java.rmi.RemoteException;
import java.util.Date;
import java.util.Map;

import javax.xml.bind.JAXBElement;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.springframework.beans.factory.BeanFactory;

import edu.harvard.i2b2.common.exception.I2B2DAOException;
import edu.harvard.i2b2.common.exception.I2B2Exception;
import edu.harvard.i2b2.common.util.jaxb.JAXBUnWrapHelper;
import edu.harvard.i2b2.common.util.jaxb.JAXBUtil;
import edu.harvard.i2b2.crc.dao.DAOFactoryHelper;
import edu.harvard.i2b2.crc.dao.IDAOFactory;
import edu.harvard.i2b2.crc.dao.SetFinderDAOFactory;
import edu.harvard.i2b2.crc.dao.setfinder.IQueryInstanceDao;
import edu.harvard.i2b2.crc.dao.setfinder.IQueryMasterDao;
import edu.harvard.i2b2.crc.dao.setfinder.IQueryResultInstanceDao;
import edu.harvard.i2b2.crc.datavo.CRCJAXBUtil;
import edu.harvard.i2b2.crc.datavo.PSMFactory;
import edu.harvard.i2b2.crc.datavo.db.DataSourceLookup;
import edu.harvard.i2b2.crc.datavo.db.QtQueryInstance;
import edu.harvard.i2b2.crc.datavo.db.QtQueryMaster;
import edu.harvard.i2b2.crc.datavo.i2b2message.BodyType;
import edu.harvard.i2b2.crc.datavo.i2b2message.PasswordType;
import edu.harvard.i2b2.crc.datavo.i2b2message.RequestMessageType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.InstanceResultResponseType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.MasterInstanceResultResponseType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.QueryDefinitionRequestType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.QueryDefinitionType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.QueryInstanceType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.QueryMasterType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.ResultOutputOptionListType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.ResultOutputOptionType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.ResultResponseType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.StatusType;
import edu.harvard.i2b2.crc.datavo.setfinder.query.StatusType.Condition;
import edu.harvard.i2b2.crc.datavo.setfinder.query.UserType;
import edu.harvard.i2b2.crc.delegate.pm.CallPMUtil;
import edu.harvard.i2b2.crc.util.QueryProcessorUtil;

/**
 * Ejb manager class for query operation
 * 
 * @author rkuttan
 * 
 * @ejb.bean description="QueryTool Query Manager"
 *           display-name="QueryTool Query Manager"
 *           jndi-name="ejb.querytool.QueryManager"
 *           local-jndi-name="ejb.querytool.QueryManagerLocal"
 *           name="querytool.QueryManager" type="Stateless" view-type="both"
 *           transaction-type="Bean"
 * 
 * @ejb.transaction type="Required"
 * 
 * 
 * @ejb.interface remote-class="edu.harvard.i2b2.crc.ejb.QueryManagerRemote"
 * 
 * 
 */
public class QueryManagerBean { // implements SessionBean {
    private static Log log = LogFactory.getLog(QueryManagerBean.class);
    public static String RESPONSE_QUEUE_NAME = "queue/jms.querytool.QueryResponse";
    // public static String UPLOADPROCESSOR_QUEUE_NAME =
    // "queue/jms.querytool.QueryExecutor";

    //   SessionContext context;

    /**
     * Function to publish patients using publish message format.
     * 
     * @ejb.interface-method view-type="both"
     * @ejb.transaction type="Required"
     * 
     * @param String
     *            publish request XML fileName
     * 
     * @return String publish response XML
     * @throws Exception 
     */
    public MasterInstanceResultResponseType processQuery(DataSourceLookup dataSourceLookup, String xmlRequest)
            throws Exception {
        String responseXML = null;

        MasterInstanceResultResponseType masterInstanceResultType = null;

        try {
            String sessionId = String.valueOf(System.currentTimeMillis());
            QueryManagerBeanUtil qmBeanUtil = new QueryManagerBeanUtil();
            long timeout = qmBeanUtil.getTimeout(xmlRequest);

            DataSourceLookup dsLookupInput = qmBeanUtil.getDataSourceLookupInput(xmlRequest);
            SetFinderDAOFactory sfDAOFactory = null;
            // tm.begin();
            //         transaction.begin();
            if (dsLookupInput.getProjectPath() == null) {
                throw new I2B2Exception("project id is missing in the request");
            }
            DAOFactoryHelper daoFactoryHelper = new DAOFactoryHelper(dsLookupInput.getDomainId(),
                    dsLookupInput.getProjectPath(), dsLookupInput.getOwnerId());
            IDAOFactory daoFactory = daoFactoryHelper.getDAOFactory();
            sfDAOFactory = daoFactory.getSetFinderDAOFactory();

            String generatedSql = null;
            RequestMessageType requestMsgType = this.getI2B2RequestType(xmlRequest);
            String queryMasterId = saveQuery(sfDAOFactory, requestMsgType, generatedSql);

            // create query instance
            IQueryInstanceDao queryInstanceDao = sfDAOFactory.getQueryInstanceDAO();

            UserType userType = getUserTypeFromSetfinderHeader(requestMsgType);
            String userId = userType.getLogin();
            String groupId = userType.getGroup();
            String queryInstanceId = queryInstanceDao.createQueryInstance(queryMasterId, userId, groupId,
                    "SMALL_QUEUE", 5);
            //               QueryExecutorMDB.SMALL_QUEUE, 5);
            log.debug("New Query instance id " + queryInstanceId);

            IQueryResultInstanceDao patientSetResultDao = sfDAOFactory.getPatientSetResultDAO();
            String patientSetId = null;
            QueryDefinitionRequestType queryDefRequestType = getQueryDefinitionRequestType(requestMsgType);
            ResultOutputOptionListType resultOptionList = queryDefRequestType.getResultOutputList();

            if (resultOptionList != null && resultOptionList.getResultOutput() != null
                    && resultOptionList.getResultOutput().size() > 0) {
                for (ResultOutputOptionType resultOption : resultOptionList.getResultOutput()) {

                    patientSetId = patientSetResultDao.createPatientSet(queryInstanceId, resultOption.getName());
                    log.debug("Patient Set ID [" + patientSetId + "] for query instance= " + queryInstanceId);
                }
            } else {
                QueryProcessorUtil qp = QueryProcessorUtil.getInstance();
                BeanFactory bf = qp.getSpringBeanFactory();
                String defaultResultType = (String) bf
                        .getBean(QueryProcessorUtil.DEFAULT_SETFINDER_RESULT_BEANNAME);
                patientSetId = patientSetResultDao.createPatientSet(queryInstanceId, defaultResultType);
                log.debug("Patient Set ID [" + patientSetId + "] for query instance= " + queryInstanceId);
            }

            // tm.commit();
            //         transaction.commit();

            log.debug("getting responsetype");
            ResultResponseType responseType = executeSqlInQueue(dsLookupInput.getDomainId(),
                    dsLookupInput.getProjectPath(), dsLookupInput.getOwnerId(), userId, generatedSql, sessionId,
                    queryInstanceId, patientSetId, xmlRequest, timeout);

            //         transaction.begin();
            // responseXML = qmBeanUtil.buildQueryRequestResponse(xmlRequest,
            // status,
            // sessionId,queryMasterId,queryInstanceId,responseType);
            log.debug("after queue exectution");

            /*
             * query instance status is updated in the query executor class
             * QtQueryInstance queryInstance = updateQueryInstanceStatus(
             * sfDAOFactory, responseType, userId, queryInstanceId);
             */

            IQueryMasterDao queryMasterDao = sfDAOFactory.getQueryMasterDAO();
            QtQueryMaster queryMaster = queryMasterDao.getQueryDefinition(queryMasterId);
            masterInstanceResultType = new MasterInstanceResultResponseType();

            QueryMasterType queryMasterType = PSMFactory.buildQueryMasterType(queryMaster);
            // set query master
            masterInstanceResultType.setQueryMaster(queryMasterType);

            // fetch query instance by queryinstance id and build response
            QtQueryInstance queryInstance = queryInstanceDao.getQueryInstanceByInstanceId(queryInstanceId);
            QueryInstanceType queryInstanceType = PSMFactory.buildQueryInstanceType(queryInstance);
            // set query instance
            masterInstanceResultType.setQueryInstance(queryInstanceType);
            // set status
            masterInstanceResultType.setStatus(responseType.getStatus());

            QueryResultBean queryResultBean = new QueryResultBean();
            ResultResponseType responseType1 = queryResultBean
                    .getResultInstanceFromQueryInstanceId(dataSourceLookup, userId, queryInstanceId);

            log.debug("Size of result when called thru ejb " + responseType1.getQueryResultInstance().size());

            //If query result instanace -> query_status_type is processing that set QUEUE
            if (responseType1.getQueryResultInstance() != null && responseType1.getQueryResultInstance().get(0)
                    .getQueryStatusType().getStatusTypeId().equals("2")) {
                responseType1.getQueryResultInstance().get(0).getQueryStatusType().setStatusTypeId("1");
                responseType1.getQueryResultInstance().get(0).getQueryStatusType().setName("QUEUED");
                responseType1.getQueryResultInstance().get(0).getQueryStatusType()
                        .setDescription("WAITING IN QUEUE TO START PROCESS");
                StatusType stype = new StatusType();
                Condition e = new Condition();
                e.setType("RUNNING");
                e.setValue("RUNNING");
                stype.getCondition().add(e);
                responseType1.setStatus(stype);
            }
            // set result instance
            masterInstanceResultType.getQueryResultInstance().addAll(responseType1.getQueryResultInstance());

            //         transaction.commit();
        } catch (I2B2DAOException ex) {
            log.debug("Got an error in QueryManagerBean, thropwing: " + ex.getMessage());
            ex.printStackTrace();

            throw new I2B2Exception(ex.getMessage());
        }

        return masterInstanceResultType;
    }

    /**
     * Function to publish patients using publish message format.
     * 
     * @ejb.interface-method view-type="both"
     * @ejb.transaction type="Required"
     * 
     * @param String
     *            userId
     * @param int master id
     * @param long timeout
     * 
     * @return InstanceResultResponseType
     */
    public InstanceResultResponseType runQueryMaster(DataSourceLookup dataSourceLookup, String userId,
            String masterId, long timeout) throws I2B2Exception {
        return null;

    }

    private ResultResponseType executeSqlInQueue(String domainId, String projectId, String ownerId, String userId,
            String generatedSql, String sessionId, String queryInstanceId, String patientSetId, String xmlRequest,
            long timeout) throws Exception {

        QueryManagerBeanUtil qmBeanUtil = new QueryManagerBeanUtil();

        // process query in queue
        log.debug("process query in queue");
        Map returnValues = qmBeanUtil.testSend(domainId, projectId, ownerId, generatedSql, sessionId,
                queryInstanceId, patientSetId, xmlRequest, timeout);

        log.debug("My returnValue map is:" + returnValues);
        log.debug("My mapssize is: " + returnValues.size());
        // build response message, if query completed before given timeout
        String status = (String) returnValues.get(QueryManagerBeanUtil.QUERY_STATUS_PARAM);
        int queryResultInstanceId = (Integer) returnValues
                .get(QueryManagerBeanUtil.QT_QUERY_RESULT_INSTANCE_ID_PARAM);
        log.debug("Query Result Instance id " + queryResultInstanceId);

        log.debug("Status coming from queue : " + status);
        StatusType statusType = new StatusType();
        StatusType.Condition condition = new StatusType.Condition();
        condition.setValue(status);
        if (status != null && status.indexOf("LOCKEDOUT") > -1) {
            status = "ERROR";
        }
        condition.setType(status);
        statusType.getCondition().add(condition);
        ResultResponseType responseType = new ResultResponseType();
        responseType.setStatus(statusType);
        return responseType;
    }

    private String saveQuery(SetFinderDAOFactory sfDAOFactory, RequestMessageType i2b2RequestMsgType,
            String generatedSql) throws Exception {
        IQueryMasterDao queryMasterDao = sfDAOFactory.getQueryMasterDAO();
        QtQueryMaster queryMaster = new QtQueryMaster();
        UserType userType = getUserTypeFromSetfinderHeader(i2b2RequestMsgType);
        String userId = userType.getLogin();
        String groupId = userType.getGroup();
        QueryDefinitionType queryDefType = getQueryDefinition(i2b2RequestMsgType);
        edu.harvard.i2b2.crc.datavo.setfinder.query.ObjectFactory of = new edu.harvard.i2b2.crc.datavo.setfinder.query.ObjectFactory();

        queryMaster.setUserId(userId);
        StringWriter queryDefWriter = new StringWriter();
        CRCJAXBUtil.getQueryDefJAXBUtil().marshaller(of.createQueryDefinition(queryDefType), queryDefWriter);

        queryMaster.setRequestXml(queryDefWriter.toString());
        queryMaster.setGroupId(groupId);
        queryMaster.setCreateDate(new Date(System.currentTimeMillis()));
        queryMaster.setDeleteFlag(QtQueryMaster.DELETE_OFF_FLAG);
        queryMaster.setGeneratedSql(generatedSql);
        queryMaster.setName(queryDefType.getQueryName());

        String pmXml = CallPMUtil.callUserResponse(i2b2RequestMsgType.getMessageHeader().getSecurity(), "");

        //remove user password form the request
        PasswordType passType = i2b2RequestMsgType.getMessageHeader().getSecurity().getPassword();
        passType.setValue("password not stored");
        passType.setIsToken(false);

        JAXBUtil util = CRCJAXBUtil.getJAXBUtil();
        StringWriter strWriter = new StringWriter();
        edu.harvard.i2b2.crc.datavo.i2b2message.ObjectFactory i2b2ObjFactory = new edu.harvard.i2b2.crc.datavo.i2b2message.ObjectFactory();
        util.marshaller(i2b2ObjFactory.createRequest(i2b2RequestMsgType), strWriter);
        String queryMasterId = queryMasterDao.createQueryMaster(queryMaster, strWriter.toString(), pmXml);

        return queryMasterId;
    }

    private UserType getUserTypeFromSetfinderHeader(RequestMessageType requestMessageType) throws Exception {
        UserType userType = new UserType();
        userType.setLogin(requestMessageType.getMessageHeader().getSecurity().getUsername());
        userType.setGroup(requestMessageType.getMessageHeader().getProjectId());

        return userType;
    }

    private RequestMessageType getI2B2RequestType(String xmlRequest) throws Exception {

        JAXBUtil jaxbUtil = CRCJAXBUtil.getJAXBUtil();
        JAXBElement jaxbElement = jaxbUtil.unMashallFromString(xmlRequest);

        if (jaxbElement == null) {
            throw new Exception("null value in after unmarshalling request string ");
        }

        RequestMessageType requestMessageType = (RequestMessageType) jaxbElement.getValue();

        return requestMessageType;
    }

    private QueryDefinitionRequestType getQueryDefinitionRequestType(RequestMessageType requestMessageType)
            throws Exception {
        String queryName = null;
        QueryDefinitionType queryDef = null;

        BodyType bodyType = requestMessageType.getMessageBody();
        JAXBUnWrapHelper unWrapHelper = new JAXBUnWrapHelper();
        QueryDefinitionRequestType queryDefReqType = (QueryDefinitionRequestType) unWrapHelper
                .getObjectByClass(bodyType.getAny(), QueryDefinitionRequestType.class);
        return queryDefReqType;

    }

    public QueryDefinitionType getQueryDefinition(RequestMessageType requestMessageType) throws Exception {
        QueryDefinitionRequestType queryDefReqType = getQueryDefinitionRequestType(requestMessageType);
        QueryDefinitionType queryDef = null;
        if (queryDefReqType != null) {
            queryDef = queryDefReqType.getQueryDefinition();
        }
        return queryDef;
    }

    /**
     * Function to publish patients using publish message format.
     * 
     * @ejb.interface-method view-type="both"
     * @ejb.transaction type="Required"
     * 
     * @param int session id publish request XML fileName
     * 
     * @return String publish response XML
     */
    public String getResponseXML(String sessionId) {
        QueryManagerBeanUtil qmBeanUtil = new QueryManagerBeanUtil();
        String status = qmBeanUtil.getStatus(sessionId);
        String response = qmBeanUtil.buildGetQueryResultResponse(sessionId, status);

        return response;
    }

    /*
    public void setSessionContext(SessionContext context) throws EJBException,
     RemoteException {
       this.context = context;
    }
        
    public void ejbCreate() throws CreateException {
    }
        
    public void ejbRemove() throws EJBException, RemoteException {
    }
        
    public void ejbActivate() throws EJBException, RemoteException {
    }
        
    public void ejbPassivate() throws EJBException, RemoteException {
    }
    */
}