262 lines
No EOL
9.8 KiB
Java
262 lines
No EOL
9.8 KiB
Java
package com.alexanderlogistics.dwc;
|
|
|
|
import java.io.ByteArrayInputStream;
|
|
import java.io.ByteArrayOutputStream;
|
|
import java.io.IOException;
|
|
import java.io.InputStream;
|
|
import java.text.DateFormat;
|
|
import java.text.SimpleDateFormat;
|
|
import java.util.ArrayList;
|
|
import java.util.Collection;
|
|
import java.util.Date;
|
|
import java.util.List;
|
|
import java.util.logging.Logger;
|
|
|
|
import org.apache.poi.ss.usermodel.CellCopyPolicy;
|
|
import org.apache.poi.ss.util.CellReference;
|
|
import org.apache.poi.xssf.usermodel.XSSFRow;
|
|
import org.apache.poi.xssf.usermodel.XSSFSheet;
|
|
import org.apache.poi.xssf.usermodel.XSSFWorkbook;
|
|
import org.imixs.ai.workflow.OpenAIAPIAdapter;
|
|
import org.imixs.archive.core.SnapshotService;
|
|
import org.imixs.workflow.FileData;
|
|
import org.imixs.workflow.ItemCollection;
|
|
import org.imixs.workflow.SignalAdapter;
|
|
import org.imixs.workflow.engine.DocumentService;
|
|
import org.imixs.workflow.engine.ReportService;
|
|
import org.imixs.workflow.engine.WorkflowService;
|
|
import org.imixs.workflow.exceptions.AdapterException;
|
|
import org.imixs.workflow.exceptions.PluginException;
|
|
import org.imixs.workflow.exceptions.QueryException;
|
|
import org.imixs.workflow.sepa.services.SepaWorkflowService;
|
|
|
|
import com.alexanderlogistics.OPListExportAdapterByWeek;
|
|
|
|
import jakarta.ejb.EJB;
|
|
import jakarta.inject.Inject;
|
|
|
|
/**
|
|
* TheSEPAExportAdapterNBD is an extension of the SEPAExportAdapter.
|
|
*
|
|
* This adapter export the payment information in a Excel Sheet acording to the
|
|
* 'businessONLINE NBD' interface description.
|
|
*
|
|
* *
|
|
*
|
|
* <pre>
|
|
* {@code
|
|
<imixs-sepa name="CONFIG">
|
|
<textblock>....</textblock>
|
|
<template>....</template>
|
|
</imixs-sepa>
|
|
* }
|
|
* </pre>
|
|
*
|
|
* @version 1.0
|
|
* @author rsoika
|
|
*/
|
|
public class SEPAExportAdapterNBD implements SignalAdapter {
|
|
|
|
private static Logger logger = Logger.getLogger(SEPAExportAdapterNBD.class.getName());
|
|
|
|
public static final String ERROR_CONFIG = "CONFIG_ERROR";
|
|
public static final String ERROR_MISSING_INVOICE = "ERROR_MISSING_INVOICE";
|
|
|
|
final String TYPE_TEXTBLOCK = "textblock";
|
|
|
|
@EJB
|
|
ReportService reportService;
|
|
|
|
@Inject
|
|
SepaWorkflowService sepaWorkflowService;
|
|
|
|
@Inject
|
|
DocumentService documentService;
|
|
|
|
@Inject
|
|
WorkflowService workflowService;
|
|
|
|
@Inject
|
|
SnapshotService snapshotService;
|
|
|
|
/**
|
|
* This method collects a data set with all invoices and computes a NBA Excel
|
|
* File. The templated is loaded from a text block
|
|
*
|
|
* @throws PluginException
|
|
*/
|
|
@SuppressWarnings("unchecked")
|
|
@Override
|
|
public ItemCollection execute(ItemCollection sepaExport, ItemCollection event)
|
|
throws AdapterException, PluginException {
|
|
|
|
String key = sepaExport.getItemValueString("name");
|
|
|
|
// Textblock laden
|
|
List<ItemCollection> sepaConfigList = workflowService.evalWorkflowResultXML(event, "imixs-sepa", "CONFIG",
|
|
sepaExport,
|
|
false);
|
|
if (sepaConfigList == null || sepaConfigList.size() != 1) {
|
|
// no configuration found!
|
|
throw new PluginException(OpenAIAPIAdapter.class.getSimpleName(), ERROR_CONFIG,
|
|
"Missing or invalid imixs-sepa definition in Event " + sepaExport.getTaskID() + "."
|
|
+ sepaExport.getEventID());
|
|
}
|
|
|
|
ItemCollection sepaConf = sepaConfigList.get(0);
|
|
String template = sepaConf.getItemValueString("template");
|
|
FileData fileData = loadTextBlockFileData(sepaConf.getItemValueString("textblock"), template);
|
|
|
|
// do we found the document?
|
|
if (fileData == null) {
|
|
throw new PluginException(OPListExportAdapterByWeek.class.getSimpleName(),
|
|
ERROR_CONFIG,
|
|
"invalid sepa configuration in model event - template not found!");
|
|
}
|
|
fileData.setName(template);
|
|
// create the attachment based on the report definition
|
|
// attach a file to the current workitem
|
|
// create a harmonized debitor name for the filename.....
|
|
String sDepName = sepaExport.getItemValueString(SepaWorkflowService.ITEM_DBTR_NAME);
|
|
sDepName = sDepName.replace("&", "_");
|
|
sDepName = sDepName.replace(">", "_");
|
|
sDepName = sDepName.replace("<", "_");
|
|
sDepName = sDepName.replace(" ", "_");
|
|
// build a timestamp for the filename
|
|
DateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HHmm");
|
|
String sepaFileName = "sepa_" + sDepName + "_" + df.format(new Date()) + ".xlsx";
|
|
|
|
fileData.setName(sepaFileName);
|
|
|
|
// append document
|
|
logger.info("...append invoices to Template: " + template);
|
|
|
|
// get the data source based on the $workitemref ....
|
|
List<String> refList = sepaExport.getItemValue("$workitemref");
|
|
List<ItemCollection> data = new ArrayList<ItemCollection>();
|
|
logger.info("...SEPA export started - " + refList.size() + " invoices found...");
|
|
|
|
for (String ref : refList) {
|
|
// load invoice
|
|
ItemCollection invoice = sepaWorkflowService.loadInvoice(ref);
|
|
if (invoice == null) {
|
|
logger.warning("Invoice '" + ref + "' not found! SEPA Export can not be executed");
|
|
continue;
|
|
}
|
|
// avoid unsupported characters in sepa fields
|
|
invoice = sepaWorkflowService.harmonizeSEPAItem(invoice, SepaWorkflowService.ITEM_CDTR_NAME);
|
|
invoice = sepaWorkflowService.harmonizeSEPAItem(invoice, SepaWorkflowService.ITEM_DBTR_NAME);
|
|
data.add(invoice);
|
|
}
|
|
|
|
// finally we add the teh invoices
|
|
try {
|
|
insertInvoiceRows(sepaExport, fileData, data);
|
|
} catch (PluginException e) {
|
|
// TODO Auto-generated catch block
|
|
e.printStackTrace();
|
|
} catch (QueryException e) {
|
|
// TODO Auto-generated catch block
|
|
e.printStackTrace();
|
|
}
|
|
|
|
return sepaExport;
|
|
}
|
|
|
|
/**
|
|
* This helper method inserts a row for each invoice of the OPListe at row 16
|
|
* into the excel template file
|
|
* <p>
|
|
* The method copies the Row A16 as a reference row
|
|
* <p>
|
|
* The named cell 'TOTAL' should contain the summary formula. It will be
|
|
* evaluated at the end.
|
|
*
|
|
* @throws PluginException
|
|
* @throws QueryException
|
|
*/
|
|
private void insertInvoiceRows(ItemCollection workitem, FileData fileData, List<ItemCollection> invoices)
|
|
throws PluginException, QueryException {
|
|
|
|
// load XSSFWorkbook
|
|
try (InputStream imputStream = new ByteArrayInputStream(fileData.getContent())) {
|
|
XSSFWorkbook doc = new XSSFWorkbook(imputStream);
|
|
// NOTE: we only take the first sheet !
|
|
XSSFSheet sheet = doc.getSheetAt(0);
|
|
CellReference cr = new CellReference("A2");
|
|
XSSFRow referenceRow = sheet.getRow(cr.getRow());
|
|
|
|
int rowPos = 1;
|
|
|
|
// int lastRow = sheet.getLastRowNum();
|
|
int lastRow = 999;
|
|
logger.finest("Last rownum=" + lastRow);
|
|
sheet.shiftRows(rowPos, lastRow, invoices.size(), true, true);
|
|
|
|
for (ItemCollection invoice : invoices) {
|
|
logger.finest("......copy row...");
|
|
// now create a new line..
|
|
XSSFRow row = sheet.createRow(rowPos);
|
|
row.copyRowFrom(referenceRow, new CellCopyPolicy());
|
|
// insert values
|
|
row.getCell(0).setCellValue(invoice.getItemValueString("numsequencenumber"));
|
|
row.getCell(1).setCellValue(invoice.getItemValueDate("invoice.date"));
|
|
row.getCell(2).setCellValue(invoice.getItemValueString("invoice.number"));
|
|
row.getCell(3).setCellValue(invoice.getItemValueDate("invoice.duedate"));
|
|
|
|
row.getCell(4).setCellValue(invoice.getItemValueDouble("invoice.total"));
|
|
|
|
rowPos++;
|
|
}
|
|
// delete reference row A2
|
|
// sheet.shiftRows(1, 1 + invoices.size(), -1, true, true);
|
|
// sheet.shiftRows(1, lastRow + invoices.size(), -1, true, true);
|
|
|
|
ByteArrayOutputStream byteArrayOutputStream = new ByteArrayOutputStream();
|
|
// write back the file
|
|
|
|
doc.write(byteArrayOutputStream);
|
|
doc.close();
|
|
byte[] newContent = byteArrayOutputStream.toByteArray();
|
|
FileData fileDataNew = new FileData(fileData.getName(), newContent, fileData.getContentType(), null);
|
|
// update the fileData
|
|
workitem.addFileData(fileDataNew);
|
|
logger.finest("......new document added");
|
|
|
|
} catch (IOException e) {
|
|
throw new PluginException(SEPAExportAdapterNBD.class.getSimpleName(), ERROR_CONFIG,
|
|
"failed to update sepa export: " + e.getMessage());
|
|
}
|
|
}
|
|
|
|
/**
|
|
* This method returns a text-block ItemCollection for a specified name.
|
|
*
|
|
* @param name in attribute txtname
|
|
*
|
|
*
|
|
*/
|
|
public FileData loadTextBlockFileData(String name, String fileName) {
|
|
ItemCollection textBlockItemCollection = null;
|
|
|
|
// load text-block by name....
|
|
String sQuery = "(type:\"" + TYPE_TEXTBLOCK + "\" AND txtname:\"" + name + "\")";
|
|
Collection<ItemCollection> col;
|
|
try {
|
|
// find the textblock...
|
|
col = documentService.find(sQuery, 1, 0);
|
|
if (col.size() > 0) {
|
|
textBlockItemCollection = col.iterator().next();
|
|
// fetch the fileData...
|
|
return snapshotService.getWorkItemFile(textBlockItemCollection.getUniqueID(), fileName);
|
|
|
|
} else {
|
|
logger.warning("Missing text-block : '" + name + "'");
|
|
}
|
|
} catch (QueryException e) {
|
|
logger.warning("getTextBlock - invalid query: " + e.getMessage());
|
|
}
|
|
|
|
return null;
|
|
}
|
|
} |