package net.sourceforge.seqware.common.dao.hibernate; import java.lang.reflect.InvocationTargetException; import java.util.ArrayList; import java.util.Collection; import java.util.HashSet; import java.util.List; import java.util.Set; import net.sourceforge.seqware.common.dao.WorkflowRunDAO; import net.sourceforge.seqware.common.model.IUS; import net.sourceforge.seqware.common.model.Processing; import net.sourceforge.seqware.common.model.Registration; import net.sourceforge.seqware.common.model.Workflow; import net.sourceforge.seqware.common.model.WorkflowRun; import net.sourceforge.seqware.common.util.NullBeanUtils; import org.apache.commons.beanutils.BeanUtilsBean; import org.hibernate.Query; import org.hibernate.SQLQuery; import org.hibernate.Session; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import org.springframework.dao.DataAccessResourceFailureException; import org.springframework.orm.hibernate3.support.HibernateDaoSupport; /** * <p> * WorkflowRunDAOHibernate class. * </p> * * @author boconnor * @version $Id: $Id */ public class WorkflowRunDAOHibernate extends HibernateDaoSupport implements WorkflowRunDAO { final Logger localLogger = LoggerFactory.getLogger(WorkflowRunDAOHibernate.class); /** * <p> * Constructor for WorkflowRunDAOHibernate. * </p> */ public WorkflowRunDAOHibernate() { super(); } /** {@inheritDoc} */ @Override public Integer insert(WorkflowRun workflowRun) { this.getHibernateTemplate().save(workflowRun); this.getSession().flush(); return workflowRun.getSwAccession(); } /** {@inheritDoc} */ @Override public void update(WorkflowRun workflowRun) { getHibernateTemplate().update(workflowRun); getSession().flush(); } /** {@inheritDoc} */ @Override public void delete(WorkflowRun workflowRun) { getHibernateTemplate().delete(workflowRun); } /** * <p> * update. * </p> * * @param workflowRun * a {@link net.sourceforge.seqware.common.model.WorkflowRun} object. * @param laneIds * a {@link java.util.List} object. */ @Override public void update(WorkflowRun workflowRun, List<Integer> laneIds) { String paramQuery = ""; for (int i = 0; i < laneIds.size() - 1; i++) { paramQuery = paramQuery + "?,"; } paramQuery = paramQuery + "?"; String query = "update processing set workflow_id=? where processing_id in " + "(select processing_id from processing_lanes where lane_id in (" + paramQuery + ") )"; SQLQuery sql = this.getSession().createSQLQuery(query); sql.setInteger(0, workflowRun.getWorkflowRunId()); for (int i = 0; i < laneIds.size(); i++) { sql.setInteger(i + 1, laneIds.get(i)); } sql.executeUpdate(); getSession().flush(); } /** * <p> * list. * </p> * * @return a {@link java.util.List} object. */ @Override public List<WorkflowRun> list() { ArrayList<WorkflowRun> workflowRuns = new ArrayList<>(); // Limit the workflows to those owned by the user String query = "from WorkflowRun as workflowRun order by workflowRun.createTimestamp desc"; // Object[] parameters = { registration.getRegistrationId() }; Session s = getSessionFactory().getCurrentSession(); SQLQuery sqlquery = s.createSQLQuery("select workflow_run_id, workflow_id, owner_id, name, ini_file, cmd, " + " workflow_template, status, status_cmd, seqware_revision, host, current_working_dir, " + "username, create_tstmp, update_tstmp, sw_accession, stderr, stdout, workflow_engine from workflow_run"); sqlquery.addEntity(WorkflowRun.class); List list = sqlquery.list(); for (Object obj : list) { WorkflowRun run = (WorkflowRun) obj; workflowRuns.add(run); s.clear(); } return workflowRuns; } /** {@inheritDoc} */ @Override public List<WorkflowRun> list(Registration registration, Boolean isAsc) { ArrayList<WorkflowRun> workflowRuns = new ArrayList<>(); localLogger.debug("Get WFR LIST. " + registration.getEmailAddress()); /* * Criteria criteria = this.getSession().createCriteria(Study.class); criteria.add(Expression.eq("owner_id", * registration.getRegistrationId())); criteria.addOrder(Order.asc("create_tstmp")); criteria.setFirstResult(100); * criteria.setMaxResults(50); List pageResults=criteria.list(); */ String query; Object[] parameters = { registration.getRegistrationId() }; String sortValue = (!isAsc) ? "asc" : "desc"; // Limit the workflows to those owned by the user if (registration.isLIMSAdmin()) { query = "from WorkflowRun as workflowRun " + "where workflowRun.status='completed' " + "order by workflowRun.createTimestamp " + sortValue; parameters = null; } else { query = "from WorkflowRun as workflowRun " + "where workflowRun.owner.registrationId=? and workflowRun.status='completed' " + "order by workflowRun.createTimestamp " + sortValue; } List list = this.getHibernateTemplate().find(query, parameters); for (Object workflowRun : list) { workflowRuns.add((WorkflowRun) workflowRun); } return workflowRuns; } /** {@inheritDoc} */ @Override public List<Workflow> listRelatedWorkflows(Registration registration) { String querySQL = "select distinct wr.workflow from WorkflowRun as wr where wr.owner.registrationId = ?"; Object[] parameters = { registration.getRegistrationId() }; List list = this.getHibernateTemplate().find(querySQL, parameters); List<Workflow> workflows = new ArrayList<>(); for (Object workflow : list) { workflows.add((Workflow) workflow); } return workflows; } /** {@inheritDoc} */ @Override public List<WorkflowRun> listMyShared(Registration registration, Boolean isAsc) { List<WorkflowRun> sharedWorkflowRuns = new ArrayList<>(); String sortValue = (!isAsc) ? "asc" : "desc"; String query = "from WorkflowRun as workflowRun where workflowRun.owner.registrationId=? " + "and workflowRun.sharedWorkflowRuns.size > 0 " + "order by workflowRun.createTimestamp " + sortValue; Object[] parameters = { registration.getRegistrationId() }; List list = this.getHibernateTemplate().find(query, parameters); for (Object workflowRun : list) { sharedWorkflowRuns.add((WorkflowRun) workflowRun); } return sharedWorkflowRuns; } /** {@inheritDoc} */ @Override public List<WorkflowRun> listSharedWithMe(Registration registration, Boolean isAsc) { List<WorkflowRun> sharedWithMeWorkflowRuns = new ArrayList<>(); if (registration == null) { return sharedWithMeWorkflowRuns; } String sortValue = (!isAsc) ? "asc" : "desc"; String query = "select workflowRun from WorkflowRun as workflowRun " + "inner join workflowRun.sharedWorkflowRuns as runs " + "where runs.registration.registrationId = ? " + "order by workflowRun.createTimestamp " + sortValue; Object[] parameters = { registration.getRegistrationId() }; List list = this.getHibernateTemplate().find(query, parameters); for (Object workflowRun : list) { sharedWithMeWorkflowRuns.add((WorkflowRun) workflowRun); } return sharedWithMeWorkflowRuns; } /** {@inheritDoc} */ @Override public List<WorkflowRun> listRunning(Registration registration, Boolean isAsc) { List<WorkflowRun> runningWorkflowRuns = new ArrayList<>(); String query; Object[] parameters = { registration.getRegistrationId() }; String sortValue = (!isAsc) ? "asc" : "desc"; if (registration.isLIMSAdmin()) { query = "from WorkflowRun as workflowRun " + "where workflowRun.status<>'completed' " + "order by workflowRun.createTimestamp " + sortValue; parameters = null; } else { query = "from WorkflowRun as workflowRun " + "where workflowRun.owner.registrationId=? and workflowRun.status<>'completed' " + "order by workflowRun.createTimestamp " + sortValue; } List list = this.getHibernateTemplate().find(query, parameters); for (Object workflowRun : list) { runningWorkflowRuns.add((WorkflowRun) workflowRun); } return runningWorkflowRuns; } /** {@inheritDoc} */ @Override public WorkflowRun findByName(String name) { String query = "from WorkflowRun as workflowRun where workflowRun.name = ?"; WorkflowRun workflowRun = null; Object[] parameters = { name }; List list = this.getHibernateTemplate().find(query, parameters); if (list.size() > 0) { workflowRun = (WorkflowRun) list.get(0); } return workflowRun; } /** {@inheritDoc} */ @Override public WorkflowRun findByID(Integer wfrID) { String query = "from WorkflowRun as workflowRun where workflowRun.workflowRunId = ?"; WorkflowRun workflowRun = null; Object[] parameters = { wfrID }; List list = this.getHibernateTemplate().find(query, parameters); if (list.size() > 0) { workflowRun = (WorkflowRun) list.get(0); } return workflowRun; } /** {@inheritDoc} */ @SuppressWarnings("unchecked") @Override public WorkflowRun findBySWAccession(Integer swAccession) { String query = "from WorkflowRun as workflowRun where workflowRun.swAccession = ?"; WorkflowRun workflowRun = null; Object[] parameters = { swAccession }; List<WorkflowRun> list = this.getHibernateTemplate().find(query, parameters); if (list.size() > 0) { workflowRun = (WorkflowRun) list.get(0); } return workflowRun; } /** {@inheritDoc} */ @SuppressWarnings("unchecked") @Override public List<WorkflowRun> findByOwnerID(Integer registrationID) { String query = "from WorkflowRun as workflowRun where workflowRun.owner.registrationId = ?"; Object[] parameters = { registrationID }; return this.getHibernateTemplate().find(query, parameters); } /** {@inheritDoc} */ @SuppressWarnings("unchecked") @Override public List<WorkflowRun> findByCriteria(String criteria, boolean isCaseSens) { String queryStringCase = "from WorkflowRun as wr where cast(wr.swAccession as string) like :sw " + " or wr.name like :name order by wr.name"; String queryStringICase = "from WorkflowRun as wr where cast(wr.swAccession as string) like :sw " + " or lower(wr.name) like :name order by wr.name"; Query query = isCaseSens ? this.getSession().createQuery(queryStringCase) : this.getSession().createQuery(queryStringICase); if (!isCaseSens) { criteria = criteria.toLowerCase(); } criteria = "%" + criteria + "%"; query.setString("sw", criteria); query.setString("name", criteria); return query.list(); } /** {@inheritDoc} */ @SuppressWarnings("rawtypes") @Override public Set<WorkflowRun> findRunsForIUS(IUS ius) { Set<WorkflowRun> wfRuns = new HashSet<>(); // wfRuns.addAll(ius.getWorkflowRuns()); // Set<Processing> processings = ius.getProcessings(); // // for (Processing processing : processings) { // wfRuns.addAll(workflowRunFromProcessing(processing)); // } String query = "WITH RECURSIVE Rec(pid, id) AS (" + " SELECT pr.parent_id, pr.child_id" + " FROM processing_relationship pr" + " JOIN processing_ius pi" + " ON (pr.parent_id = pi.processing_id)" + " WHERE pi.ius_id = ?" + " UNION" + " SELECT null, pi.processing_id" + " FROM processing_ius pi" + " WHERE pi.ius_id = ?" + " UNION" + " SELECT r.pid, sr.child_id FROM Rec r" + " JOIN processing_relationship sr" + " ON (r.id = sr.parent_id)" + ")" + " SELECT wr.* FROM Rec r" + " JOIN processing p" + " ON (p.processing_id = r.id)" + " JOIN workflow_run wr ON (p.workflow_run_id = wr.workflow_run_id)"; List list = this.getSession().createSQLQuery(query).addEntity(WorkflowRun.class).setInteger(0, ius.getIusId()) .setInteger(1, ius.getIusId()).list(); for (Object wfRunObj : list) { WorkflowRun wfRun = (WorkflowRun) wfRunObj; wfRuns.add(wfRun); } wfRuns.addAll(ius.getWorkflowRuns()); return wfRuns; } private Collection<? extends WorkflowRun> workflowRunFromProcessing(Processing processing) { Set<WorkflowRun> wfRuns = new HashSet<>(); if (processing.getWorkflowRun() != null) { wfRuns.add(processing.getWorkflowRun()); } for (Processing child : processing.getChildren()) { wfRuns.addAll(workflowRunFromProcessing(child)); } return wfRuns; } /** {@inheritDoc} */ @Override public WorkflowRun updateDetached(WorkflowRun workflowRun) { WorkflowRun dbWf = reattachWorkflowRun(workflowRun); try { BeanUtilsBean beanUtils = new NullBeanUtils(); beanUtils.copyProperties(dbWf, workflowRun); return (WorkflowRun) this.getHibernateTemplate().merge(dbWf); } catch (IllegalAccessException | InvocationTargetException e) { localLogger.error("Error updating detached WorkflowRun", e); } return null; } /** {@inheritDoc} */ @Override public List<WorkflowRun> findByCriteria(String criteria) { /* * Not sure why this doesn't work but I think the :sw sub is only good for a value and not an HQL phrase String queryStringCase = * "from WorkflowRun as wr where :sw"; Query query = this.getSession().createQuery(queryStringCase); query.setString("sw", * criteria); */ String queryStringCase = "from WorkflowRun as wr where "; Query query = this.getSession().createQuery(queryStringCase + " " + criteria); return query.list(); } /** {@inheritDoc} */ @Override public void update(Registration registration, WorkflowRun workflowRun) { WorkflowRun dbWf = reattachWorkflowRun(workflowRun); if (registration == null) { localLogger.error("WorkflowRunDAOHibernate update registration is null"); } else if (registration.isLIMSAdmin() || (dbWf.givesPermission(registration) && workflowRun.givesPermission(registration))) { localLogger.info("Updating workflow run object"); update(workflowRun); } else { localLogger.error("WorkflowRunDAOHibernate update not authorized"); } } /** {@inheritDoc} */ @Override public Integer insert(Registration registration, WorkflowRun workflowRun) { if (registration == null) { localLogger.error("WorkflowRunDAOHibernate insert registration is null"); } else if (registration.isLIMSAdmin() || workflowRun.givesPermission(registration)) { localLogger.info("insert workflow run object"); return insert(workflowRun); } else { localLogger.error("WorkflowRunDAOHibernate insert not authorized"); } return null; } /** {@inheritDoc} */ @Override public WorkflowRun updateDetached(Registration registration, WorkflowRun workflowRun) { WorkflowRun dbWf = reattachWorkflowRun(workflowRun); if (registration == null) { localLogger.error("WorkflowRunDAOHibernate updateDetached registration is null"); } else if (registration.isLIMSAdmin() || dbWf.givesPermission(registration)) { localLogger.info("updateDetached workflow run object"); return updateDetached(workflowRun); } else { localLogger.error("WorkflowRunDAOHibernate updateDetached not authorized"); } return null; } private WorkflowRun reattachWorkflowRun(WorkflowRun workflowRun) throws IllegalStateException, DataAccessResourceFailureException { WorkflowRun dbObject = workflowRun; if (!getSession().contains(workflowRun)) { dbObject = findByID(workflowRun.getWorkflowRunId()); } return dbObject; } }