1
\$\begingroup\$

I'm pretty new to Java development and have written a little POJO to "PDF Form Filler" program. I'd be interested in recommendations and suggestions about coding style, used methods and classes and so on. The project uses apache's pdfBox and can be found in total at https://github.com/baao/pdffiller.

Extra Question:

As you can see in my POJO, all the properties are Strings, as they have to be written as Strings. Should I change this and convert them to string later.

Here's the main class:

package formfiller;

import org.apache.pdfbox.pdmodel.PDDocument;
import org.apache.pdfbox.pdmodel.interactive.form.PDAcroForm;

import java.io.File;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import java.time.Instant;
import java.time.ZoneOffset;
import java.time.format.DateTimeFormatter;

public final class PdfFormFiller {
    private String thisMoment;
    private PDDocument pdfDocument;
    private Method[] methods;

    public static void main(String[] a) throws Exception {
        NachforschungsauftragPOJO nachforschungsauftragPOJO = new NachforschungsauftragPOJO("kljsdfls");
        nachforschungsauftragPOJO.setAmountNachnahme("1000");
        new PdfFormFiller().fillAllFieldsWithTheirNames();
    }

    private PdfFormFiller() throws IOException {
        this("/opt/IdeaProjects/Bewertungsmailer/src/main/resources/GKS_Nachforschungsauftrag.pdf");
    }

    public PdfFormFiller(String pdfFile) throws IOException {
        setThisMoment();
        pdfDocument = PDDocument.load(new File(pdfFile));
    }

    public PdfFormFiller fill(Object pojo) throws IOException, NoFormCouldBeFoundException {
        if (this.methods == null) this.forSchema(pojo.getClass());
        PDAcroForm form = pdfDocument.getDocumentCatalog().getAcroForm();
        if (form == null) throw new NoFormCouldBeFoundException();
        for (Method m : getMethods()) {
            if (m.isAnnotationPresent(FormField.class)) {
                FormField formField = m.getAnnotation(FormField.class);
                try {
                    if (!formField.isCheckBox()) {
                        form.getField(formField.name()).setValue((String) m.invoke(pojo));
                    } else if (formField.isCheckBox() && (boolean) m.invoke(pojo)) {
                        form.getField(formField.name()).setValue(formField.value());
                        if (! formField.equalField().equals("")) form.getField(formField.equalField()).setValue(formField.value());
                    }
                    if (!formField.equalField().equals("") && ! formField.isCheckBox()) {
                        form.getField(formField.equalField()).setValue((String) m.invoke(pojo));
                    }
                } catch (IllegalAccessException | InvocationTargetException e) {
                    System.out.println("--- Method couldn't be executed: " + m.getName() + " ---");
                    e.printStackTrace();
                } catch (NullPointerException nullPointer) {
                    System.out.println("--- Field not found in PDF Form: " + formField.name() + " ---");
                    nullPointer.printStackTrace();
                }
            }
        }
        return this;
    }

    public void fillAllFieldsWithTheirNames() throws IOException, NoFormCouldBeFoundException {
        PDAcroForm form = pdfDocument.getDocumentCatalog().getAcroForm();
        if (form == null) throw new NoFormCouldBeFoundException();
        form.getFields().forEach(field -> {
            System.out.println(field.getPartialName());
            try {
                field.setValue(field.getPartialName());
            } catch (Exception e) {
                try {
                    field.setValue("On");
                } catch (Exception ee) {
                    ee.printStackTrace();
                }
            }
        });
        this.save();
    }

    private String getThisMoment() {
        return thisMoment;
    }

    private void setThisMoment() {
        this.thisMoment = DateTimeFormatter.ofPattern("yyyy-MM-dd'T'HH:mmX")
                .withZone(ZoneOffset.UTC)
                .format(Instant.now());
    }

    private Method[] getMethods() {
        return methods;
    }

    public PdfFormFiller forSchema(Class forClass) {
        this.methods = forClass.getMethods();
        return this;
    }

    public boolean save(String fileName) {
        try {
            pdfDocument.save(fileName);
            pdfDocument.close();
        } catch (IOException e) {
            e.printStackTrace();
            return false;
        }
        return true;
    }

    public boolean save() throws IOException {
        return this.save(getThisMoment() + ".pdf");
    }

    public boolean fillAndSave(Object pojo) throws IOException, NoFormCouldBeFoundException {
        return this
                .fill(pojo)
                .save();
    }

    public boolean fillAndSave(Object pojo, String outputFileName) throws IOException, NoFormCouldBeFoundException {
        return this
                .fill(pojo)
                .save(outputFileName);
    }


}

The annotation @interface:

package formfiller;

import java.lang.annotation.ElementType;
import java.lang.annotation.Retention;
import java.lang.annotation.RetentionPolicy;
import java.lang.annotation.Target;

@Retention(RetentionPolicy.RUNTIME)
@Target(ElementType.METHOD)
public @interface FormField {
    String name();
    boolean isCheckBox() default false;
    String value() default "";
    String equalField() default "";
}

The custom exception

package formfiller;

public class NoFormCouldBeFoundException extends Exception{

    public NoFormCouldBeFoundException() {
        super("There's no form found in the document!");
    }
}

The pojo I'm using is quite large, I've omitted hashCode, equals and toString function:

package formfiller;

public class NachforschungsauftragPOJO {
private boolean dhlPackage;
private boolean nachnahmeSendung;
private boolean paeckchenOderWarensendung;
private boolean internationalPackage;
private boolean paeckchenInternational;
private boolean unfrei;
private boolean isHigherInsured2500;
private boolean isHigherInsured25000;
private String sentDate;
private String shipmentWeight;
private String bankNachnahme;
private String verwendungszweckNachnahme;
private String senderName;
private String receiverName;
private String senderStreetHouseNo;
private String receiverStreetHouseNo;
private String senderPlzOrt;
private String receiverPlzOrt;
private String senderCountry;
private String receiverCountry;
private String senderPhoneEmail;
private String receiverPhoneEmail;
private String refundIban;
private String refundBic;
private String refundBank;
private String refundDifferentNameOfAccountHolder;
private String refundDifferentAddressOfAccountHolder;
private String sendungsnummer;
private String amountNachnahme;
private String bicNachnahme;
private String ibanNachnahme;
private String articleOne;
private String articleTwo;
private String articleThree;
private String articleFour;
private String articleFive;

private String euroArticleOne;
private String euroArticleTwo;
private String euroArticleThree;
private String euroArticleFour;
private String euroArticleFive;

private String centArticleOne;
private String centArticleTwo;
private String centArticleThree;
private String centArticleFour;
private String centArticleFive;

private String euroSumBrutto;
private String centSumBrutto;
private String euroUst;
private String centUst;
private String euroSumNetto;
private String centSumNetto;

private String orderId;

public String getOrderId() {
    return orderId;
}

public void setOrderId(String orderId) {
    this.orderId = orderId;
}

public NachforschungsauftragPOJO(String orderId) {
    this.orderId = orderId;
}

@FormField(name = "DHL Paket", isCheckBox = true, value = "On", equalField = "DHL Paket_2")
public boolean isDhlPackage() {
    return dhlPackage;
}

public void setDhlPackage(boolean dhlPackage) {
    this.dhlPackage = dhlPackage;
}

@FormField(name = "Nachnahmebetrag Die Sendung wurde dem Empfänger", isCheckBox = true, value = "On", equalField = "Nachnahmebetrag Die Sendung wurde dem Empfänger_2")
public boolean isNachnahmeSendung() {
    return nachnahmeSendung;
}

public void setNachnahmeSendung(boolean nachnahmeSendung) {
    this.nachnahmeSendung = nachnahmeSendung;
}

@FormField(name = "anderen Produkt", isCheckBox = true, value = "On", equalField = "anderen Produkt_2")
public boolean isPaeckchenOderWarensendung() {
    return paeckchenOderWarensendung;
}

public void setPaeckchenOderWarensendung(boolean paeckchenOderWarensendung) {
    this.paeckchenOderWarensendung = paeckchenOderWarensendung;
}

@FormField(name = "DHL Paket International  Weltpaket", isCheckBox = true, value = "On", equalField = "DHL Paket International  Weltpaket_2")
public boolean isInternationalPackage() {
    return internationalPackage;
}

public void setInternationalPackage(boolean internationalPackage) {
    this.internationalPackage = internationalPackage;
}

@FormField(name = "DHL Päckchen International", isCheckBox = true, value = "On", equalField = "DHL Päckchen International_2")
public boolean isPaeckchenInternational() {
    return paeckchenInternational;
}

public void setPaeckchenInternational(boolean paeckchenInternational) {
    this.paeckchenInternational = paeckchenInternational;
}

@FormField(name = "unfrei", isCheckBox = true, value = "On", equalField = "unfrei_2")
public boolean isUnfrei() {
    return unfrei;
}

public void setUnfrei(boolean unfrei) {
    this.unfrei = unfrei;
}

@FormField(name = "2500 Euro oder", isCheckBox = true, value = "On", equalField = "2500 Euro oder_2")
public boolean isHigherInsured2500() {
    return isHigherInsured2500;
}

public void setHigherInsured2500(boolean higherInsured2500) {
    isHigherInsured2500 = higherInsured2500;
}

@FormField(name = "25000 Euro", isCheckBox = true, value = "On", equalField = "25000 Euro_2")
public boolean isHigherInsured25000() {
    return isHigherInsured25000;
}

public void setHigherInsured25000(boolean higherInsured25000) {
    isHigherInsured25000 = higherInsured25000;
}

@FormField(name = "Text12")
public String getSentDate() {
    return sentDate;
}

public void setSentDate(String sentDate) {
    this.sentDate = sentDate;
}

@FormField(name = "Text13")
public String getShipmentWeight() {
    return shipmentWeight;
}

public void setShipmentWeight(String shipmentWeight) {
    this.shipmentWeight = shipmentWeight;
}

@FormField(name = "Bank", equalField = "Bank_3")
public String getBankNachnahme() {
    return bankNachnahme;
}

public void setBankNachnahme(String bankNachnahme) {
    this.bankNachnahme = bankNachnahme;
}

@FormField(name = "Verwendungszweck", equalField = "Verwendungszweck_2")
public String getVerwendungszweckNachnahme() {
    return verwendungszweckNachnahme;
}

public void setVerwendungszweckNachnahme(String verwendungszweckNachnahme) {
    this.verwendungszweckNachnahme = verwendungszweckNachnahme;
}

@FormField(name = "Name Vorname  Firma", equalField = "Name Vorname  Firma_3")
public String getSenderName() {
    return senderName;
}

public void setSenderName(String senderName) {
    this.senderName = senderName;
}

@FormField(name = "Name Vorname  Firma_2", equalField = "Name Vorname  Firma_4")
public String getReceiverName() {
    return receiverName;
}

public void setReceiverName(String receiverName) {
    this.receiverName = receiverName;
}

@FormField(name = "Straße Hausnummer", equalField = "Straße Hausnummer_3")
public String getSenderStreetHouseNo() {
    return senderStreetHouseNo;
}

public void setSenderStreetHouseNo(String senderStreetHouseNo) {
    this.senderStreetHouseNo = senderStreetHouseNo;
}

@FormField(name = "Straße Hausnummer_2", equalField = "Straße Hausnummer_4")
public String getReceiverStreetHouseNo() {
    return receiverStreetHouseNo;
}

public void setReceiverStreetHouseNo(String receiverStreetHouseNo) {
    this.receiverStreetHouseNo = receiverStreetHouseNo;
}

@FormField(name = "PLZ Ort", equalField = "PLZ Ort_3")
public String getSenderPlzOrt() {
    return senderPlzOrt;
}

public void setSenderPlzOrt(String senderPlzOrt) {
    this.senderPlzOrt = senderPlzOrt;
}

@FormField(name = "PLZ Ort_2", equalField = "PLZ Ort_4")
public String getReceiverPlzOrt() {
    return receiverPlzOrt;
}

public void setReceiverPlzOrt(String receiverPlzOrt) {
    this.receiverPlzOrt = receiverPlzOrt;
}

@FormField(name = "Land", equalField = "Land_3")
public String getSenderCountry() {
    return senderCountry;
}

public void setSenderCountry(String senderCountry) {
    this.senderCountry = senderCountry;
}

@FormField(name = "Land_2", equalField = "Land_4")
public String getReceiverCountry() {
    return receiverCountry;
}

public void setReceiverCountry(String receiverCountry) {
    this.receiverCountry = receiverCountry;
}

@FormField(name = "TelefonNr mit Durchwahl Ansprechpartner EMailAdresse", equalField = "TelefonNr mit Durchwahl Ansprechpartner EMailAdresse_3")
public String getSenderPhoneEmail() {
    return senderPhoneEmail;
}

public void setSenderPhoneEmail(String senderPhoneEmail) {
    this.senderPhoneEmail = senderPhoneEmail;
}

@FormField(name = "TelefonNr mit Durchwahl Ansprechpartner EMailAdresse_2", equalField = "TelefonNr mit Durchwahl Ansprechpartner EMailAdresse_4")
public String getReceiverPhoneEmail() {
    return receiverPhoneEmail;
}

public void setReceiverPhoneEmail(String receiverPhoneEmail) {
    this.receiverPhoneEmail = receiverPhoneEmail;
}

@FormField(name = "IBAN", equalField = "IBAN_2")
public String getRefundIban() {
    return refundIban;
}

public void setRefundIban(String refundIban) {
    this.refundIban = refundIban;
}

@FormField(name = "BIC", equalField = "BIC_2")
public String getRefundBic() {
    return refundBic;
}

public void setRefundBic(String refundBic) {
    this.refundBic = refundBic;
}

@FormField(name = "Bank_2", equalField = "Bank_4")
public String getRefundBank() {
    return refundBank;
}

public void setRefundBank(String refundBank) {
    this.refundBank = refundBank;
}

@FormField(name = "Kontoinhaber bei Abweichungen oder Abtretung", equalField = "Kontoinhaber bei Abweichungen oder Abtretung_2")
public String getRefundDifferentNameOfAccountHolder() {
    return refundDifferentNameOfAccountHolder;
}

public void setRefundDifferentNameOfAccountHolder(String refundDifferentNameOfAccountHolder) {
    this.refundDifferentNameOfAccountHolder = refundDifferentNameOfAccountHolder;
}

@FormField(name = "Anschrift des Kontoinhabers bei Abweichungen oder Abtretung", equalField = "Anschrift des Kontoinhabers bei Abweichungen oder Abtretung_2")
public String getRefundDifferentAddressOfAccountHolder() {
    return refundDifferentAddressOfAccountHolder;
}

public void setRefundDifferentAddressOfAccountHolder(String refundDifferentAddressOfAccountHolder) {
    this.refundDifferentAddressOfAccountHolder = refundDifferentAddressOfAccountHolder;
}

@FormField(name = "Text1")
public String getSendungsnummer() {
    return sendungsnummer;
}

public void setSendungsnummer(String sendungsnummer) {
    this.sendungsnummer = sendungsnummer;
}

@FormField(name = "Text2")
public String getAmountNachnahme() {
    return amountNachnahme;
}

public void setAmountNachnahme(String amountNachnahme) {
    this.amountNachnahme = amountNachnahme;
}

@FormField(name = "Text3")
public String getBicNachnahme() {
    return bicNachnahme;
}


public void setBicNachnahme(String bicNachnahme) {
    this.bicNachnahme = bicNachnahme;
}

@FormField(name = "Text4")
public String getIbanNachnahme() {
    return ibanNachnahme;
}


public void setIbanNachnahme(String ibanNachnahme) {
    this.ibanNachnahme = ibanNachnahme;
}

@FormField(name = "Text5")
public String getArticleOne() {
    return articleOne;
}

public void setArticleOne(String articleOne) {
    this.articleOne = articleOne;
}

@FormField(name = "Text6")
public String getArticleTwo() {
    return articleTwo;
}

public void setArticleTwo(String articleTwo) {
    this.articleTwo = articleTwo;
}

@FormField(name = "Text7")
public String getArticleThree() {
    return articleThree;
}

public void setArticleThree(String articleThree) {
    this.articleThree = articleThree;
}

@FormField(name = "Text8")
public String getArticleFour() {
    return articleFour;
}

public void setArticleFour(String articleFour) {
    this.articleFour = articleFour;
}

@FormField(name = "Text9")
public String getArticleFive() {
    return articleFive;
}

public void setArticleFive(String articleFive) {
    this.articleFive = articleFive;
}

@FormField(name = "EuroRow1")
public String getEuroArticleOne() {
    return euroArticleOne;
}

public void setEuroArticleOne(String euroArticleOne) {
    this.euroArticleOne = euroArticleOne;
}

@FormField(name = "EuroRow2")
public String getEuroArticleTwo() {
    return euroArticleTwo;
}

public void setEuroArticleTwo(String euroArticleTwo) {
    this.euroArticleTwo = euroArticleTwo;
}

@FormField(name = "EuroRow3")
public String getEuroArticleThree() {
    return euroArticleThree;
}

public void setEuroArticleThree(String euroArticleThree) {
    this.euroArticleThree = euroArticleThree;
}

@FormField(name = "EuroRow4")
public String getEuroArticleFour() {
    return euroArticleFour;
}

public void setEuroArticleFour(String euroArticleFour) {
    this.euroArticleFour = euroArticleFour;
}

@FormField(name = "Text10")
public String getEuroArticleFive() {
    return euroArticleFive;
}

public void setEuroArticleFive(String euroArticleFive) {
    this.euroArticleFive = euroArticleFive;
}

@FormField(name = "CentRow1")
public String getCentArticleOne() {
    return centArticleOne;
}

public void setCentArticleOne(String centArticleOne) {
    this.centArticleOne = centArticleOne;
}

@FormField(name = "CentRow2")
public String getCentArticleTwo() {
    return centArticleTwo;
}

public void setCentArticleTwo(String centArticleTwo) {
    this.centArticleTwo = centArticleTwo;
}

@FormField(name = "CentRow3")
public String getCentArticleThree() {
    return centArticleThree;
}

public void setCentArticleThree(String centArticleThree) {
    this.centArticleThree = centArticleThree;
}

@FormField(name = "CentRow4")
public String getCentArticleFour() {
    return centArticleFour;
}

public void setCentArticleFour(String centArticleFour) {
    this.centArticleFour = centArticleFour;
}

@FormField(name = "CentSumme Brutto abzüglich USt nach  2 UStG  Summe Netto")
public String getCentArticleFive() {
    return centArticleFive;
}

public void setCentArticleFive(String centArticleFive) {
    this.centArticleFive = centArticleFive;
}

@FormField(name = "Text11")
public String getEuroSumBrutto() {
    return euroSumBrutto;
}

public void setEuroSumBrutto(String euroSumBrutto) {
    this.euroSumBrutto = euroSumBrutto;
}

@FormField(name = "CentSumme Brutto abzüglich USt nach  2 UStG  Summe Netto_2")
public String getCentSumBrutto() {
    return centSumBrutto;
}

public void setCentSumBrutto(String centSumBrutto) {
    this.centSumBrutto = centSumBrutto;
}

@FormField(name = "EuroSumme Brutto abzüglich USt nach  2 UStG  Summe Netto_2")
public String getEuroUst() {
    return euroUst;
}

public void setEuroUst(String euroUst) {
    this.euroUst = euroUst;
}

@FormField(name = "CentSumme Brutto abzüglich USt nach  2 UStG  Summe Netto_3")
public String getCentUst() {
    return centUst;
}

public void setCentUst(String centUst) {
    this.centUst = centUst;
}

@FormField(name = "EuroSumme Brutto abzüglich USt nach  2 UStG  Summe Netto_3")
public String getEuroSumNetto() {
    return euroSumNetto;
}

public void setEuroSumNetto(String euroSumNetto) {
    this.euroSumNetto = euroSumNetto;
}

@FormField(name = "CentSumme Brutto abzüglich USt nach  2 UStG  Summe Netto_4")
public String getCentSumNetto() {
    return centSumNetto;
}

public void setCentSumNetto(String centSumNetto) {
    this.centSumNetto = centSumNetto;
}

The method fillAllFieldsWithTheirNames() is intentionally bad :-) and just for a first scrape of the form's fields...

In case you need the pdf I'm working on... here it is

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Browse other questions tagged or ask your own question.