org.openmrs.module.reporting.web.datasets.PatientDataSetEditor.java Source code

Java tutorial

Introduction

Here is the source code for org.openmrs.module.reporting.web.datasets.PatientDataSetEditor.java

Source

/**
 * The contents of this file are subject to the OpenMRS Public License
 * Version 1.0 (the "License"); you may not use this file except in
 * compliance with the License. You may obtain a copy of the License at
 * http://license.openmrs.org
 *
 * Software distributed under the License is distributed on an "AS IS"
 * basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
 * License for the specific language governing rights and limitations
 * under the License.
 *
 * Copyright (C) OpenMRS, LLC.  All Rights Reserved.
 */
package org.openmrs.module.reporting.web.datasets;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Comparator;
import java.util.List;
import java.util.Properties;

import javax.servlet.http.HttpSession;

import org.apache.commons.lang.StringUtils;
import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;
import org.openmrs.api.context.Context;
import org.openmrs.module.htmlwidgets.web.WidgetUtil;
import org.openmrs.module.htmlwidgets.web.html.Option;
import org.openmrs.module.reporting.cohort.definition.CohortDefinition;
import org.openmrs.module.reporting.common.ObjectUtil;
import org.openmrs.module.reporting.data.DataDefinition;
import org.openmrs.module.reporting.data.patient.definition.PatientDataDefinition;
import org.openmrs.module.reporting.data.person.definition.PersonDataDefinition;
import org.openmrs.module.reporting.dataset.column.definition.RowPerObjectColumnDefinition;
import org.openmrs.module.reporting.dataset.definition.PatientDataSetDefinition;
import org.openmrs.module.reporting.dataset.definition.service.DataSetDefinitionService;
import org.openmrs.module.reporting.evaluation.parameter.Mapped;
import org.openmrs.module.reporting.evaluation.parameter.Parameter;
import org.openmrs.module.reporting.propertyeditor.MappedEditor;
import org.openmrs.module.reporting.web.util.ParameterUtil;
import org.openmrs.web.WebConstants;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.ModelAttribute;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.bind.annotation.RequestParam;
import org.springframework.web.context.request.WebRequest;

/**
 * For creating and editing {@link PatientDataSetDefinition}s
 */
@Controller
public class PatientDataSetEditor {

    public final static String DSD_ATTR = "PatientDataSetEditor_dsd";
    public final static String IS_UNSAVED_ATTR = "PatientDataSetEditor_is_unsaved";
    public final static String SUCCESS_URL_ATTR = "PatientDataSetEditor_successUrl";
    public final static String DISCARD_URL_ATTR = "PatientDataSetEditor_discardUrl";

    Log log = LogFactory.getLog(getClass());

    @ModelAttribute("dsd")
    public PatientDataSetDefinition getDataSetDefinition(
            @RequestParam(required = false, value = "uuid") String uuid,
            @RequestParam(required = false) String successUrl, @RequestParam(required = false) String discardUrl,
            HttpSession session) {
        PatientDataSetDefinition dsd = getFromSession(session);
        if (dsd != null && uuid != null && !uuid.equals(dsd.getUuid())) {
            removeFromSession(session);
            dsd = null;
        }

        if (dsd == null) {
            if (uuid != null) {
                dsd = (PatientDataSetDefinition) Context.getService(DataSetDefinitionService.class)
                        .getDefinitionByUuid(uuid);
                if (dsd == null)
                    throw new RuntimeException("No PatientDataSetDefinition found with uuid " + uuid);
                putInSession(session, dsd, false);
            } else {
                dsd = new PatientDataSetDefinition();
                dsd.setName("Untitled");
                putInSession(session, dsd, true);
            }
        }

        if (!StringUtils.isBlank(successUrl)) {
            session.setAttribute(SUCCESS_URL_ATTR, successUrl);
        }
        if (!StringUtils.isBlank(discardUrl)) {
            session.setAttribute(DISCARD_URL_ATTR, discardUrl);
        }

        return dsd;
    }

    @ModelAttribute("parameterTypes")
    public List<Option> getAvailableParameterTypes() {
        return ParameterUtil.getSupportedTypes();
    }

    @ModelAttribute("parameterCollectionTypes")
    public List<Option> getAvailableParameterCollectionTypes() {
        return ParameterUtil.getSupportedCollectionTypes();
    }

    private void putInSession(HttpSession session, PatientDataSetDefinition dsd, boolean isUnsaved) {
        session.setAttribute(DSD_ATTR, dsd);
        session.setAttribute(IS_UNSAVED_ATTR, isUnsaved);
    }

    private void removeFromSession(HttpSession session) {
        session.removeAttribute(DSD_ATTR);
        session.removeAttribute(IS_UNSAVED_ATTR);
        session.removeAttribute(SUCCESS_URL_ATTR);
        session.removeAttribute(DISCARD_URL_ATTR);
    }

    private PatientDataSetDefinition getFromSession(HttpSession session) {
        try {
            return (PatientDataSetDefinition) session.getAttribute(DSD_ATTR);
        } catch (ClassCastException ex) {
            // module has been reloaded
            removeFromSession(session);
            return null;
        }
    }

    @RequestMapping("/module/reporting/datasets/patientDataSetEditor")
    public void showDataset(HttpSession session, Model model) {
        model.addAttribute("unsaved", session.getAttribute(IS_UNSAVED_ATTR));
        model.addAttribute("dsd", session.getAttribute(DSD_ATTR));
        model.addAttribute("dataDefinitionTypes",
                PatientDataDefinition.class.getName() + "," + PersonDataDefinition.class.getName());
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-nameDescription", method = RequestMethod.POST)
    public String changeNameAndDescription(@RequestParam("name") String name,
            @RequestParam("description") String description, HttpSession session) {
        PatientDataSetDefinition dsd = getFromSession(session);
        dsd.setName(name);
        dsd.setDescription(description);
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-addParam", method = RequestMethod.POST)
    public String addParameter(
            @RequestParam(value = "collectionType", required = false) Class<? extends Collection<?>> collectionType,
            @RequestParam(value = "parameterType", required = false) Class<?> parameterType,
            @RequestParam(value = "name", required = false) String name,
            @RequestParam(value = "label", required = false) String label,
            @RequestParam(value = "widgetConfiguration", required = false) String widgetConfiguration,
            HttpSession session) {
        if (parameterType == null || name == null || label == null) {
            session.setAttribute(WebConstants.OPENMRS_ERROR_ATTR, "Type, Name, and Label are required");
            return "redirect:patientDataSetEditor.form";
        }

        Properties widgetConfig = null;
        if (ObjectUtil.notNull(widgetConfiguration)) {
            widgetConfig = WidgetUtil.parseInput(widgetConfiguration, Properties.class);
        }

        PatientDataSetDefinition dsd = getFromSession(session);
        dsd.addParameter(new Parameter(name, label, parameterType, collectionType, null, widgetConfig));
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-removeParam", method = RequestMethod.POST)
    public String removeParameter(@RequestParam("name") String name, HttpSession session) {
        PatientDataSetDefinition dsd = getFromSession(session);
        dsd.removeParameter(name);
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-addColumn", method = RequestMethod.POST)
    public String addColumn(@RequestParam(value = "label", required = false) String label,
            @RequestParam(value = "columnDefinition", required = false) String columnDefinition,
            HttpSession session) {
        if (StringUtils.isBlank(label) || StringUtils.isBlank(columnDefinition)) {
            session.setAttribute(WebConstants.OPENMRS_ERROR_ATTR, "Label and Definition are required");
            return "redirect:patientDataSetEditor.form";
        }

        PatientDataSetDefinition dsd = getFromSession(session);
        for (RowPerObjectColumnDefinition col : dsd.getColumnDefinitions()) {
            if (label.equals(col.getName())) {
                session.setAttribute(WebConstants.OPENMRS_ERROR_ATTR,
                        "There is already a column named '" + label + "'");
                return "redirect:patientDataSetEditor.form";
            }
        }

        MappedEditor editor = new MappedEditor();
        editor.setAsText(columnDefinition);
        Mapped<DataDefinition> mappedDef = (Mapped<DataDefinition>) editor.getValue();

        dsd.addColumn(label, mappedDef.getParameterizable(), mappedDef.getParameterMappings());
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-removeColumn", method = RequestMethod.POST)
    public String removeColumn(@RequestParam("name") String name, HttpSession session) {
        PatientDataSetDefinition dsd = getFromSession(session);
        dsd.removeColumnDefinition(name);
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-addFilter", method = RequestMethod.POST)
    public String addFilter(@RequestParam(value = "filterDefinition", required = false) String filterDefinition,
            HttpSession session) {
        if (StringUtils.isBlank(filterDefinition)) {
            session.setAttribute(WebConstants.OPENMRS_ERROR_ATTR, "Definition is required");
            return "redirect:patientDataSetEditor.form";
        }

        PatientDataSetDefinition dsd = getFromSession(session);

        MappedEditor editor = new MappedEditor();
        editor.setAsText(filterDefinition);
        Mapped<CohortDefinition> mappedDef = (Mapped<CohortDefinition>) editor.getValue();
        dsd.addRowFilter(mappedDef);

        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-removeFilter", method = RequestMethod.POST)
    public String removeFilter(@RequestParam("filterIndex") int index, HttpSession session) {
        PatientDataSetDefinition dsd = getFromSession(session);
        dsd.getRowFilters().remove(index);
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-sortColumns", method = RequestMethod.POST)
    public String sortColumns(WebRequest request, HttpSession session) {
        final List<String> columnOrder = new ArrayList<String>();
        int i = 0;
        while (true) {
            String colName = request.getParameter("column" + i);
            if (colName == null)
                break;
            columnOrder.add(colName);
            ++i;
        }

        PatientDataSetDefinition dsd = getFromSession(session);
        Collections.sort(dsd.getColumnDefinitions(), new Comparator<RowPerObjectColumnDefinition>() {
            public int compare(RowPerObjectColumnDefinition left, RowPerObjectColumnDefinition right) {
                Integer leftIndex = columnOrder.indexOf(left.getName());
                Integer rightIndex = columnOrder.indexOf(right.getName());
                return leftIndex.compareTo(rightIndex);
            }
        });
        putInSession(session, dsd, true);
        return "redirect:patientDataSetEditor.form";
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-save", method = RequestMethod.POST)
    public String save(HttpSession session) {
        PatientDataSetDefinition dsd = getFromSession(session);
        String successUrl = (String) session.getAttribute(SUCCESS_URL_ATTR);

        Context.getService(DataSetDefinitionService.class).saveDefinition(dsd);

        removeFromSession(session);

        if (!StringUtils.isBlank(successUrl)) {
            return "redirect:" + successUrl;
        } else {
            return "redirect:patientDataSetEditor.form?uuid=" + dsd.getUuid();
        }
    }

    @RequestMapping(value = "/module/reporting/datasets/patientDataSetEditor-discard", method = RequestMethod.POST)
    public String discard(HttpSession session) {
        String discardUrl = (String) session.getAttribute(DISCARD_URL_ATTR);

        removeFromSession(session);

        if (!StringUtils.isBlank(discardUrl)) {
            return "redirect:" + discardUrl;
        } else {
            return "redirect:/module/reporting/definition/manageDefinitions.form?type=org.openmrs.module.reporting.dataset.definition.DataSetDefinition";
        }
    }

}