001/* Copyright (C) 2014 konik.io
002 *
003 * This file is part of the Konik library.
004 *
005 * The Konik library is free software: you can redistribute it and/or modify
006 * it under the terms of the GNU Affero General Public License as
007 * published by the Free Software Foundation, either version 3 of the
008 * License, or (at your option) any later version.
009 *
010 * The Konik library is distributed in the hope that it will be useful,
011 * but WITHOUT ANY WARRANTY; without even the implied warranty of
012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
013 * GNU Affero General Public License for more details.
014 *
015 * You should have received a copy of the GNU Affero General Public License
016 * along with the Konik library. If not, see <http://www.gnu.org/licenses/>.
017 */
018package io.konik.zugferd.entity;
019
020import com.neovisionaries.i18n.LanguageCode;
021import io.konik.jaxb.adapter.PeriodCompleteToDateTimeAdapter;
022import io.konik.validator.annotation.Basic;
023import io.konik.validator.annotation.Extended;
024import io.konik.validator.annotation.NotBlank;
025import io.konik.zugferd.unece.codes.DocumentCode;
026import io.konik.zugferd.unqualified.Indicator;
027import io.konik.zugferd.unqualified.ZfDate;
028
029import javax.validation.Valid;
030import javax.validation.constraints.NotNull;
031import javax.xml.bind.annotation.XmlAccessType;
032import javax.xml.bind.annotation.XmlAccessorType;
033import javax.xml.bind.annotation.XmlElement;
034import javax.xml.bind.annotation.XmlType;
035import javax.xml.bind.annotation.adapters.CollapsedStringAdapter;
036import javax.xml.bind.annotation.adapters.XmlJavaTypeAdapter;
037import java.io.Serializable;
038import java.util.ArrayList;
039import java.util.List;
040
041import static java.util.Collections.addAll;
042
043/**
044 * = The Invoice Document Header
045 */
046@XmlAccessorType(XmlAccessType.FIELD)
047@XmlType(name = "HeaderExchangedDocument", propOrder = { "invoiceNumber", "name", "code", "issued", "copy",
048      "languages", "notes", "contractualDueDate" })
049public class Header implements Serializable {
050
051   @XmlElement(name = "ID")
052   @XmlJavaTypeAdapter(CollapsedStringAdapter.class)
053   private String invoiceNumber;
054
055   @XmlElement(name = "Name")
056   private String name;
057
058   @XmlElement(name = "TypeCode")
059   private DocumentCode code;
060
061   @XmlElement(name = "IssueDateTime")
062   private ZfDate issued;
063
064   @XmlElement(name = "CopyIndicator")
065   private Indicator copy;
066
067   @XmlElement(name = "LanguageID")
068   private List<LanguageCode> languages;
069
070   @XmlElement(name = "IncludedNote")
071   private List<Note> notes;
072
073   @XmlElement(name = "EffectiveSpecifiedPeriod")
074   @XmlJavaTypeAdapter(value = PeriodCompleteToDateTimeAdapter.class)
075   private ZfDate contractualDueDate;
076
077   /**
078    * Gets the invoice number.
079    * 
080    * Example:: {@code 2012-12345}
081    *
082    * @return the invoice number
083    */
084   @Basic
085   @NotBlank
086   public String getInvoiceNumber() {
087      return invoiceNumber;
088   }
089
090   /**
091    * Sets the invoice number.
092    * 
093    * Example:: {@code 2012-12345}
094    *
095    * @param invoiceNumber the invoice number
096    * @return the header document
097    */
098   public Header setInvoiceNumber(String invoiceNumber) {
099      this.invoiceNumber = invoiceNumber;
100      return this;
101   }
102
103   /**
104    * Gets the free text invoice name.
105    * 
106    * Example:: {@code invoice, credit advice, debit note, pro forma invoice}
107    * 
108    * @return the invoice name
109    */
110   @Basic
111   @NotBlank
112   public String getName() {
113      return this.name;
114   }
115
116   /**
117    * Adds a free text invoice name.
118    * 
119    * Example:: {@code invoice, credit advice, debit note, pro forma invoice}
120    *
121    * @param name the new name
122    * @return the exchanged document
123    * @see #getName()
124    */
125   public Header setName(String name) {
126      this.name = name;
127      return this;
128   }
129
130   /**
131    * Gets +UNCL 1001+ Document Name Code.
132    * 
133    * Example:: {@code 380, 381, 383, 389, 261}
134    * 
135    * @return the document name code
136    * @see http://www.unece.org/trade/untdid/d13b/tred/tred1001.htm[UN/EDIFACT 1001 Document name coe^]
137    */
138   @Basic
139   @NotNull
140   public DocumentCode getCode() {
141      return code;
142   }
143
144   /**
145    * Sets the +UNCL 1001+ Document Name Code.
146    * 
147    * Example:: {@code 380, 381, 383, 389, 261}
148    *
149    * @param code the new document name code
150    * @return the header document
151    * @see http://www.unece.org/trade/untdid/d13b/tred/tred1001.htm[UN/EDIFACT 1001 Document name coe^]
152    */
153
154   public Header setCode(DocumentCode code) {
155      this.code = code;
156      return this;
157   }
158
159   /**
160    * Gets the invoice issue date time.
161    * 
162    * @return the issue date time
163    */
164   @Basic
165   @Valid
166   @NotNull
167   public ZfDate getIssued() {
168      return issued;
169   }
170
171   /**
172    * Sets the invoice issue date time.
173    * 
174    * 
175    * @param issued the new issue date time
176    * @return the exchanged document
177    */
178   public Header setIssued(ZfDate issued) {
179      this.issued = issued;
180      return this;
181   }
182
183   /**
184    * Checks if is copy.
185    *
186    * @return the indicator
187    */
188   @Extended
189   public boolean isCopy() {
190      return copy == null?false:copy.getIndicator();
191   }
192
193   /**
194    * Sets the copy.
195    *
196    * @param copy the new copy
197    */
198   public void setCopy(boolean copy) {
199      this.copy = new Indicator(copy);
200   }
201
202   /**
203    * Gets the languages.
204    *
205    * @return the languages
206    */
207   @Extended
208   public List<LanguageCode> getLanguages() {
209      if (languages == null) {
210         languages = new ArrayList<LanguageCode>();
211      }
212      return languages;
213   }
214
215   /**
216    * Adds the language.
217    *
218    * @param language the language
219    */
220   public void addLanguage(LanguageCode language) {
221      getLanguages().add(language);
222   }
223
224   /**
225    * Gets the invoice header notes.
226    * 
227    * Example::
228    * - {@code note content: }{@link Note#getContent() Invoice like agreed on the telephone with Mr.X.} -
229    * - {@code note subject code as UNCL 4451: }{@link Note#getSubjectCode() AAK}
230    * 
231    * @return the included note
232    */
233   @Basic
234   @Valid  
235   public List<Note> getNotes() {
236      if (notes == null) {
237         notes = new ArrayList<Note>();
238      }
239      return this.notes;
240   }
241
242   /**
243    * Adds a invoice header note.
244    * 
245    * Example::
246    * - {@code note content: }{@link Note#getContent() Invoice like agreed on the telephone with Mr.X.} -
247    * - {@code note subject code as UNCL 4451: }{@link Note#getSubjectCode() AAK}
248    *
249    * @param additionalNote the additional note
250    * @return the header
251    */
252   public Header addNote(Note... additionalNote) {
253      addAll(getNotes(), additionalNote);
254      return this;
255   }
256
257   /**
258    * Gets contractual due date of the invoice.
259    * 
260    * Remark: Should only be used, if the contractual due date is different to the payment due date (e.g. with SEPA credit transfers).
261    *  
262    * @return the contractual due date
263    */
264   @Extended
265   public ZfDate getContractualDueDate() {
266      return contractualDueDate;
267   }
268
269   /**
270    * Sets contractual due date of the invoice.
271    * 
272    * Remark: Should only be used, if the contractual due date is different to the payment due date (e.g. with SEPA credit transfers).
273    *
274    * @param contractualDueDate the contractual due date
275    * @return the header
276    */
277   public Header setContractualDueDate(ZfDate contractualDueDate) {
278      this.contractualDueDate = contractualDueDate;
279      return this;
280   }
281
282}