]> git.mxchange.org Git - jproduct-core.git/blob - src/org/mxchange/jproduct/model/product/GenericProduct.java
Changed copyright notice to the FSF, so after my death they will continue my
[jproduct-core.git] / src / org / mxchange / jproduct / model / product / GenericProduct.java
1 /*
2  * Copyright (C) 2016, 2017 Free Software Foundation
3  *
4  * This program is free software: you can redistribute it and/or modify
5  * it under the terms of the GNU General Public License as published by
6  * the Free Software Foundation, either version 3 of the License, or
7  * (at your option) any later version.
8  *
9  * This program is distributed in the hope that it will be useful,
10  * but WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12  * GNU General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program.  If not, see <http://www.gnu.org/licenses/>.
16  */
17 package org.mxchange.jproduct.model.product;
18
19 import java.text.MessageFormat;
20 import java.util.Date;
21 import java.util.Objects;
22 import javax.persistence.Basic;
23 import javax.persistence.CascadeType;
24 import javax.persistence.Column;
25 import javax.persistence.Entity;
26 import javax.persistence.EnumType;
27 import javax.persistence.Enumerated;
28 import javax.persistence.GeneratedValue;
29 import javax.persistence.GenerationType;
30 import javax.persistence.Id;
31 import javax.persistence.Index;
32 import javax.persistence.JoinColumn;
33 import javax.persistence.NamedQueries;
34 import javax.persistence.NamedQuery;
35 import javax.persistence.OneToOne;
36 import javax.persistence.Table;
37 import javax.persistence.Temporal;
38 import javax.persistence.TemporalType;
39 import javax.persistence.Transient;
40 import org.mxchange.jcontactsbusiness.model.basicdata.BasicData;
41 import org.mxchange.jcontactsbusiness.model.basicdata.BusinessBasicData;
42 import org.mxchange.jproduct.model.category.Category;
43 import org.mxchange.jproduct.model.category.ProductCategory;
44 import org.mxchange.jproduct.model.product.agegroup.AgeGroup;
45
46 /**
47  * Generic product class
48  * <p>
49  * @author Roland Häder<roland@mxchange.org>
50  * TODO: Find a better name
51  */
52 @Entity (name = "generic_products")
53 @Table (
54                 name = "generic_products",
55                 indexes = {
56                         @Index (
57                                         name = "idx_i18n_age_size",
58                                         columnList = "product_i18n_key,product_age_group,product_size",
59                                         unique = true
60                         )
61                 }
62 )
63 @NamedQueries (
64                 {
65                         @NamedQuery (name = "AllProducts", query = "SELECT p FROM generic_products AS p ORDER BY p.productId ASC"),
66                         @NamedQuery (name = "AllAvailableProducts", query = "SELECT p FROM generic_products AS p WHERE p.productAvailability=TRUE ORDER BY p.productId ASC")
67                 }
68 )
69 @SuppressWarnings ("PersistenceUnitPresent")
70 public class GenericProduct implements Product {
71
72         /**
73          * Serial number
74          */
75         @Transient
76         private static final long serialVersionUID = 54_578_571_769_283L;
77
78         /**
79          * Product's age group (if any)
80          */
81         @Column (name = "product_age_group")
82         @Enumerated (EnumType.STRING)
83         private AgeGroup productAgeGroup;
84
85         /**
86          * Availability of product
87          */
88         @Basic (optional = false)
89         @Column (name = "product_availability", nullable = false)
90         private Boolean productAvailability;
91
92         /**
93          * Product productCategory
94          */
95         @JoinColumn (name = "product_category_id", referencedColumnName = "category_id", nullable = false, updatable = false)
96         @OneToOne (targetEntity = ProductCategory.class, cascade = CascadeType.REFRESH, optional = false)
97         private Category productCategory;
98
99         /**
100          * When this product has been created
101          */
102         @Basic (optional = false)
103         @Column (name = "product_created", nullable = false, updatable = false)
104         @Temporal (TemporalType.TIMESTAMP)
105         private Date productCreated;
106
107         /**
108          * Currency code for both prices, like EUR or USD
109          */
110         @Basic (optional = false)
111         @Column (name = "product_currency_code", nullable = false, length = 3)
112         private String productCurrencyCode;
113
114         /**
115          * Gross price of product
116          */
117         @Basic (optional = false)
118         @Column (name = "product_gross_price", nullable = false)
119         private Float productGrossPrice;
120
121         /**
122          * I18n key of product
123          */
124         @Basic (optional = false)
125         @Column (name = "product_i18n_key", length = 100, nullable = false)
126         private String productI18nKey;
127
128         /**
129          * Id number of product
130          */
131         @Id
132         @GeneratedValue (strategy = GenerationType.IDENTITY)
133         @Column (name = "product_id", nullable = false, updatable = false)
134         private Long productId;
135
136         /**
137          * The company that has manufactured/produced this product
138          */
139         @JoinColumn (name = "product_manufacturer_id", referencedColumnName = "company_data_id")
140         @OneToOne (targetEntity = BusinessBasicData.class, cascade = CascadeType.REFRESH)
141         private BasicData productManufacturer;
142
143         /**
144          * Net price of product
145          */
146         @Column (name = "product_net_price")
147         private Float productNetPrice;
148
149         /**
150          * Number of product
151          */
152         @Column (name = "product_number")
153         private Long productNumber;
154
155         /**
156          * Product size (like for shoes, clothing)
157          */
158         @Column (name = "product_size", length = 10)
159         private String productSize;
160
161         /**
162          * Tax rate (0-1, by 1=100%)
163          */
164         @Column (name = "product_tax_rate")
165         private Float productTaxRate;
166
167         /**
168          * Amount of this product (for example 1 for 1 liter)
169          */
170         @Basic (optional = false)
171         @Column (name = "product_unit_amount", nullable = false)
172         private Float productUnitAmount;
173
174         /**
175          * Unit type (for example liter)
176          */
177         @Basic (optional = false)
178         @Column (name = "product_unit_i18n_key", nullable = false)
179         private String productUnitI18nKey;
180
181         /**
182          * Default constructor
183          */
184         public GenericProduct () {
185         }
186
187         /**
188          * Constructor will all required data
189          * <p>
190          * @param productI18nKey      I18n key of product
191          * @param productGrossPrice   Product's gross price
192          * @param productCurrencyCode Currency code for both prices
193          * @param productCategory     Category instance
194          * @param productAvailability Availability (selectable by customer)
195          * @param productUnitAmount   Unit amount
196          * @param productUnitI18nKey  Unit's i18n key
197          * <p>
198          * @throws NullPointerException If a parameter is null
199          * @throws IllegalArgumentException If a parameter is empty (string) or out
200          * of bounds
201          */
202         public GenericProduct (final String productI18nKey, final Float productGrossPrice, final String productCurrencyCode, final Category productCategory, final Boolean productAvailability, final Float productUnitAmount, final String productUnitI18nKey) {
203                 // Call other constructor first
204                 this();
205
206                 // Validate all parameters
207                 if (null == productAvailability) {
208                         // Throw NPE
209                         throw new NullPointerException("productAvailability is null"); //NOI18N
210                 } else if (null == productCategory) {
211                         // Throw it again
212                         throw new NullPointerException("productCategory is null"); //NOI18N
213                 } else if (productCategory.getCategoryId() == null) {
214                         // Throw it again
215                         throw new NullPointerException("productCategory.categoryId is null"); //NOI18N
216                 } else if (productCategory.getCategoryId() < 1) {
217                         // Throw IAE
218                         throw new IllegalArgumentException(MessageFormat.format("productCategory.categoryId={0} is invalid", productCategory.getCategoryId())); //NOI18N
219                 } else if (null == productCurrencyCode) {
220                         // Throw it again
221                         throw new NullPointerException("productCurrencyCode is null"); //NOI18N
222                 } else if (productCurrencyCode.isEmpty()) {
223                         // Throw IAE
224                         throw new IllegalArgumentException("productCurrencyCode is empty"); //NOI18N
225                 } else if (null == productGrossPrice) {
226                         // Throw it again
227                         throw new NullPointerException("productGrossPrice is null"); //NOI18N
228                 } else if (productGrossPrice < 0) {
229                         // Throw IAE
230                         throw new IllegalArgumentException(MessageFormat.format("productGrossPrice={0} is invalid. Do not enter discounts as products.", productGrossPrice)); //NOI18N
231                 } else if (null == productI18nKey) {
232                         // Throw NPE
233                         throw new NullPointerException("productI18nKey is null"); //NOI18N
234                 } else if (productI18nKey.isEmpty()) {
235                         // Throw IAE
236                         throw new IllegalArgumentException("productI18nKey is empty"); //NOI18N
237                 } else if (null == productUnitAmount) {
238                         // Throw it again
239                         throw new NullPointerException("productUnitAmount is null"); //NOI18N
240                 } else if (productUnitAmount < 0) {
241                         // Throw IAE
242                         throw new IllegalArgumentException(MessageFormat.format("productUnitAmount={0} is invalid. Do not enter discounts as products.", productUnitAmount)); //NOI18N
243                 } else if (null == productUnitI18nKey) {
244                         // Throw NPE
245                         throw new NullPointerException("productUnitI18nKey is null"); //NOI18N
246                 } else if (productUnitI18nKey.isEmpty()) {
247                         // Throw IAE
248                         throw new IllegalArgumentException("productUnitI18nKey is empty"); //NOI18N
249                 }
250
251                 // Set all here
252                 this.productI18nKey = productI18nKey;
253                 this.productGrossPrice = productGrossPrice;
254                 this.productCurrencyCode = productCurrencyCode.toUpperCase();
255                 this.productCategory = productCategory;
256                 this.productAvailability = productAvailability;
257                 this.productUnitAmount = productUnitAmount;
258                 this.productUnitI18nKey = productUnitI18nKey;
259         }
260
261         @Override
262         public boolean equals (final Object object) {
263                 if (this == object) {
264                         return true;
265                 } else if (null == object) {
266                         return false;
267                 } else if (this.getClass() != object.getClass()) {
268                         return false;
269                 }
270
271                 final Product product = (Product) object;
272
273                 if (!Objects.equals(this.getProductId(), product.getProductId())) {
274                         return false;
275                 } else if (!Objects.equals(this.getProductI18nKey(), product.getProductI18nKey())) {
276                         return false;
277                 } else if (!Objects.equals(this.getProductAgeGroup(), product.getProductAgeGroup())) {
278                         return false;
279                 } else if (!Objects.equals(this.getProductSize(), product.getProductSize())) {
280                         return false;
281                 }
282
283                 return true;
284         }
285
286         @Override
287         public AgeGroup getProductAgeGroup () {
288                 return this.productAgeGroup;
289         }
290
291         @Override
292         public void setProductAgeGroup (final AgeGroup productAgeGroup) {
293                 this.productAgeGroup = productAgeGroup;
294         }
295
296         @Override
297         public Boolean getProductAvailability () {
298                 return this.productAvailability;
299         }
300
301         @Override
302         public void setProductAvailability (final Boolean productAvailability) {
303                 this.productAvailability = productAvailability;
304         }
305
306         @Override
307         public Category getProductCategory () {
308                 return this.productCategory;
309         }
310
311         @Override
312         public void setProductCategory (final Category productCategory) {
313                 this.productCategory = productCategory;
314         }
315
316         @Override
317         @SuppressWarnings ("ReturnOfDateField")
318         public Date getProductCreated () {
319                 return this.productCreated;
320         }
321
322         @Override
323         @SuppressWarnings ("AssignmentToDateFieldFromParameter")
324         public void setProductCreated (final Date productCreated) {
325                 this.productCreated = productCreated;
326         }
327
328         @Override
329         public String getProductCurrencyCode () {
330                 return this.productCurrencyCode;
331         }
332
333         @Override
334         public void setProductCurrencyCode (final String productCurrencyCode) {
335                 this.productCurrencyCode = productCurrencyCode;
336         }
337
338         @Override
339         public Float getProductGrossPrice () {
340                 return this.productGrossPrice;
341         }
342
343         @Override
344         public void setProductGrossPrice (final Float productGrossPrice) {
345                 this.productGrossPrice = productGrossPrice;
346         }
347
348         @Override
349         public String getProductI18nKey () {
350                 return this.productI18nKey;
351         }
352
353         @Override
354         public void setProductI18nKey (final String productI18nKey) {
355                 this.productI18nKey = productI18nKey;
356         }
357
358         @Override
359         public Long getProductId () {
360                 return this.productId;
361         }
362
363         @Override
364         public void setProductId (final Long productId) {
365                 this.productId = productId;
366         }
367
368         @Override
369         public BasicData getProductManufacturer () {
370                 return this.productManufacturer;
371         }
372
373         @Override
374         public void setProductManufacturer (final BasicData productManufacturer) {
375                 this.productManufacturer = productManufacturer;
376         }
377
378         @Override
379         public Float getProductNetPrice () {
380                 return this.productNetPrice;
381         }
382
383         @Override
384         public void setProductNetPrice (final Float productNetPrice) {
385                 this.productNetPrice = productNetPrice;
386         }
387
388         @Override
389         public Long getProductNumber () {
390                 return this.productNumber;
391         }
392
393         @Override
394         public void setProductNumber (final Long productNumber) {
395                 this.productNumber = productNumber;
396         }
397
398         @Override
399         public String getProductSize () {
400                 return this.productSize;
401         }
402
403         @Override
404         public void setProductSize (final String productSize) {
405                 this.productSize = productSize;
406         }
407
408         @Override
409         public Float getProductTaxRate () {
410                 return this.productTaxRate;
411         }
412
413         @Override
414         public void setProductTaxRate (final Float productTaxRate) {
415                 this.productTaxRate = productTaxRate;
416         }
417
418         @Override
419         public Float getProductUnitAmount () {
420                 return this.productUnitAmount;
421         }
422
423         @Override
424         public void setProductUnitAmount (final Float productUnitAmount) {
425                 this.productUnitAmount = productUnitAmount;
426         }
427
428         @Override
429         public String getProductUnitI18nKey () {
430                 return this.productUnitI18nKey;
431         }
432
433         @Override
434         public void setProductUnitI18nKey (final String productUnitI18nKey) {
435                 this.productUnitI18nKey = productUnitI18nKey;
436         }
437
438         @Override
439         public int hashCode () {
440                 int hash = 7;
441
442                 hash = 23 * hash + Objects.hashCode(this.getProductId());
443                 hash = 23 * hash + Objects.hashCode(this.getProductI18nKey());
444                 hash = 23 * hash + Objects.hashCode(this.getProductAgeGroup());
445                 hash = 23 * hash + Objects.hashCode(this.getProductSize());
446
447                 return hash;
448         }
449
450 }