package net.techreadiness.plugin.action.reports; import java.io.ByteArrayInputStream; import java.io.InputStream; import java.text.SimpleDateFormat; import java.util.Collections; import java.util.List; import java.util.Map; import java.util.TimeZone; import javax.inject.Inject; import net.techreadiness.plugin.action.reports.ReportBreadcrumb.ProgressReportLink; import net.techreadiness.plugin.action.reports.ReportItemProvider.ExportType; import net.techreadiness.plugin.service.SnapshotWindowService; import net.techreadiness.plugin.service.object.SnapshotWindow; import net.techreadiness.plugin.service.reports.MinimumRecommendedFlag; import net.techreadiness.plugin.service.reports.ReportsService; import net.techreadiness.service.OrgPartService; import net.techreadiness.service.OrganizationService; import net.techreadiness.service.ScopeService; import net.techreadiness.service.ServiceContext; import net.techreadiness.service.exception.ServiceException; import net.techreadiness.service.object.Org; import net.techreadiness.service.object.Scope; import net.techreadiness.ui.BaseAction; import org.apache.commons.lang3.BooleanUtils; import org.apache.commons.lang3.StringUtils; import org.apache.struts2.convention.annotation.Action; import org.apache.struts2.convention.annotation.Result; import com.google.common.collect.Lists; public abstract class ReportAction extends BaseAction { private static final long serialVersionUID = 1L; public enum Consortium { SBAC("smart", "/readiness/smart"), PARCC("parcc", "/readiness/parcc"); public final String code, path; Consortium(final String code, final String path) { this.code = code; this.path = path; } public static Consortium getConsortium(String code) { for (Consortium corsortium : Consortium.values()) { if (corsortium.code.equals(code)) { return corsortium; } } return null; } } protected enum ViewBy { table, map; } public enum Requirements { Minimum, Recommended; } @Inject protected OrganizationService orgService; @Inject protected OrgPartService orgPartService; @Inject protected ScopeService scopeService; @Inject SnapshotWindowService snapshotWindowService; @Inject private ReportsService reportService; // List of minimum and recommended requirements set by the consortium private List<Map<String, String>> minRecReq; protected List<ReportBreadcrumb> breadcrumbs; protected ViewBy viewBy; protected Consortium consortium; protected Requirements requirements; protected String snapshotName; protected long snapshotScopeId; protected String fileName; protected String fileType; protected String contentType; private InputStream inputStream; private String reportAggDate; private String year; private String monthZ; private String date; private int hourInt; private String hour; private String ampm; private String minutes; private String mm; private static final SimpleDateFormat dateFormat = new SimpleDateFormat("MMMM dd, yyyy"); private static final SimpleDateFormat timeFormat = new SimpleDateFormat("hh:mm a "); protected abstract ReportExport getReportExport(ExportType type) throws Exception; protected abstract ReportExport getAllSchoolsReportExport(ExportType type) throws Exception; @Action(value = "download", results = { @Result(name = "success", type = "stream", params = { "inputName", "inputStream", "contentType", "${contentType}", "contentDisposition", "attachment;filename=\"${fileName}.${fileType}\"", "bufferSize", "1024" }) }) public String download() throws Exception { // check input types for validity try { switch (ExportType.valueOf(fileType)) { case csv: contentType = "text/csv"; break; case pdf: contentType = "application/pdf"; break; } } catch (Exception e) { throw new Exception("File Type not implemented."); } ReportExport export = getReportExport(ExportType.valueOf(fileType)); inputStream = new ByteArrayInputStream(export.getReport()); return SUCCESS; } @Action(value = "downloadAllSchools", results = { @Result(name = "success", type = "stream", params = { "inputName", "inputStream", "contentType", "${contentType}", "contentDisposition", "attachment;filename=\"${fileName}.${fileType}\"", "bufferSize", "1024" }) }) public String downloadAllSchools() throws Exception { // check input types for validity try { switch (ExportType.valueOf(fileType)) { case csv: contentType = "text/csv"; break; default: break; } } catch (Exception e) { throw new Exception("File Type not implemented."); } ReportExport export = getAllSchoolsReportExport(ExportType.valueOf(fileType)); inputStream = new ByteArrayInputStream(export.getReport()); return SUCCESS; } @Action(value = "minRequirements", results = { @Result(name = "success", location = "/net/techreadiness/plugin/action/reports/minRequirements.jsp") }) public String minRequirements() throws ServiceException { // select consortium (based on past selection) if (consortium == null) { consortium = Consortium.SBAC; } // get the consortiums scope object queryRequirements(getSnapshotWindow(snapshotName, snapshotScopeId)); return SUCCESS; } @Action(value = "exceptionTypes", results = { @Result(name = "success", location = "/net/techreadiness/plugin/action/reports/exceptionTypes.jsp") }) public String exceptionTypes() throws ServiceException { if (consortium == null) { consortium = Consortium.SBAC; } return SUCCESS; } private SnapshotWindow currentSnapshotWindow = null; private Scope consortiumScope; protected SnapshotWindow getCurrentSnapshotWindow() { if (currentSnapshotWindow == null) { consortiumScope = scopeService.getByScopePath(consortium.path); currentSnapshotWindow = snapshotWindowService.getByScopeIdAndName(getServiceContext(), consortiumScope.getScopeId(), ReportsService.DEFAULT_SNAPSHOT_WINDOW); } return currentSnapshotWindow; } public SnapshotWindow getSnapshotWindow() { if (snapshotName == null || snapshotName.equals("")) { return getCurrentSnapshotWindow(); } return getSnapshotWindow(snapshotName, snapshotScopeId); } protected SnapshotWindow getSnapshotWindow(String snapshotName, long snapshotScopeId) { if (snapshotName == null || snapshotName.equals("")) { return getCurrentSnapshotWindow(); } return snapshotWindowService.getByScopeIdAndName(getServiceContext(), snapshotScopeId, snapshotName); } protected void queryRequirements() { minRecReq = reportService.retrieveMinimumRecommendedValues(getCurrentSnapshotWindow().getSnapshotWindowId()); } protected void queryRequirements(SnapshotWindow snapshotWindow) { minRecReq = reportService.retrieveMinimumRecommendedValues(snapshotWindow.getSnapshotWindowId()); } @Action(value = "TBD", results = { @Result(name = "success", location = "/net/techreadiness/plugin/action/reports/tbd.jsp") }) public String tbd() throws ServiceException { return SUCCESS; } public String getFileName() { return fileName; } public void setFileName(String fileName) { this.fileName = fileName; } public String getFileType() { return fileType; } public void setFileType(String fileType) { this.fileType = fileType; } public String getContentType() { return contentType; } public InputStream getInputStream() { return inputStream; } public String getViewBy() { return viewBy == null ? ViewBy.map.toString() : viewBy.toString(); } public void setViewBy(String viewBy) { this.viewBy = ViewBy.valueOf(viewBy); } public String getRequirements() { return requirements == null ? Requirements.Minimum.toString() : requirements.toString(); } public void setRequirements(String requirements) { this.requirements = Requirements.valueOf(requirements); } public String getConsortium() { return consortium == null ? Consortium.SBAC.toString() : consortium.toString(); } public void setConsortium(String consortium) { this.consortium = Consortium.valueOf(consortium); } public List<ReportBreadcrumb> getBreadcrumbs() { return breadcrumbs; } public void setBreadcrumbs(List<ReportBreadcrumb> breadcrumbs) { this.breadcrumbs = breadcrumbs; } public List<Map<String, String>> getMinRecReq() { return minRecReq; } public String getSnapshotName() { return snapshotName; } public void setSnapshotName(String snapshotName) { this.snapshotName = snapshotName; } public long getSnapshotScopeId() { return snapshotScopeId; } public void setSnapshotScopeId(long snapshotScopeId) { this.snapshotScopeId = snapshotScopeId; } protected MinimumRecommendedFlag getMinimumRecommendedFlag() { if (requirements == null) { return MinimumRecommendedFlag.MINIMUM; } switch (requirements) { case Minimum: return MinimumRecommendedFlag.MINIMUM; case Recommended: return MinimumRecommendedFlag.RECOMMENDED; default: return MinimumRecommendedFlag.MINIMUM; } } protected void buildBreadcrumbs(Org org, Consortium consortium, String action) { List<ReportBreadcrumb> crumbs = Lists.newArrayList(); ServiceContext context = getServiceContext(); if (org.getOrgTypeName().equals("School")) { ReportBreadcrumb bc = new ReportBreadcrumb(); bc.setAction(action); bc.setLabel(org.getName()); bc.setLink(userService.hasAccessToOrg(context, context.getUserId(), org.getOrgId())); bc.setOrgCode(org.getCode()); crumbs.add(bc); org = orgService.getByCode(getServiceContext(), org.getParentOrgCode()); } if (org.getOrgTypeName().equals("District")) { ReportBreadcrumb bc = new ReportBreadcrumb(); bc.setAction(action); bc.setLabel(org.getName()); bc.setLink(userService.hasAccessToOrg(context, context.getUserId(), org.getOrgId())); bc.setOrgCode(org.getCode()); crumbs.add(bc); org = orgService.getByCode(getServiceContext(), org.getParentOrgCode()); } String stateName = null, stateCode = null; if (org.getOrgTypeName().equals("State")) { ReportBreadcrumb bc = new ReportBreadcrumb(); bc.setAction(action); bc.setLabel(org.getName()); bc.setLink(userService.hasAccessToOrg(context, context.getUserId(), org.getOrgId())); bc.setOrgCode(org.getCode()); stateName = org.getLocalCode(); stateName = org.getName(); crumbs.add(bc); org = orgService.getByCode(getServiceContext(), org.getParentOrgCode()); } // add the state code to the available crumbs for (ReportBreadcrumb crumb : crumbs) { crumb.setStateCode(stateCode); crumb.setStateName(stateName); } ReportBreadcrumb consortiumBC = new ReportBreadcrumb(); consortiumBC.setAction(action); consortiumBC.setLabel(consortium.toString()); consortiumBC.setLink(userService.hasAccessToOrg(context, context.getUserId(), org.getOrgId())); consortiumBC.setOrgCode(org.getCode()); crumbs.add(consortiumBC); Collections.reverse(crumbs); breadcrumbs = crumbs; } protected void addProgressReportLink(ProgressReportLink link) { if (breadcrumbs == null || breadcrumbs.isEmpty()) { breadcrumbs = Lists.newArrayList(); } ReportBreadcrumb progress = new ReportBreadcrumb(); progress.setProgressReportLink(link); breadcrumbs.add(0, progress); } public String getColor(double percentage) { if (percentage < .26) { return "report-level1"; } if (percentage < .51) { return "report-level2"; } if (percentage < .76) { return "report-level3"; } return "report-level4"; } public String getColor(Long percentage) { if (percentage < 26) { return "report-level1"; } if (percentage < 51) { return "report-level2"; } if (percentage < 76) { return "report-level3"; } return "report-level4"; } public String getColor(String value) { if ("TBD".equals(value) || "--".equals(value)) { return "report-level-null"; } return getColor(Double.valueOf(value)); } public String getColorStaff(double percentage) { if (percentage <= 3) { return "report-level4"; } if (percentage <= 5) { return "report-level3"; } if (percentage <= 7) { return "report-level2"; } return "report-level1"; } public String getColorStaff(String value) { return getColorStaff(Double.valueOf(value)); } public String getPercent(String value) { if ("TBD".equalsIgnoreCase(value)) { return value; } return value + "%"; } public String getPercentColor(String value) { String percent = StringUtils.defaultString(value).replaceAll("[>%]", ""); try { return getColor(Long.valueOf(percent)); } catch (Exception e) { return "report-level-null"; } } public String getColorBoolean(String value) { if (BooleanUtils.toBoolean(value)) { return getColor(1); } return getColor(0); } public String getAsOfDate() { SnapshotWindow snapshot = getCurrentSnapshotWindow(); if (snapshot.getExecuteDate() == null) { return ""; } dateFormat.setTimeZone(TimeZone.getTimeZone("CST")); timeFormat.setTimeZone(TimeZone.getTimeZone("CST")); StringBuilder sb = new StringBuilder(); sb.append("Data as of "); sb.append(dateFormat.format(snapshot.getExecuteDate())); sb.append(" at "); sb.append(timeFormat.format(snapshot.getExecuteDate())); sb.append(" CT"); return sb.toString(); } public String getFormattedDate() { reportAggDate = getSnapshotWindow().getExecuteDate().toString(); if (!reportAggDate.isEmpty()) { if (reportAggDate.contains("CST") || reportAggDate.contains("-0600")) { reportAggDate.replace("CST", "CT"); reportAggDate.replace("-0600", "CT"); } mm = reportAggDate.substring(5, 7); if (mm.equals("01")) { monthZ = "January"; } else if (mm.equals("02")) { monthZ = "February"; } else if (mm.equals("03")) { monthZ = "March"; } else if (mm.equals("04")) { monthZ = "April"; } else if (mm.equals("05")) { monthZ = "May"; } else if (mm.equals("06")) { monthZ = "June"; } else if (mm.equals("07")) { monthZ = "July"; } else if (mm.equals("08")) { monthZ = "August"; } else if (mm.equals("09")) { monthZ = "September"; } else if (mm.equals("10")) { monthZ = "October"; } else if (mm.equals("11")) { monthZ = "November"; } else if (mm.equals("12")) { monthZ = "December"; } hourInt = Integer.parseInt(reportAggDate.substring(11, 13)); // hour integer value if (hourInt < 12) { ampm = "AM"; } else { ampm = "PM"; } year = reportAggDate.substring(0, 4); // year hour = reportAggDate.substring(11, 13); // hour minutes = reportAggDate.substring(14, 16); // minutes date = reportAggDate.substring(8, 10); // date } return monthZ + " " + date + ", " + year + " at " + hour + ":" + minutes + " " + ampm + " CT"; } public Scope getConsortiumScope() { return consortiumScope; } }