/*********************************************************************************
* The contents of this file are subject to the Common Public Attribution
* 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://www.openemm.org/cpal1.html. The License is based on the Mozilla
* Public License Version 1.1 but Sections 14 and 15 have been added to cover
* use of software over a computer network and provide for limited attribution
* for the Original Developer. In addition, Exhibit A has been modified to be
* consistent with Exhibit B.
* 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.
*
* The Original Code is OpenEMM.
* The Original Developer is the Initial Developer.
* The Initial Developer of the Original Code is AGNITAS AG. All portions of
* the code written by AGNITAS AG are Copyright (c) 2009 AGNITAS AG. All Rights
* Reserved.
*
* Contributor(s): AGNITAS AG.
********************************************************************************/
package org.agnitas.web;
import java.beans.IntrospectionException;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.util.*;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Future;
import javax.servlet.ServletException;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import org.agnitas.beans.Admin;
import org.agnitas.beans.ColumnMapping;
import org.agnitas.beans.CustomerImportStatus;
import org.agnitas.beans.DatasourceDescription;
import org.agnitas.beans.ImportProfile;
import org.agnitas.beans.Mailinglist;
import org.agnitas.beans.ProfileRecipientFields;
import org.agnitas.dao.ImportProfileDao;
import org.agnitas.dao.ImportRecipientsDao;
import org.agnitas.dao.MailinglistDao;
import org.agnitas.service.ImportErrorRecipientQueryWorker;
import org.agnitas.service.ImportRecipientsAssignMailinglistsWorker;
import org.agnitas.service.ImportRecipientsProcessWorker;
import org.agnitas.service.NewImportWizardService;
import org.agnitas.service.csv.Toolkit;
import org.agnitas.service.impl.CSVColumnState;
import org.agnitas.service.impl.ImportWizardContentParseException;
import org.agnitas.service.impl.NewImportWizardServiceImpl;
import org.agnitas.util.AgnUtils;
import org.agnitas.util.EmailAttachment;
import org.agnitas.util.ImportCsvGenerator;
import org.agnitas.util.ImportReportEntry;
import org.agnitas.util.ImportUtils;
import org.agnitas.util.importvalues.Charset;
import org.agnitas.util.importvalues.DateFormat;
import org.agnitas.util.importvalues.ImportMode;
import org.agnitas.util.importvalues.Separator;
import org.agnitas.util.importvalues.TextRecognitionChar;
import org.agnitas.web.forms.NewImportWizardForm;
import org.apache.commons.io.FileUtils;
import org.apache.commons.lang.StringUtils;
import org.apache.commons.validator.GenericValidator;
import org.apache.commons.validator.ValidatorResults;
import org.apache.log4j.Logger;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.action.ActionMessage;
import org.apache.struts.action.ActionMessages;
import org.apache.struts.upload.FormFile;
import org.displaytag.pagination.PaginatedList;
import org.springframework.context.ApplicationContext;
import org.springframework.jdbc.datasource.SingleConnectionDataSource;
/**
* @author Viktor Gema
*/
public class NewImportWizardAction extends ImportBaseFileAction {
private static final transient Logger logger = Logger.getLogger(NewImportWizardAction.class);
public static final String FUTURE_TASK1 = "IMPORT_RECIPIENT_LIST";
public static final String FUTURE_TASK2 = "IMPORT_RECIPIENT_PROCESS";
public static final String FUTURE_TASK3 = "IMPORT_RECIPIENT_WORKER";
public static final int ACTION_START = 1;
public static final int ACTION_PREVIEW = 2;
public static final int ACTION_PROCEED = 3;
public static final int ACTION_ERROR_EDIT = 4;
public static final int ACTION_MLISTS = 5;
public static final int ACTION_RESULT_PAGE = 6;
public static final int ACTION_DOWNLOAD_CSV_FILE = 7;
public static final int ACTION_MLISTS_SAVE = 8;
/**
* Process the specified HTTP request, and create the corresponding HTTP
* response (or forward to another web component that will create it).
* Return an <code>ActionForward</code> instance describing where and how
* control should be forwarded, or <code>null</code> if the response has
* already been completed.<br>
* Error and success messages are set during the action to give the user
* a feedback in the forwarded web component.<br>
* <br>
* ACTION_START: Loads the list of all available profiles for import and ID of default import profile for current user.<br>
* Resets import status and resultPagePrepared property of form. Forwards to "start".
* <br><br>
* ACTION_PREVIEW: performs general validation before starting recipients import.<br>
* Initializes import helper with initial values; <br>
* Created unique import ID and sets it to import profile; <br>
* If csv-file is missing or there are no import profiles in system - forwards to "start" with corresponding
* error messages.<br>
* If import profile doesn't match the csv-file or has no key column in its column mappings forwards to
* "profile_edit" with corresponding error messages.<br>
* If validation is passed loads first 20 recipients from csv-file for preview, loads mailinglists into form,
* chooses mailinglist message according to import mode, forwards to "preview".<br>
* If the session parameter "IMPORT_KEY_COLUMNS" is set - import ignores key column from import profile and uses
* list of key columns from "IMPORT_KEY_COLUMNS" (example "email, firstname, lastname"). The values from this
* session parameter is set to import profile.
* <br><br>
* ACTION_PROCEED:<br>
* In general performs recipient import using settings from selected import profile.<br><br>
* If the FutureHolder doesn't contain yet the recipient import worker:<br>
* Checks if there are mailinglists selected. If the current import mode needs mailinglists and no list is
* selected - forwards to "preview" with appropriate error message. Stores the list of mailinglists to assign in
* form. Creates import recipient worker and puts it to FutureHolder. Stores import parameters (importMode,
* separator, delimiter etc.) to status property of form.<br><br>
* If FutureHolder is finished and there are errors for edit error page - forwards to error editing page and
* also checks for import limits.<br><br>
* If FutureHolder is finished and there are no errors for edit error page: puts worker for assigning
* mailinglists into FutureHolder (and forwards to "progress"), if that FutureHolder is finished - removes
* temporary table of import recipients from DB, removes stored csv, forwards to "result_page"; if it is still
* running - increases refresh rate and forwards to "progress". Also checks for import limits.<br><br>
* If FutureHolder is still running - increases refresh time and forwards to "progress"<br><br>
* If there were errors during the import - removed the recipient import worker from the FutureHolder and
* forwards to "preview" page with error messages.
* <br><br>
* ACTION_ERROR_EDIT:
* If the FutureHolder doesn't have task running and there's attribute "recipientsInCurrentTable" in request -
* validates recipient fixed on error edit page and performs the import for fixed recipients.<br>
* If there are still errors for error-edit-page - forwards to error-edit page. If there are no errors left -
* prepares result page: calls future holder for assigning mailing lists and forwards to "progress" or
* "result_page" depending on FutureHolder finished or not.
* <br><br>
* ACTION_MLISTS: puts worker for assigning mailinglists into FutureHolder (and forwards to "progress"), if that
* FutureHolder is finished - removes temporary table of import recipients from DB, removes stored csv,
* forwards to "result_page"; if it is still running - increases refresh rate and forwards to "progress".
* <br><br>
* ACTION_DOWNLOAD_CSV_FILE: checks what type of file user wants to download. Gets the file depending on that type.
* Writes that file to response (for user to download). Forwards to null destination.
* <br><br>
* Any other ACTION_* would cause a forward to null
* <br><br>
* If current destination is "error_edit":<br>
* If the FutureHolder is not running yet - puts there a worker for getting invalid recipients from temporary table
* containing beans of import-recipients from csv-file<br>
* If the FutureHolder is not finished yet - increases refresh time and forwards to "loading"<br>
* If FutureHolder is finished - puts found invalid recipients to request and to session attribute
* "recipientsInCurrentTable", sets the total number of invalid recipients to form, removes current task from
* FutureHolder
* <br><br>
* @param form data for the action filled by the jsp
* @param req request from jsp <br>
* If the request parameter "start_proceed" is set - changes action to ACTION_PREVIEW.<br>
* If the request parameter "preview_back" is set - changes action to ACTION_START.<br>
* If the request parameter "preview_proceed" is set - changes action to ACTION_PROCEED.<br>
* If the request parameter "edit_page_save" is set - changes action to ACTION_ERROR_EDIT.<br>
* @param res response
* @param mapping
* The ActionMapping used to select this instance
* @exception IOException
* if an input/output error occurs
* @exception ServletException
* if a servlet exception occurs
* @return destination specified in struts-config.xml to forward to next jsp
*/
public ActionForward execute(ActionMapping mapping, ActionForm form, HttpServletRequest req, HttpServletResponse res) throws IOException, ServletException {
super.execute(mapping, form, req, res);
AbstractMap<String, Object> futureHolder = (AbstractMap<String, Object>) getBean("futureHolder");
String futureKeyList = FUTURE_TASK1 + "@" + req.getSession(false).getId();
String futureKeyProcess = FUTURE_TASK2 + "@" + req.getSession(false).getId();
String futureKeyWorker = FUTURE_TASK3 + "@" + req.getSession(false).getId();
// Validate the request parameters specified by the user
NewImportWizardForm aForm = null;
ActionMessages errors = new ActionMessages();
ActionForward destination = null;
ApplicationContext aContext = this.getWebApplicationContext();
if (!AgnUtils.isUserLoggedIn(req)) {
return mapping.findForward("logon");
}
if (form != null) {
aForm = (NewImportWizardForm) form;
} else {
aForm = new NewImportWizardForm();
}
if (logger.isInfoEnabled()) logger.info("NewImportWizard action: " + aForm.getAction());
if (AgnUtils.parameterNotEmpty(req, "start_proceed")) {
aForm.setAction(NewImportWizardAction.ACTION_PREVIEW);
}
if (AgnUtils.parameterNotEmpty(req, "preview_back")) {
aForm.setAction(NewImportWizardAction.ACTION_START);
}
if (AgnUtils.parameterNotEmpty(req, "preview_proceed")) {
aForm.setAction(NewImportWizardAction.ACTION_PROCEED);
}
if (req.getParameter("edit_page_save") != null) {
aForm.setAction(NewImportWizardAction.ACTION_ERROR_EDIT);
}
if (!allowed("wizard.import", req)) {
errors.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage("error.permissionDenied"));
saveErrors(req, errors);
return null;
}
try {
NewImportWizardService importWizardHelper = aForm.getImportWizardHelper();
switch (aForm.getAction()) {
case NewImportWizardAction.ACTION_START:
final Map<Integer, String> importProfiles = new HashMap<Integer, String>();
aForm.setDefaultProfileId(AgnUtils.getAdmin(req).getDefaultImportProfileID());
final List<ImportProfile> importProfileList = getProfileList(req);
for (ImportProfile importProfile : importProfileList) {
importProfiles.put(importProfile.getId(), importProfile.getName());
}
aForm.setImportProfiles(importProfiles);
aForm.setStatus((CustomerImportStatus) getWebApplicationContext().getBean("CustomerImportStatus"));
destination = mapping.findForward("start");
aForm.setResultPagePrepared(false);
break;
case NewImportWizardAction.ACTION_PREVIEW:
if (!aForm.getHasFile() && (aForm.getCsvFile() == null || StringUtils.isEmpty(aForm.getCsvFile().getFileName()))) {
errors.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage("error.import.no_file"));
destination = mapping.findForward("start");
} else if (aForm.getImportProfiles().size() == 0) {
errors.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage("error.import.no_profile"));
destination = mapping.findForward("start");
} else {
boolean profileFits = initImportWizardHelper(req, aForm, errors);
boolean keyColumnValid = isProfileKeyColumnValid(aForm, errors);
logImportStart(aForm);
if ((!profileFits || !keyColumnValid) && !errors.isEmpty()) {
HttpSession session = req.getSession();
session.setAttribute(ImportProfileAction.IMPORT_PROFILE_ERRORS_KEY, errors);
session.setAttribute(ImportProfileAction.IMPORT_PROFILE_ID_KEY, aForm.getDefaultProfileId());
destination = mapping.findForward("profile_edit");
} else if (!errors.isEmpty()) {
destination = mapping.findForward("start");
} else {
aForm.setPreviewParsedContent(importWizardHelper.getPreviewParsedContent(errors));
if (!errors.isEmpty()) {
destination = mapping.findForward("start");
break;
}
aForm.setAllMailingLists(getAllMailingLists(req));
aForm.setMailinglistAddMessage(createMailinglistAddMessage(aForm));
destination = mapping.findForward("preview");
}
}
break;
case NewImportWizardAction.ACTION_PROCEED:
aForm.setAction(NewImportWizardAction.ACTION_PROCEED);
destination = mapping.findForward("progress");
if (!futureHolder.containsKey(futureKeyProcess) && aForm.getErrorsDuringImport() == null) {
List<Integer> assignedLists = getAssignedMailingLists(req, aForm);
if (!ignoreEmptyAssignedList()) {
int importMode = aForm.getImportWizardHelper().getImportProfile().getImportMode();
if ((importMode == ImportMode.ADD.getIntValue() || importMode == ImportMode.ADD_AND_UPDATE.getIntValue()) && assignedLists.size() == 0) {
errors.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage("error.import.no_mailinglist"));
destination = mapping.findForward("preview");
break;
}
}
aForm.setListsToAssign(assignedLists);
final ImportRecipientsProcessWorker worker = new ImportRecipientsProcessWorker(importWizardHelper);
ImportProfile importProfile = aForm.getImportWizardHelper().getImportProfile();
futureHolder.put(futureKeyProcess, importRecipientsProcess(aForm, req, aContext, worker, importProfile));
futureHolder.put(futureKeyWorker, worker);
String charset = Charset.getPublicValue(importProfile.getCharset());
String separator = Separator.getValue(importProfile.getSeparator());
int mode = importProfile.getImportMode();
int doublette = importProfile.getCheckForDuplicates();
int nullValues = importProfile.getNullValuesAction();
String recognitionChar = TextRecognitionChar.getValue(importProfile.getTextRecognitionChar());
aForm.getStatus().setCharset(charset);
aForm.getStatus().setSeparator(separator);
aForm.getStatus().setMode(mode);
aForm.getStatus().setDoubleCheck(doublette);
aForm.getStatus().setIgnoreNull(nullValues);
aForm.getStatus().setDelimiter(recognitionChar);
}
if (aForm.getErrorsDuringImport() != null) {
errors.add(aForm.getErrorsDuringImport());
destination = mapping.findForward("preview");
futureHolder.remove(futureKeyProcess);
futureHolder.remove(futureKeyWorker);
aForm.setRefreshMillis(RecipientForm.DEFAULT_REFRESH_MILLIS);
aForm.setErrorsDuringImport(null);
break;
}
if (futureHolder.containsKey(futureKeyWorker) && futureHolder.get(futureKeyWorker) != null) {
final ActionMessage message = ((ImportRecipientsProcessWorker) futureHolder.get(futureKeyWorker)).getMessage();
if (message != null) {
errors.add(ActionMessages.GLOBAL_MESSAGE, message);
futureHolder.remove(futureKeyProcess);
futureHolder.remove(futureKeyWorker);
aForm.setRefreshMillis(RecipientForm.DEFAULT_REFRESH_MILLIS);
destination = mapping.findForward("preview");
break;
}
}
if (futureHolder.containsKey(futureKeyProcess) && ((Future) futureHolder.get(futureKeyProcess)).isDone()) {
futureHolder.remove(futureKeyProcess);
futureHolder.remove(futureKeyWorker);
if (importWizardHelper.isPresentErrorForErrorEditPage()) {
destination = mapping.findForward("error_edit");
} else {
destination = prepareResultPage(mapping, req, aForm, futureHolder, futureKeyProcess);
}
destination = checkImportLimits(mapping, errors, destination, importWizardHelper, aForm, req, futureHolder,futureKeyProcess);
if( "start".equals(destination.getName())) {
futureHolder.remove(futureKeyProcess);
futureHolder.remove(futureKeyWorker);
}
aForm.setRefreshMillis(RecipientForm.DEFAULT_REFRESH_MILLIS);
} else {
if (aForm.getRefreshMillis() < 100000) { // raise the refresh time
aForm.setRefreshMillis(aForm.getRefreshMillis() + 50);
}
//aForm.set
}
break;
case NewImportWizardAction.ACTION_ERROR_EDIT:
if (!futureHolder.containsKey(futureKeyList) && (PaginatedList) req.getSession().getAttribute("recipientsInCurrentTable") != null) {
final HashMap<String, ProfileRecipientFields> mapRecipientsFromTable = new HashMap<String, ProfileRecipientFields>();
final PaginatedList recipientsFromTable = (PaginatedList) req.getSession().getAttribute("recipientsInCurrentTable");
for (Object object : recipientsFromTable.getList()) {
final Map dynaBean = (Map) object;
final ProfileRecipientFields recipient = (ProfileRecipientFields) dynaBean.get(NewImportWizardService.ERROR_EDIT_RECIPIENT_EDIT_RESERVED);
mapRecipientsFromTable.put(recipient.getTemporaryId(), recipient);
}
final Map<String, String> changedRecipients = getChangedRecipients(req);
for (String key : changedRecipients.keySet()) {
final String temporaryId = key.substring(0, key.indexOf("/RESERVED/"));
final String propertyName = key.substring(key.indexOf("/RESERVED/") + 10, key.length());
final ProfileRecipientFields recipient = mapRecipientsFromTable.get(temporaryId);
Toolkit.setValueFromBean(recipient, propertyName, changedRecipients.get(key));
}
importWizardHelper.setBeansAfterEditOnErrorEditPage(new ArrayList<ProfileRecipientFields>(mapRecipientsFromTable.values()));
importWizardHelper.doValidate(true);
}
if (importWizardHelper.isPresentErrorForErrorEditPage()) {
destination = mapping.findForward("error_edit");
} else {
destination = prepareResultPage(mapping, req, aForm, futureHolder, futureKeyProcess);
}
destination = checkImportLimits(mapping, errors, destination, importWizardHelper, aForm, req, futureHolder, futureKeyProcess);
break;
case NewImportWizardAction.ACTION_MLISTS:
destination = prepareResultPage(mapping, req, aForm, futureHolder, futureKeyProcess);
break;
case NewImportWizardAction.ACTION_DOWNLOAD_CSV_FILE:
File outfile = null;
if (aForm.getDownloadFileType() ==
NewImportWizardService.RECIPIENT_TYPE_VALID) {
outfile = aForm.getValidRecipientsFile();
} else if (aForm.getDownloadFileType() ==
NewImportWizardService.RECIPIENT_TYPE_INVALID) {
outfile = aForm.getInvalidRecipientsFile();
} else if (aForm.getDownloadFileType() ==
NewImportWizardService.RECIPIENT_TYPE_FIXED_BY_HAND) {
outfile = aForm.getFixedRecipientsFile();
} else if (aForm.getDownloadFileType() ==
NewImportWizardService.RECIPIENT_TYPE_DUPLICATE_RECIPIENT) {
outfile = aForm.getDuplicateRecipientsFile();
} else if (aForm.getDownloadFileType() ==
NewImportWizardService.RESULT_TYPE){
outfile = aForm.getResultFile();
}
transferFile(res, errors, outfile);
destination = null;
break;
}
} catch (Exception e) {
logger.error("execute: " + e + "\n" + AgnUtils.getStackTrace(e));
errors.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage("error.exception"));
}
if (destination != null && "error_edit".equals(destination.getName())) {
try {
setNumberOfRows(req, aForm);
destination = mapping.findForward("loading");
if (! futureHolder.containsKey(futureKeyList)) {
futureHolder.put(futureKeyList,getRecipientListFuture(req, aContext, aForm));
}
if (futureHolder.containsKey(futureKeyList) && ((Future) futureHolder.get(futureKeyList)).isDone()) {
req.setAttribute("recipientList", ((Future) futureHolder.get(futureKeyList)).get());
req.getSession().setAttribute("recipientsInCurrentTable", ((Future) futureHolder.get(futureKeyList)).get());
destination = mapping.findForward("error_edit");
aForm.setAll(((PaginatedList) ((Future) futureHolder.get(futureKeyList)).get()).getFullListSize());
futureHolder.remove(futureKeyList);
aForm.setRefreshMillis(RecipientForm.DEFAULT_REFRESH_MILLIS);
} else {
if (aForm.getRefreshMillis() < 1000) { // raise the refresh time
aForm.setRefreshMillis(aForm.getRefreshMillis() + 50);
}
aForm.setError(false);
}
} catch (Exception e) {
logger.error("recipientList: " + e + "\n" + AgnUtils.getStackTrace(e));
errors.add(ActionMessages.GLOBAL_MESSAGE, new ActionMessage("error.exception"));
aForm.setError(true); // do not refresh when an error has been occurred
}
}
// Report any errors we have discovered back to the original form
if (!errors.isEmpty() && destination != null)
{
saveErrors(req, errors);
if (destination.getName().equals("progress")) {
aForm.setErrorsDuringImport(errors);
}
// return new ActionForward(mapping.getForward());
}
return destination;
}
private void logImportStart(NewImportWizardForm aForm) {
Random random = new Random();
int importId = Math.abs(random.nextInt());
aForm.getImportWizardHelper().getImportProfile().setImportId(importId);
if (logger.isInfoEnabled()) logger.info("Import ID: " + importId +
"\nImport Profile ID: " + aForm.getImportWizardHelper().getImportProfile().getId() +
"\nImport Profile Name: " + aForm.getImportWizardHelper().getImportProfile().getName() +
"\nFile Name: " + aForm.getCurrentFileName());
}
protected boolean ignoreEmptyAssignedList(){
return false;
}
private ActionForward prepareResultPage(ActionMapping mapping, HttpServletRequest req, NewImportWizardForm aForm, AbstractMap<String, Object> futureHolder, String futureKeyProcess) {
if (!aForm.isResultPagePrepared()) {
if (!futureHolder.containsKey(futureKeyProcess) && aForm.getErrorsDuringImport() == null) {
futureHolder.put(futureKeyProcess, assignMailinglists(aForm, req));
aForm.setAction(NewImportWizardAction.ACTION_MLISTS);
return mapping.findForward("progress");
}
if (futureHolder.containsKey(futureKeyProcess) && ((Future) futureHolder.get(futureKeyProcess)).isDone()) {
removeTemporaryTable(req, aForm);
removeStoredCsvFile(req);
aForm.setResultPagePrepared(true);
futureHolder.remove(futureKeyProcess);
aForm.setRefreshMillis(RecipientForm.DEFAULT_REFRESH_MILLIS);
NewImportWizardService importWizardHelper = aForm.getImportWizardHelper();
if (importWizardHelper != null){
destroyTemporaryConnection(importWizardHelper.getImportRecipientsDao());
}
FormFile file = aForm.getCsvFile();
Admin admin = AgnUtils.getAdmin(req);
String userName = admin != null ? admin.getUsername() : "";
String fileName = file != null ? file.getFileName() : "";
AgnUtils.userlogger().info( userName + ": do import from file " + fileName);
return mapping.findForward("result_page");
} else {
if (aForm.getRefreshMillis() < 100000) { // raise the refresh time
aForm.setRefreshMillis(aForm.getRefreshMillis() + 50);
}
}
aForm.setAction(NewImportWizardAction.ACTION_MLISTS);
return mapping.findForward("progress");
}
NewImportWizardService importWizardHelper = aForm.getImportWizardHelper();
if (importWizardHelper != null){
destroyTemporaryConnection(importWizardHelper.getImportRecipientsDao());
}
return mapping.findForward("result_page");
}
private void destroyTemporaryConnection(ImportRecipientsDao importRecipientsDao) {
if (importRecipientsDao != null){
SingleConnectionDataSource temporaryConnection = importRecipientsDao.getTemporaryConnection();
if (temporaryConnection != null){
temporaryConnection.destroy();
importRecipientsDao.setTemporaryConnection(null);
}
}
}
private Object assignMailinglists(NewImportWizardForm aForm, HttpServletRequest req) {
ExecutorService service = (ExecutorService) getWebApplicationContext().getBean("workerExecutorService");
ImportProfileDao profileDao = (ImportProfileDao) getWebApplicationContext().getBean("ImportProfileDao");
Locale locale = (Locale) req.getSession().getAttribute(org.apache.struts.Globals.LOCALE_KEY);
TimeZone zone = TimeZone.getTimeZone(AgnUtils.getAdmin(req).getAdminTimezone());
final Future future = service.submit(new ImportRecipientsAssignMailinglistsWorker(aForm, profileDao, getMessageSourceAccessor(), locale, zone));
return future;
}
/**
* Method removes temporary recipient table used by import
* @param req request
* @param aForm form
*/
private void removeTemporaryTable(HttpServletRequest req, NewImportWizardForm aForm) {
final String prefix = "cust_" + AgnUtils.getAdmin(req).getAdminID() + "_tmp_";
final String tableName = prefix + aForm.getDatasourceId() + "_tbl";
aForm.getImportWizardHelper().getImportRecipientsDao().removeTemporaryTable(tableName, req.getSession().getId());
}
/**
* Method checks if current import reaches the recipient limits (recipients
* per import; max recipient number in DB)
* @param mapping action mapping
* @param errors errors
* @param destination the current destination
* @param importWizardHelper the import service
* @param aForm the form
* @param req request
* @param futureHolder
*@param futureKeyProcess @return the action destination
*/
private ActionForward checkImportLimits(ActionMapping mapping, ActionMessages errors, ActionForward destination, NewImportWizardService importWizardHelper, NewImportWizardForm aForm, HttpServletRequest req, AbstractMap<String, Object> futureHolder, String futureKeyProcess) {
if (importWizardHelper.isImportLimitReached()) {
errors.add("global", new ActionMessage("error.import.too_many_records", AgnUtils.getDefaultValue("import.maxRows")));
destination = mapping.findForward("start");
removeTemporaryTable(req, aForm);
}
else if (importWizardHelper.isRecipientLimitReached()) {
errors.add("global", new ActionMessage("error.import.maxCount"));
destination = prepareResultPage(mapping, req, aForm, futureHolder, futureKeyProcess);
}
else if (importWizardHelper.isNearLimit()) {
errors.add("global", new ActionMessage("warning.import.maxCount"));
}
return destination;
}
/**
* Method checks if profile has key column in its column mappings
*
* @param aForm a form
* @param errors errors to add error to if key column is not imported
* @return true if key column is contained in one of column mappings
*/
private boolean isProfileKeyColumnValid(NewImportWizardForm aForm, ActionMessages errors) {
ImportProfile profile = aForm.getImportWizardHelper().getImportProfile();
List<ColumnMapping> columns = profile.getColumnMapping();
List<String> keyColumns = profile.getKeyColumns();
List<String> dbColumns = new ArrayList<String>();
for (ColumnMapping column : columns) {
dbColumns.add(column.getDatabaseColumn());
}
if (keyColumns.isEmpty()) {
if (dbColumns.contains(profile.getKeyColumn())) {
return true;
}
} else {
if (dbColumns.containsAll(keyColumns)) {
return true;
}
}
errors.add("profile", new ActionMessage("error.import.keycolumn_not_imported"));
return false;
}
/**
* Method takes changed recipient fields that were changed on error-edit-page
* Gets changed data from request
*
* @param request request
* @return result map (temporary id -> new value)
*/
private Map<String, String> getChangedRecipients(HttpServletRequest request) {
Map<String, String> result = new HashMap<String, String>();
Enumeration parameterNames = request.getParameterNames();
while (parameterNames.hasMoreElements()) {
String pName = (String) parameterNames.nextElement();
String paramBeginStr = "changed_recipient_";
if (pName.startsWith(paramBeginStr)) {
String id = pName.substring(paramBeginStr.length());
String value = request.getParameter(pName);
result.put(id, value);
}
}
return result;
}
/**
* Method creates date format for error-edit-page calendar using import
* profile date format
*
* @param aForm a form
* @return date format for jscalendar
*/
private String createCalendarDateFormat(NewImportWizardForm aForm) {
int dateFormat = aForm.getImportWizardHelper().getImportProfile().getDateFormat();
String csvFormat = DateFormat.getValue(dateFormat);
csvFormat = csvFormat.replace("yyyy", "%Y");
csvFormat = csvFormat.replace("MM", "%m");
csvFormat = csvFormat.replace("dd", "%d");
csvFormat = csvFormat.replace("HH", "%H");
csvFormat = csvFormat.replace("mm", "%M");
csvFormat = csvFormat.replace("ss", "%S");
return csvFormat;
}
/**
* Method creates message about assigning recipients to mailing lists
* according to import mode for displaying in result page and in report
* email
*
* @param aForm form
* @return mailing list add message
*/
private String createMailinglistAddMessage(NewImportWizardForm aForm) {
int importMode = aForm.getImportWizardHelper().getImportProfile().getImportMode();
String mlistAddedMessage = "";
if (importMode == ImportMode.ADD.getIntValue() ||
importMode == ImportMode.ADD_AND_UPDATE.getIntValue() ||
importMode == ImportMode.UPDATE.getIntValue()) {
mlistAddedMessage = "import.result.subscribersAdded";
} else if (importMode == ImportMode.MARK_OPT_OUT.getIntValue() ||
importMode == ImportMode.TO_BLACKLIST.getIntValue()) {
mlistAddedMessage = "import.result.subscribersUnsubscribed";
} else if (importMode == ImportMode.MARK_BOUNCED.getIntValue()) {
mlistAddedMessage = "import.result.subscribersBounced";
}
return mlistAddedMessage;
}
/**
* Gets all mailing lists for current company id
*
* @param req request to take company id
* @return all mailing lists for current company id
*/
private List<Mailinglist> getAllMailingLists(HttpServletRequest req) {
MailinglistDao dao = (MailinglistDao) getWebApplicationContext().getBean("MailinglistDao");
List mailinglists = dao.getMailinglists(AgnUtils.getCompanyID(req));
return mailinglists;
}
/**
* Gets list of mailing lists ids that were assigned on
* assign-mailinglist-page; takes data from request
*
* @param req request
* @param aForm form
* @return ids of assigned mailing lists
*/
private List<Integer> getAssignedMailingLists(HttpServletRequest req, NewImportWizardForm aForm) {
String aParam = null;
List<Integer> mailingLists = new ArrayList<Integer>();
Enumeration e = req.getParameterNames();
while (e.hasMoreElements()) {
aParam = (String) e.nextElement();
if (aParam.startsWith("agn_mlid_")) {
mailingLists.add(Integer.valueOf(aParam.substring(9)));
}
}
return mailingLists;
}
/**
* Inits import wizard helper, checks if import profile matches the csv-file
*
* @param req request
* @param aForm form
* @param errors list of errors
* @return true if no profile-match errors occured, false otherwise
*/
private boolean initImportWizardHelper(HttpServletRequest req, NewImportWizardForm aForm, ActionMessages errors) {
NewImportWizardService importWizardHelper = aForm.getImportWizardHelper();
try {
importWizardHelper.setProfileId(aForm.getDefaultProfileId());
importWizardHelper.setInputFile(getCurrentFile(req));
importWizardHelper.setAdminId(AgnUtils.getAdmin(req).getAdminID());
importWizardHelper.setCompanyId(AgnUtils.getCompanyID(req));
if (AgnUtils.getAdmin(req).permissionAllowed("recipient.gender.extended")) {
importWizardHelper.setMaxGenderValue(NewImportWizardService.MAX_GENDER_VALUE_EXTENDED);
} else {
importWizardHelper.setMaxGenderValue(NewImportWizardService.MAX_GENDER_VALUE_BASIC);
}
importWizardHelper.validateImportProfileMatchGivenCVSFile();
String importKeyColumns = (String) req.getSession().getAttribute("IMPORT_KEY_COLUMNS");
if(!StringUtils.isEmpty(importKeyColumns)){
List<String> keyColumns = importWizardHelper.getImportProfile().getKeyColumns();
keyColumns.clear();
String[] columns = importKeyColumns.split(", ");
keyColumns.addAll(Arrays.asList(columns));
// remove session var
req.getSession().removeAttribute("IMPORT_KEY_COLUMNS");
}
return true;
} catch (ImportWizardContentParseException e) {
aForm.setAction(NewImportWizardAction.ACTION_START);
if (e.getParameterValue() != null) {
errors.add("profile", new ActionMessage(e.getErrorMessageKey(), e.getParameterValue()));
} else {
errors.add("profile", new ActionMessage(e.getErrorMessageKey()));
}
return false;
} catch (IOException e) {
errors.add("csvFile", new ActionMessage("error.import.no_file"));
return true;
}
}
/**
* Method transfers given file to action response (for user to download)
*
* @param response action response
* @param errors errors
* @param outfile file to transfer
* @throws IOException exceptions that can occur while working with IO
*/
private void transferFile(HttpServletResponse response, ActionMessages errors, File outfile) throws IOException {
if (outfile != null) {
byte bytes[] = new byte[16384];
int len;
FileInputStream instream = new FileInputStream(outfile);
try {
if (outfile.getName().endsWith(".zip")) {
response.setContentType("application/zip");
} else if (outfile.getName().endsWith(".txt")) {
response.setContentType("application/txt");
}
response.setHeader("Content-Disposition", "attachment; filename=\"" + outfile.getName() + "\";");
response.setContentLength((int) outfile.length());
@SuppressWarnings("resource") // Do not close this stream, it's managed by the servlet container
ServletOutputStream ostream = response.getOutputStream();
while ((len = instream.read(bytes)) != -1) {
ostream.write(bytes, 0, len);
}
} finally {
instream.close();
}
} else {
errors.add("global", new ActionMessage("error.export.file_not_ready"));
}
}
/**
* @param request request
* @return list of import profiles for overview page with current company id
*/
private List<ImportProfile> getProfileList(HttpServletRequest request) throws InstantiationException, IllegalAccessException {
ImportProfileDao profileDao = (ImportProfileDao) getWebApplicationContext().getBean("ImportProfileDao");
return profileDao.getImportProfilesByCompanyId(AgnUtils.getCompanyID(request));
}
/**
* Get a list of recipients according to your validation
*
* @param request
* @param aContext
* @param aForm
* @return
* @throws NumberFormatException
* @throws IllegalAccessException
* @throws InstantiationException
* @throws java.util.concurrent.ExecutionException
*
* @throws InterruptedException
*/
public Future getRecipientListFuture(HttpServletRequest request, ApplicationContext aContext, NewImportWizardForm aForm)
throws NumberFormatException, IllegalAccessException, InstantiationException, InterruptedException, ExecutionException, IntrospectionException, InvocationTargetException {
//ImportRecipientsDao recipientDao = (ImportRecipientsDao) aContext.getBean("ImportRecipientsDao");
String sort = getSort(request, aForm);
String direction = request.getParameter("dir");
int rownums = aForm.getNumberofRows();
if (direction == null) {
direction = aForm.getOrder();
} else {
aForm.setOrder(direction);
}
String pageStr = request.getParameter("page");
if (pageStr == null || "".equals(pageStr.trim())) {
if (aForm.getPage() == null || "".equals(aForm.getPage().trim())) {
aForm.setPage("1");
}
pageStr = aForm.getPage();
} else {
aForm.setPage(pageStr);
}
if (aForm.isNumberOfRowsChanged()) {
aForm.setPage("1");
aForm.setNumberOfRowsChanged(false);
pageStr = "1";
}
final CSVColumnState[] columns = aForm.getImportWizardHelper().getColumns();
ExecutorService service = (ExecutorService) aContext.getBean("workerExecutorService");
Future future = service.submit(new ImportErrorRecipientQueryWorker(aForm.getImportWizardHelper().getImportRecipientsDao(), AgnUtils.getAdmin(request).getAdminID(), sort, direction, Integer.parseInt(pageStr), rownums, aForm.getAll(), columns, aForm.getImportWizardHelper().getStatus().getDatasourceID()));
//return aForm.getImportWizardHelper().getImportRecipientsDao().getInvalidRecipientList(columns, sort, direction, Integer.parseInt(pageStr), rownums, 0, AgnUtils.getAdmin(request).getAdminID(), aForm.getImportWizardHelper().getStatus().getDatasourceID());
return future;
}
public Future importRecipientsProcess(NewImportWizardForm aForm, HttpServletRequest req, ApplicationContext aContext, ImportRecipientsProcessWorker worker, ImportProfile importProfile) {
String calendarDateFormat = createCalendarDateFormat(aForm);
aForm.setCalendarDateFormat(calendarDateFormat);
//set datasource id
final DatasourceDescription dsDescription = ImportUtils.getNewDatasourceDescription(AgnUtils.getCompanyID(req), aForm.getCurrentFileName(), aContext);
aForm.getStatus().setDatasourceID(dsDescription.getId());
aForm.setDatasourceId(dsDescription.getId());
ImportUtils.createTemporaryTable(AgnUtils.getAdmin(req).getAdminID(), dsDescription.getId(), importProfile, req.getSession().getId(), aForm.getImportWizardHelper().getImportRecipientsDao());
ExecutorService service = (ExecutorService) aContext.getBean("workerExecutorService");
final Future future = service.submit(worker);
return future;
}
/**
* Initialize the list which keeps the current width of the columns, with a default value of '-1'
* A JavaScript in the corresponding jsp will set the style.width of the column.
*
* @param size number of columns
* @return
*/
protected List<String> getInitializedColumnWidthList(int size) {
List<String> columnWidthList = new ArrayList<String>();
for (int i = 0; i < size; i++) {
columnWidthList.add("-1");
}
return columnWidthList;
}
protected String getSort(HttpServletRequest request, NewImportWizardForm aForm) {
String sort = request.getParameter("sort");
if(sort == null) {
sort = aForm.getSort();
} else {
aForm.setSort(sort);
}
return sort;
}
/**
* Method generates result recipient files (valid, invalid, fixed)
* and stores them to form. If there are no recipients of some type
* (i.e. invalid) the corresponding form file will be set to null
*
* @param request request
* @param aForm a form
*/
private void generateResultFiles(HttpServletRequest request, NewImportWizardForm aForm) {
// generate valid recipients file
File validRecipients = createRecipientsCsv(request, aForm,
new Integer[]{NewImportWizardService.RECIPIENT_TYPE_VALID,
NewImportWizardService.RECIPIENT_TYPE_DUPLICATE_RECIPIENT}, "valid_recipients");
aForm.setValidRecipientsFile(validRecipients);
// generate invalid recipietns file (invalid by wrong field values + other invalid: blacklisted etc.)
File invalidRecipients = createRecipientsCsv(request, aForm,
new Integer[]{NewImportWizardService.RECIPIENT_TYPE_INVALID,
NewImportWizardService.RECIPIENT_TYPE_FIELD_INVALID}, "invalid_recipients");
aForm.setInvalidRecipientsFile(invalidRecipients);
// generate fixed recipients file (fixed on error edit page)
File fixedRecipients = createRecipientsCsv(request, aForm,
new Integer[]{NewImportWizardService.RECIPIENT_TYPE_FIXED_BY_HAND}, "fixed_recipients");
aForm.setFixedRecipientsFile(fixedRecipients);
// generate duplicate recipients file
File duplicateRecipients = createRecipientsCsv(request, aForm,
new Integer[]{NewImportWizardService.RECIPIENT_TYPE_DUPLICATE_IN_NEW_DATA_RECIPIENT,
NewImportWizardService.RECIPIENT_TYPE_DUPLICATE_RECIPIENT}, "duplicate_recipients");
aForm.setDuplicateRecipientsFile(duplicateRecipients);
}
/**
* Method generates recipients csv-file for the given types of recipients.
* If there are no recipients of such type(s) in temporary table the
* returned file will be null.
*
* @param request request
* @param aForm a form
* @param types types of recipients to include in csv-file
* @param fileName file name start part (random number will be appended)
* @return generated csv-file
*/
private File createRecipientsCsv(HttpServletRequest request, NewImportWizardForm aForm, Integer[] types, String fileName) {
ImportRecipientsDao recipientDao = aForm.getImportWizardHelper().getImportRecipientsDao();
int adminId = AgnUtils.getAdmin(request).getAdminID();
int datasourceId = aForm.getStatus().getDatasourceID();
int recipientCount = recipientDao.getRecipientsCountByType(types, adminId, datasourceId);
if (recipientCount == 0) {
return null;
}
ImportProfileDao profileDao = (ImportProfileDao) getWebApplicationContext().getBean("ImportProfileDao");
ImportProfile profile = profileDao.getImportProfileById(aForm.getDefaultProfileId());
ImportCsvGenerator generator = new ImportCsvGenerator();
CSVColumnState[] columns = aForm.getImportWizardHelper().getColumns();
generator.createCsv(profile, columns, fileName);
int page = 0;
int rowNum = NewImportWizardService.BLOCK_SIZE;
HashMap<ProfileRecipientFields, ValidatorResults> recipients = null;
while (recipients == null || recipients.size() == rowNum) {
recipients = recipientDao.getRecipientsByTypePaginated(types, page, rowNum, adminId, datasourceId);
generator.writeDataToFile(recipients.keySet(), columns, profile);
page++;
}
File file = generator.finishFileGeneration();
return file;
}
/**
* Generates report data: import statistics, recipient files; sends report email
*
* @param request request
* @param aForm a form
*/
private void generateReportData(HttpServletRequest request, NewImportWizardForm aForm) {
CustomerImportStatus status = aForm.getImportWizardHelper().getStatus();
ImportProfile profile = aForm.getImportWizardHelper().getImportProfile();
generateResultStatistics(request, aForm, status);
Collection<ImportReportEntry> reportEntries = generateReportData(status, profile);
final Map<String, String> statusReportMap = localizeReportItems(request, reportEntries);
aForm.getImportWizardHelper().log(aForm.getDatasourceId(), status.getInserted() + status.getUpdated(), ImportUtils.describeMap(statusReportMap));
aForm.setReportEntries(reportEntries);
generateResultFiles(request, aForm);
sendReportEmail(request, aForm);
}
private void generateResultStatistics(HttpServletRequest request, NewImportWizardForm aForm, CustomerImportStatus status) {
ImportRecipientsDao dao = aForm.getImportWizardHelper().getImportRecipientsDao();
int adminId = AgnUtils.getAdmin(request).getAdminID();
int datasourceId = aForm.getDatasourceId();
Integer[] types = {NewImportWizardService.RECIPIENT_TYPE_FIELD_INVALID};
int page = 0;
int rowNum = NewImportWizardService.BLOCK_SIZE;
HashMap<ProfileRecipientFields, ValidatorResults> recipients = null;
while (recipients == null || recipients.size() == rowNum) {
recipients = dao.getRecipientsByTypePaginated(types, page, rowNum, adminId, datasourceId);
for (ValidatorResults validatorResults : recipients.values()) {
for (CSVColumnState column : aForm.getImportWizardHelper().getColumns()) {
if (column.getImportedColumn()) {
if (!ImportUtils.checkIsCurrentFieldValid(validatorResults, column.getColName())) {
if (column.getColName().equals("email")) {
status.addError(NewImportWizardServiceImpl.EMAIL_ERROR);
} else if (column.getColName().equals("mailtype")) {
status.addError(NewImportWizardServiceImpl.MAILTYPE_ERROR);
} else if (column.getColName().equals("gender")) {
status.addError(NewImportWizardServiceImpl.GENDER_ERROR);
} else if (column.getType() == CSVColumnState.TYPE_DATE) {
status.addError(NewImportWizardServiceImpl.DATE_ERROR);
} else if (column.getType() == CSVColumnState.TYPE_NUMERIC) {
status.addError(NewImportWizardServiceImpl.NUMERIC_ERROR);
}
}
}
}
}
page++;
}
}
private Map<String, String> localizeReportItems(HttpServletRequest request, Collection<ImportReportEntry> reportEntries) {
final Map<String, String> statusReportMap = new HashMap<String, String>();
for (ImportReportEntry entry : reportEntries) {
final String messageKey = entry.getKey();
final String localizedMessage = getMessage(messageKey, request);
statusReportMap.put(localizedMessage, entry.getValue());
}
return statusReportMap;
}
/**
* Sends import report if profile has emailForReport
*
* @param request request
* @param aForm a form
*/
private void sendReportEmail(HttpServletRequest request, NewImportWizardForm aForm) {
ImportProfileDao profileDao = (ImportProfileDao) getWebApplicationContext().getBean("ImportProfileDao");
ImportProfile profile = profileDao.getImportProfileById(aForm.getDefaultProfileId());
String address = profile.getMailForReport();
if (!GenericValidator.isBlankOrNull(address) && GenericValidator.isEmail(address)) {
Locale locale = (Locale) request.getSession().getAttribute(org.apache.struts.Globals.LOCALE_KEY);
ResourceBundle bundle = ResourceBundle.getBundle("messages", locale);
Collection<EmailAttachment> attachments = new ArrayList<EmailAttachment>();
File invalidRecipientsFile = aForm.getInvalidRecipientsFile();
File fixedRecipientsFile = aForm.getFixedRecipientsFile();
EmailAttachment invalidRecipients = createZipAttachment(invalidRecipientsFile,
"invalid_recipients.zip", bundle.getString("import.recipients.invalid"));
if (invalidRecipients != null) {
attachments.add(invalidRecipients);
}
EmailAttachment fixedRecipients = createZipAttachment(fixedRecipientsFile,
"fixed_recipients.zip", bundle.getString("import.recipients.fixed"));
if (fixedRecipients != null) {
attachments.add(fixedRecipients);
}
EmailAttachment[] attArray = attachments.toArray(new EmailAttachment[]{});
String subject = bundle.getString("import.recipients.report");
String message = generateReportEmailBody(bundle, aForm);
message = subject + ":\n" + message;
ImportUtils.sendEmailWithAttachments( AgnUtils.getDefaultValue( "import.report.from.address"), AgnUtils.getDefaultValue( "import.report.from.name"), address, subject, message, attArray);
}
}
/**
* Generates body of report email
*
* @param bundle message resource bundle
* @param aForm a form
* @return body of email containing import statistics
*/
private String generateReportEmailBody(ResourceBundle bundle, NewImportWizardForm aForm) {
String body = "";
for (ImportReportEntry entry : aForm.getReportEntries()) {
body = body + bundle.getString(entry.getKey()) + ": " + entry.getValue() + "\n";
}
for (Mailinglist mlist : aForm.getAssignedMailingLists()) {
String mlistStr = mlist.getShortname() + ": " + aForm.getMailinglistAssignStats().get(mlist.getId()) +
" " + bundle.getString(aForm.getMailinglistAddMessage()) + "\n";
body = body + mlistStr;
}
return body;
}
/**
* Generates report statistics: errros, update information, datasource id
*
* @param status recipient import status
* @param profile import profile
* @return collection of statistics entries
*/
private Collection<ImportReportEntry> generateReportData(CustomerImportStatus status, ImportProfile profile) {
Collection<ImportReportEntry> reportValues = new ArrayList<ImportReportEntry>();
reportValues.add(new ImportReportEntry("import.csv_errors_email",
String.valueOf(status.getError(NewImportWizardService.EMAIL_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_blacklist",
String.valueOf(status.getError(NewImportWizardService.BLACKLIST_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_double",
String.valueOf(status.getError(NewImportWizardService.EMAILDOUBLE_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_numeric",
String.valueOf(status.getError(NewImportWizardService.NUMERIC_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_mailtype",
String.valueOf(status.getError(NewImportWizardService.MAILTYPE_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_gender",
String.valueOf(status.getError(NewImportWizardService.GENDER_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_date",
String.valueOf(status.getError(NewImportWizardService.DATE_ERROR))));
reportValues.add(new ImportReportEntry("import.csv_errors_linestructure",
String.valueOf(status.getError(NewImportWizardService.STRUCTURE_ERROR))));
reportValues.add(new ImportReportEntry("import.RecipientsAllreadyinDB",
String.valueOf(status.getAlreadyInDb())));
reportValues.add(new ImportReportEntry("import.result.imported",
String.valueOf(status.getInserted())));
reportValues.add(new ImportReportEntry("import.result.updated",
String.valueOf(status.getUpdated())));
if (profile.getImportMode() == ImportMode.ADD.getIntValue() ||
profile.getImportMode() == ImportMode.ADD_AND_UPDATE.getIntValue()) {
reportValues.add(new ImportReportEntry("import.result.datasource_id",
String.valueOf(status.getDatasourceID())));
}
return reportValues;
}
/**
* Creates attachment from zip-file
*
* @param recipientsFile file
* @param name name of attachment
* @param description attachment description
* @return created attachment
*/
private EmailAttachment createZipAttachment(File recipientsFile, String name, String description) {
EmailAttachment attachment;
if (recipientsFile != null) {
try {
byte[] data = FileUtils.readFileToByteArray(recipientsFile);
attachment = new EmailAttachment(name, data, "application/zip", description);
return attachment;
} catch (IOException e) {
logger.error("Error creating attachment: " + AgnUtils.getStackTrace(e));
}
}
return null;
}
/**
* Loads available mailing lists, creates mailing list add message
*
* @param mapping action mapping
* @param req request
* @param aForm form
* @return destination to mailing list assignment page
*/
private ActionForward prepareMailingListPage(ActionMapping mapping, HttpServletRequest req, NewImportWizardForm aForm) {
aForm.setAllMailingLists(getAllMailingLists(req));
aForm.setMailinglistAddMessage(createMailinglistAddMessage(aForm));
ActionForward destination = mapping.findForward("mailing_lists");
aForm.setAction(ACTION_MLISTS_SAVE);
return destination;
}
}