OpenConcerto

Dépôt officiel du code source de l'ERP OpenConcerto
sonarqube

svn://code.openconcerto.org/openconcerto

Rev

Rev 180 | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
83 ilm 1
/*
2
 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3
 *
185 ilm 4
 * Copyright 2011-2019 OpenConcerto, by ILM Informatique. All rights reserved.
83 ilm 5
 *
6
 * The contents of this file are subject to the terms of the GNU General Public License Version 3
7
 * only ("GPL"). You may not use this file except in compliance with the License. You can obtain a
8
 * copy of the License at http://www.gnu.org/licenses/gpl-3.0.html See the License for the specific
9
 * language governing permissions and limitations under the License.
10
 *
11
 * When distributing the software, include this License Header Notice in each file.
12
 */
13
 
14
 package org.openconcerto.erp.core.supplychain.stock.element;
15
 
142 ilm 16
import org.openconcerto.erp.preferences.GestionArticleGlobalPreferencePanel;
90 ilm 17
import org.openconcerto.sql.model.SQLInjector;
18
import org.openconcerto.sql.model.SQLRow;
83 ilm 19
import org.openconcerto.sql.model.SQLRowAccessor;
90 ilm 20
import org.openconcerto.sql.model.SQLRowValues;
83 ilm 21
import org.openconcerto.sql.model.SQLTable;
22
import org.openconcerto.sql.model.Where;
93 ilm 23
import org.openconcerto.sql.preferences.SQLPreferences;
83 ilm 24
import org.openconcerto.sql.request.UpdateBuilder;
90 ilm 25
import org.openconcerto.utils.ListMap;
83 ilm 26
 
90 ilm 27
import java.math.BigDecimal;
83 ilm 28
import java.util.ArrayList;
29
import java.util.List;
30
 
93 ilm 31
/**
32
 * Représente un article avec son stock
33
 *
34
 * @author Utilisateur
35
 *
36
 */
83 ilm 37
public class StockItem {
38
 
93 ilm 39
    public enum TypeStockMouvement {
132 ilm 40
        REEL, THEORIQUE, REEL_THEORIQUE, RETOUR
83 ilm 41
    };
42
 
43
    private double realQty, virtualQty, receiptQty, deliverQty;
156 ilm 44
    public SQLRowAccessor article, stock;
83 ilm 45
 
46
    List<StockItemComponent> components = new ArrayList<StockItemComponent>();
47
 
156 ilm 48
    public StockItem(SQLRowAccessor article, SQLRowAccessor stock) {
83 ilm 49
        this.article = article;
156 ilm 50
        this.stock = stock;
51
        this.realQty = stock.getFloat("QTE_REEL");
52
        this.virtualQty = stock.getFloat("QTE_TH");
53
        this.receiptQty = stock.getFloat("QTE_RECEPT_ATTENTE");
54
        this.deliverQty = stock.getFloat("QTE_LIV_ATTENTE");
83 ilm 55
    }
56
 
93 ilm 57
    public void updateQty(double qty, TypeStockMouvement t) {
83 ilm 58
        updateQty(qty, t, false);
59
    }
60
 
156 ilm 61
    public void setDeliverQty(double deliverQty) {
62
        this.deliverQty = deliverQty;
63
    }
64
 
65
    public void setRealQty(double realQty) {
66
        this.realQty = realQty;
67
    }
68
 
69
    public void setReceiptQty(double receiptQty) {
70
        this.receiptQty = receiptQty;
71
    }
72
 
73
    public void setVirtualQty(double virtualQty) {
74
        this.virtualQty = virtualQty;
75
    }
76
 
83 ilm 77
    public SQLRowAccessor getArticle() {
78
        return article;
79
    };
80
 
81
    public void addItemComponent(StockItemComponent item) {
82
        this.components.add(item);
83
    };
84
 
156 ilm 85
    public boolean updateQtyFromChildren() throws IllegalArgumentException {
83 ilm 86
        if (components.size() == 0) {
156 ilm 87
            if (this.article.isUndefined()) {
88
                return false;
89
            }
90
            String code = "";
91
            if (this.article != null && this.article.getFields().contains("CODE") && this.article.getString("CODE") != null) {
92
                code = this.article.getString("CODE");
93
            }
94
            System.err.println("Impossible de mettre à jour le stock, l'articel n'est pas une nomenclature " + code);
95
            return false;
96
 
83 ilm 97
        }
98
        StockItemComponent comp = components.get(0);
180 ilm 99
        double real = comp.getItem().getRealQty() == 0 ? 0 : Math.floor(comp.getItem().getRealQty() / (comp.getQty() * comp.getQtyUnit().doubleValue()));
100
        double virtual = comp.getItem().getVirtualQty() == 0 ? 0 : Math.floor(comp.getItem().getVirtualQty() / (comp.getQty() * comp.getQtyUnit().doubleValue()));
83 ilm 101
        for (StockItemComponent stockItemComponent : components) {
132 ilm 102
            real = Math.min(real, stockItemComponent.getItem().getRealQty() == 0 ? 0
180 ilm 103
                    : Math.floor(stockItemComponent.getItem().getRealQty() / (stockItemComponent.getQty() * stockItemComponent.getQtyUnit().doubleValue())));
132 ilm 104
            virtual = Math.min(virtual, stockItemComponent.getItem().getVirtualQty() == 0 ? 0
180 ilm 105
                    : Math.floor(stockItemComponent.getItem().getVirtualQty() / (stockItemComponent.getQty() * stockItemComponent.getQtyUnit().doubleValue())));
83 ilm 106
 
107
        }
94 ilm 108
        // La quantité du kit ne peut être négative
109
        this.realQty = Math.max(0, real);
110
        this.virtualQty = Math.max(0, virtual);
156 ilm 111
        return true;
83 ilm 112
    }
113
 
90 ilm 114
    public void fillCommandeFournisseur(ListMap<SQLRow, SQLRowValues> cmd) {
156 ilm 115
        // TODO Gestion Stock Min par depot
93 ilm 116
        SQLPreferences prefs = new SQLPreferences(article.getTable().getDBRoot());
142 ilm 117
        boolean gestionStockMin = prefs.getBoolean(GestionArticleGlobalPreferencePanel.WARNING_STOCK_MIN, true);
156 ilm 118
        if (gestionStockMin && stock.getObject("QTE_MIN") != null && getRealQty() < stock.getFloat("QTE_MIN")) {
90 ilm 119
            // final float qteShow = qteNvlle;
120
            SQLInjector inj = SQLInjector.getInjector(article.getTable(), article.getTable().getTable("COMMANDE_ELEMENT"));
121
            final SQLRow asRow = article.asRow();
122
            SQLRowValues rowValsElt = new SQLRowValues(inj.createRowValuesFrom(asRow));
123
            rowValsElt.put("ID_STYLE", 2);
124
            final SQLRowAccessor unite = article.getForeign("ID_UNITE_VENTE");
156 ilm 125
            final double qteElt = stock.getFloat("QTE_MIN") - getRealQty();
90 ilm 126
            if (unite.isUndefined() || unite.getBoolean("A_LA_PIECE")) {
127
                rowValsElt.put("QTE", Math.round(qteElt));
128
                rowValsElt.put("QTE_UNITAIRE", BigDecimal.ONE);
129
            } else {
130
                rowValsElt.put("QTE", 1);
131
                rowValsElt.put("QTE_UNITAIRE", new BigDecimal(qteElt));
132
            }
133
            rowValsElt.put("ID_TAXE", rowValsElt.getObject("ID_TAXE"));
134
            rowValsElt.put("T_POIDS", rowValsElt.getLong("POIDS") * qteElt);
135
            rowValsElt.put("T_PA_HT", rowValsElt.getLong("PA_HT") * qteElt);
136
            rowValsElt.put("T_PA_TTC", rowValsElt.getLong("T_PA_HT") * (rowValsElt.getForeign("ID_TAXE").getFloat("TAUX") / 100.0 + 1.0));
137
 
138
            cmd.add(asRow.getForeignRow("ID_FOURNISSEUR"), rowValsElt);
139
        }
140
 
141
    }
142
 
83 ilm 143
    /**
144
     * Mise à jour des quantités de stocks. Stock Reel : inc/dec QTE_REEL, inc/dec
145
     * QTE_LIV_ATTENTE/inc/dec QTE_RECEPT_ATTENTE Stock Th : inc/dec QTE_TH, inc/dec
146
     * QTE_LIV_ATTENTE/inc/dec QTE_RECEPT_ATTENTE
147
     *
148
     * @param qty quantité à ajouter ou à soustraire
149
     * @param t Type de stock à mettre à jour (réel ou virtuel)
150
     * @param archive annulation du stock
151
     */
93 ilm 152
    public void updateQty(double qty, TypeStockMouvement t, boolean archive) {
83 ilm 153
 
132 ilm 154
        if (t == TypeStockMouvement.REEL || t == TypeStockMouvement.REEL_THEORIQUE || t == TypeStockMouvement.RETOUR) {
83 ilm 155
            final double qteNvlle;
156
            final double qteOrigin = this.realQty;
157
            if (archive) {
158
                qteNvlle = qteOrigin - qty;
132 ilm 159
                if (t != TypeStockMouvement.RETOUR) {
160
                    // Réception
161
                    if (qty > 0) {
162
                        this.receiptQty += qty;
163
                    } else {
164
                        // Livraison
165
                        this.deliverQty -= qty;
166
                    }
83 ilm 167
                }
168
            } else {
169
                qteNvlle = qteOrigin + qty;
132 ilm 170
                if (t != TypeStockMouvement.RETOUR) {
171
                    // Réception
172
                    if (qty > 0) {
173
                        this.receiptQty -= qty;
174
                    } else {
175
                        // Livraison
176
                        this.deliverQty += qty;
177
                    }
83 ilm 178
                }
179
            }
180
 
181
            this.realQty = qteNvlle;
182
 
93 ilm 183
        }
184
 
132 ilm 185
        if (t == TypeStockMouvement.THEORIQUE || t == TypeStockMouvement.REEL_THEORIQUE || t == TypeStockMouvement.RETOUR) {
93 ilm 186
 
90 ilm 187
            // THEORIQUE
83 ilm 188
            final double qteNvlle;
189
            final double qteOrigin = this.virtualQty;
190
            if (archive) {
191
                qteNvlle = qteOrigin - qty;
132 ilm 192
                if (t != TypeStockMouvement.RETOUR) {
193
                    // Réception
194
                    if (qty > 0) {
195
                        this.receiptQty -= qty;
196
                    } else {
197
                        // Livraison
198
                        this.deliverQty += qty;
199
                    }
83 ilm 200
                }
201
            } else {
202
                qteNvlle = qteOrigin + qty;
132 ilm 203
                if (t != TypeStockMouvement.RETOUR) {
204
                    // Réception
205
                    if (qty > 0) {
206
                        this.receiptQty += qty;
207
                    } else {
208
                        // Livraison
209
                        this.deliverQty -= qty;
210
                    }
83 ilm 211
                }
212
            }
213
 
214
            this.virtualQty = qteNvlle;
215
        }
216
    }
217
 
218
    public double getDeliverQty() {
219
        return deliverQty;
220
    }
221
 
222
    public double getRealQty() {
223
        return realQty;
224
    }
225
 
226
    public double getReceiptQty() {
227
        return receiptQty;
228
    }
229
 
230
    public double getVirtualQty() {
231
        return virtualQty;
232
    }
233
 
234
    public boolean isStockInit() {
156 ilm 235
        return this.stock != null && !this.stock.isUndefined();
83 ilm 236
    }
237
 
185 ilm 238
    public int getStockID() {
239
        return this.stock.getID();
240
    }
241
 
90 ilm 242
    public void clearStockValues() {
243
        this.realQty = 0;
244
        this.deliverQty = 0;
245
        this.receiptQty = 0;
246
        this.virtualQty = 0;
247
    }
248
 
83 ilm 249
    public String getUpdateRequest() {
156 ilm 250
        final SQLTable stockTable = this.stock.getTable();
83 ilm 251
        UpdateBuilder update = new UpdateBuilder(stockTable);
156 ilm 252
        update.setWhere(new Where(stockTable.getKey(), "=", this.stock.getID()));
83 ilm 253
        update.setObject("QTE_REEL", getRealQty());
254
        update.setObject("QTE_TH", getVirtualQty());
255
        update.setObject("QTE_LIV_ATTENTE", getDeliverQty());
256
        update.setObject("QTE_RECEPT_ATTENTE", getReceiptQty());
257
        return update.asString();
258
    }
259
 
260
}