001// --------------------------------------------------------------------------------
002// Copyright 2002-2025 Echo Three, LLC
003//
004// Licensed under the Apache License, Version 2.0 (the "License");
005// you may not use this file except in compliance with the License.
006// You may obtain a copy of the License at
007//
008//     http://www.apache.org/licenses/LICENSE-2.0
009//
010// Unless required by applicable law or agreed to in writing, software
011// distributed under the License is distributed on an "AS IS" BASIS,
012// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
013// See the License for the specific language governing permissions and
014// limitations under the License.
015// --------------------------------------------------------------------------------
016
017package com.echothree.control.user.warehouse.server.command;
018
019import com.echothree.control.user.warehouse.common.edit.WarehouseEdit;
020import com.echothree.control.user.warehouse.common.edit.WarehouseEditFactory;
021import com.echothree.control.user.warehouse.common.form.EditWarehouseForm;
022import com.echothree.control.user.warehouse.common.result.EditWarehouseResult;
023import com.echothree.control.user.warehouse.common.result.WarehouseResultFactory;
024import com.echothree.control.user.warehouse.common.spec.WarehouseUniversalSpec;
025import com.echothree.model.control.accounting.server.control.AccountingControl;
026import com.echothree.model.control.party.common.PartyTypes;
027import com.echothree.model.control.party.server.control.PartyControl;
028import com.echothree.model.control.printer.common.PrinterConstants;
029import com.echothree.model.control.printer.server.control.PrinterControl;
030import com.echothree.model.control.security.common.SecurityRoleGroups;
031import com.echothree.model.control.security.common.SecurityRoles;
032import com.echothree.model.control.warehouse.server.control.WarehouseControl;
033import com.echothree.model.control.warehouse.server.logic.WarehouseLogic;
034import com.echothree.model.control.warehouse.server.logic.WarehouseTypeLogic;
035import com.echothree.model.data.accounting.server.entity.Currency;
036import com.echothree.model.data.party.server.entity.DateTimeFormat;
037import com.echothree.model.data.party.server.entity.Language;
038import com.echothree.model.data.party.server.entity.Party;
039import com.echothree.model.data.party.server.entity.TimeZone;
040import com.echothree.model.data.printer.server.entity.PrinterGroup;
041import com.echothree.model.data.user.common.pk.UserVisitPK;
042import com.echothree.model.data.warehouse.server.entity.WarehouseType;
043import com.echothree.util.common.message.ExecutionErrors;
044import com.echothree.util.common.validation.FieldDefinition;
045import com.echothree.util.common.validation.FieldType;
046import com.echothree.util.server.control.BaseAbstractEditCommand;
047import com.echothree.util.server.control.CommandSecurityDefinition;
048import com.echothree.util.server.control.PartyTypeDefinition;
049import com.echothree.util.server.control.SecurityRoleDefinition;
050import com.echothree.util.server.persistence.Session;
051import java.util.List;
052import javax.enterprise.context.RequestScoped;
053
054@RequestScoped
055public class EditWarehouseCommand
056        extends BaseAbstractEditCommand<WarehouseUniversalSpec, WarehouseEdit, EditWarehouseResult, Party, Party> {
057
058    private final static CommandSecurityDefinition COMMAND_SECURITY_DEFINITION;
059    private final static List<FieldDefinition> SPEC_FIELD_DEFINITIONS;
060    private final static List<FieldDefinition> EDIT_FIELD_DEFINITIONS;
061    
062    static {
063        COMMAND_SECURITY_DEFINITION = new CommandSecurityDefinition(List.of(
064                new PartyTypeDefinition(PartyTypes.UTILITY.name(), null),
065                new PartyTypeDefinition(PartyTypes.EMPLOYEE.name(), List.of(
066                        new SecurityRoleDefinition(SecurityRoleGroups.Warehouse.name(), SecurityRoles.Edit.name())
067                ))
068        ));
069
070        SPEC_FIELD_DEFINITIONS = List.of(
071                new FieldDefinition("WarehouseName", FieldType.ENTITY_NAME, false, null, null),
072                new FieldDefinition("PartyName", FieldType.ENTITY_NAME, false, null, null),
073                new FieldDefinition("EntityRef", FieldType.ENTITY_REF, false, null, null),
074                new FieldDefinition("Uuid", FieldType.UUID, false, null, null)
075        );
076        
077        EDIT_FIELD_DEFINITIONS = List.of(
078                new FieldDefinition("WarehouseName", FieldType.ENTITY_NAME, true, null, null),
079                new FieldDefinition("WarehouseTypeName", FieldType.ENTITY_NAME, true, null, null),
080                new FieldDefinition("Name", FieldType.STRING, false, 1L, 60L),
081                new FieldDefinition("PreferredLanguageIsoName", FieldType.ENTITY_NAME, false, null, null),
082                new FieldDefinition("PreferredCurrencyIsoName", FieldType.ENTITY_NAME, false, null, null),
083                new FieldDefinition("PreferredJavaTimeZoneName", FieldType.TIME_ZONE_NAME, false, null, null),
084                new FieldDefinition("PreferredDateTimeFormatName", FieldType.ENTITY_NAME, false, null, null),
085                new FieldDefinition("IsDefault", FieldType.BOOLEAN, true, null, null),
086                new FieldDefinition("SortOrder", FieldType.SIGNED_INTEGER, true, null, null),
087                new FieldDefinition("InventoryMovePrinterGroupName", FieldType.ENTITY_NAME, true, null, null),
088                new FieldDefinition("PicklistPrinterGroupName", FieldType.ENTITY_NAME, true, null, null),
089                new FieldDefinition("PackingListPrinterGroupName", FieldType.ENTITY_NAME, true, null, null),
090                new FieldDefinition("ShippingManifestPrinterGroupName", FieldType.ENTITY_NAME, true, null, null)
091        );
092    }
093    
094    /** Creates a new instance of EditWarehouseCommand */
095    public EditWarehouseCommand() {
096        super(COMMAND_SECURITY_DEFINITION, SPEC_FIELD_DEFINITIONS, EDIT_FIELD_DEFINITIONS);
097    }
098
099    @Override
100    public EditWarehouseResult getResult() {
101        return WarehouseResultFactory.getEditWarehouseResult();
102    }
103
104    @Override
105    public WarehouseEdit getEdit() {
106        return WarehouseEditFactory.getWarehouseEdit();
107    }
108
109    @Override
110    public Party getEntity(EditWarehouseResult result) {
111        var warehouse = WarehouseLogic.getInstance().getWarehouseByUniversalSpec(this, spec, false, editModeToEntityPermission(editMode));
112
113        return warehouse == null ? null : warehouse.getParty();
114    }
115
116    @Override
117    public Party getLockEntity(Party party) {
118        return party;
119    }
120
121    @Override
122    public void fillInResult(EditWarehouseResult result, Party party) {
123        var warehouseControl = Session.getModelController(WarehouseControl.class);
124
125        result.setWarehouse(warehouseControl.getWarehouseTransfer(getUserVisit(), party));
126    }
127
128    @Override
129    public void doLock(WarehouseEdit edit, Party party) {
130        var partyControl = Session.getModelController(PartyControl.class);
131        var printerControl = Session.getModelController(PrinterControl.class);
132        var warehouseControl = Session.getModelController(WarehouseControl.class);
133        var warehouse = warehouseControl.getWarehouse(party);
134        var partyDetail = party.getLastDetail();
135        var partyGroup = partyControl.getPartyGroup(party);
136        var preferredLanguage = partyDetail.getPreferredLanguage();
137        var preferredCurrency = partyDetail.getPreferredCurrency();
138        var preferredTimeZone = partyDetail.getPreferredTimeZone();
139        var dateTimeFormat = partyDetail.getPreferredDateTimeFormat();
140
141        edit.setWarehouseName(warehouse.getWarehouseName());
142        edit.setWarehouseTypeName(warehouse.getWarehouseType().getLastDetail().getWarehouseTypeName());
143        edit.setName(partyGroup == null? null: partyGroup.getName());
144        edit.setPreferredLanguageIsoName(preferredLanguage == null ? null : preferredLanguage.getLanguageIsoName());
145        edit.setPreferredCurrencyIsoName(preferredCurrency == null ? null : preferredCurrency.getCurrencyIsoName());
146        edit.setPreferredJavaTimeZoneName(preferredTimeZone == null ? null : preferredTimeZone.getLastDetail().getJavaTimeZoneName());
147        edit.setPreferredDateTimeFormatName(dateTimeFormat == null ? null : dateTimeFormat.getLastDetail().getDateTimeFormatName());
148        edit.setIsDefault(warehouse.getIsDefault().toString());
149        edit.setSortOrder(warehouse.getSortOrder().toString());
150        edit.setInventoryMovePrinterGroupName(printerControl.getPartyPrinterGroupUseUsingNames(party, PrinterConstants.PrinterGroupUseType_WAREHOUSE_INVENTORY_MOVE).getPrinterGroup().getLastDetail().getPrinterGroupName());
151        edit.setPicklistPrinterGroupName(printerControl.getPartyPrinterGroupUseUsingNames(party, PrinterConstants.PrinterGroupUseType_WAREHOUSE_PACKING_LIST).getPrinterGroup().getLastDetail().getPrinterGroupName());
152        edit.setPackingListPrinterGroupName(printerControl.getPartyPrinterGroupUseUsingNames(party, PrinterConstants.PrinterGroupUseType_WAREHOUSE_PICKLIST).getPrinterGroup().getLastDetail().getPrinterGroupName());
153        edit.setShippingManifestPrinterGroupName(printerControl.getPartyPrinterGroupUseUsingNames(party, PrinterConstants.PrinterGroupUseType_WAREHOUSE_SHIPPING_MANIFEST).getPrinterGroup().getLastDetail().getPrinterGroupName());
154    }
155
156    WarehouseType warehouseType;
157    PrinterGroup inventoryMovePrinterGroup;
158    PrinterGroup picklistPrinterGroup;
159    PrinterGroup packingListPrinterGroup;
160    PrinterGroup shippingManifestPrinterGroup;
161    Language preferredLanguage;
162    TimeZone preferredTimeZone;
163    DateTimeFormat preferredDateTimeFormat;
164    Currency preferredCurrency;
165
166    @Override
167    public void canUpdate(Party party) {
168        var partyControl = Session.getModelController(PartyControl.class);
169        var printerControl = Session.getModelController(PrinterControl.class);
170        var warehouseControl = Session.getModelController(WarehouseControl.class);
171        var warehouse = warehouseControl.getWarehouseForUpdate(party);
172        var warehouseName = edit.getWarehouseName();
173        var duplicateWarehouse = warehouseControl.getWarehouseByName(warehouseName);
174
175        warehouseType = WarehouseTypeLogic.getInstance().getWarehouseTypeByName(this, edit.getWarehouseTypeName());
176
177        if(duplicateWarehouse == null || duplicateWarehouse.getPrimaryKey().equals(warehouse.getPrimaryKey())) {
178            var inventoryMovePrinterGroupName = edit.getInventoryMovePrinterGroupName();
179
180            inventoryMovePrinterGroup = printerControl.getPrinterGroupByName(inventoryMovePrinterGroupName);
181
182            if(inventoryMovePrinterGroup != null) {
183                var picklistPrinterGroupName = edit.getPicklistPrinterGroupName();
184
185                picklistPrinterGroup = printerControl.getPrinterGroupByName(picklistPrinterGroupName);
186
187                if(picklistPrinterGroup != null) {
188                    var packingListPrinterGroupName = edit.getPackingListPrinterGroupName();
189
190                    packingListPrinterGroup = printerControl.getPrinterGroupByName(packingListPrinterGroupName);
191
192                    if(packingListPrinterGroup != null) {
193                        var shippingManifestPrinterGroupName = edit.getShippingManifestPrinterGroupName();
194
195                        shippingManifestPrinterGroup = printerControl.getPrinterGroupByName(shippingManifestPrinterGroupName);
196
197                        if(shippingManifestPrinterGroup != null) {
198                            var preferredLanguageIsoName = edit.getPreferredLanguageIsoName();
199
200                            preferredLanguage = preferredLanguageIsoName == null ? null : partyControl.getLanguageByIsoName(preferredLanguageIsoName);
201
202                            if(preferredLanguageIsoName == null || (preferredLanguage != null)) {
203                                var preferredJavaTimeZoneName = edit.getPreferredJavaTimeZoneName();
204
205                                preferredTimeZone = preferredJavaTimeZoneName == null ? null : partyControl.getTimeZoneByJavaName(preferredJavaTimeZoneName);
206
207                                if(preferredJavaTimeZoneName == null || (preferredTimeZone != null)) {
208                                    var preferredDateTimeFormatName = edit.getPreferredDateTimeFormatName();
209
210                                    preferredDateTimeFormat = preferredDateTimeFormatName == null ? null : partyControl.getDateTimeFormatByName(preferredDateTimeFormatName);
211
212                                    if(preferredDateTimeFormatName == null || (preferredDateTimeFormat != null)) {
213                                        var preferredCurrencyIsoName = edit.getPreferredCurrencyIsoName();
214
215                                        if(preferredCurrencyIsoName == null) {
216                                            preferredCurrency = null;
217                                        } else {
218                                            var accountingControl = Session.getModelController(AccountingControl.class);
219
220                                            preferredCurrency = accountingControl.getCurrencyByIsoName(preferredCurrencyIsoName);
221                                        }
222
223                                        if(preferredCurrencyIsoName != null && (preferredCurrency == null)) {
224                                            addExecutionError(ExecutionErrors.UnknownCurrencyIsoName.name(), preferredCurrencyIsoName);
225                                        }
226                                    } else {
227                                        addExecutionError(ExecutionErrors.UnknownDateTimeFormatName.name(), preferredDateTimeFormatName);
228                                    }
229                                } else {
230                                    addExecutionError(ExecutionErrors.UnknownJavaTimeZoneName.name(), preferredJavaTimeZoneName);
231                                }
232                            } else {
233                                addExecutionError(ExecutionErrors.UnknownLanguageIsoName.name(), preferredLanguageIsoName);
234                            }
235                        } else {
236                            addExecutionError(ExecutionErrors.UnknownShippingManifestPrinterGroupName.name(), shippingManifestPrinterGroupName);
237                        }
238                    } else {
239                        addExecutionError(ExecutionErrors.UnknownPackingListPrinterGroupName.name(), packingListPrinterGroupName);
240                    }
241                } else {
242                    addExecutionError(ExecutionErrors.UnknownPicklistPrinterGroupName.name(), picklistPrinterGroupName);
243                }
244            } else {
245                addExecutionError(ExecutionErrors.UnknownInventoryMovePrinterGroupName.name(), inventoryMovePrinterGroupName);
246            }
247        } else {
248            addExecutionError(ExecutionErrors.DuplicateWarehouseName.name(), warehouseName);
249        }
250    }
251
252    @Override
253    public void doUpdate(Party party) {
254        var partyControl = Session.getModelController(PartyControl.class);
255        var printerControl = Session.getModelController(PrinterControl.class);
256        var warehouseControl = Session.getModelController(WarehouseControl.class);
257        var warehouse = warehouseControl.getWarehouseForUpdate(party);
258        var warehouseValue = warehouseControl.getWarehouseValue(warehouse);
259        var partyDetailValue = partyControl.getPartyDetailValueForUpdate(party);
260        var partyGroup = partyControl.getPartyGroupForUpdate(party);
261        var name = edit.getName();
262        var updatedBy = getPartyPK();
263
264        warehouseValue.setWarehouseName(edit.getWarehouseName());
265        warehouseValue.setWarehouseTypePK(warehouseType.getPrimaryKey());
266        warehouseValue.setIsDefault(Boolean.valueOf(edit.getIsDefault()));
267        warehouseValue.setSortOrder(Integer.valueOf(edit.getSortOrder()));
268
269        partyDetailValue.setPreferredLanguagePK(preferredLanguage == null ? null : preferredLanguage.getPrimaryKey());
270        partyDetailValue.setPreferredTimeZonePK(preferredTimeZone == null ? null : preferredTimeZone.getPrimaryKey());
271        partyDetailValue.setPreferredDateTimeFormatPK(preferredDateTimeFormat == null ? null : preferredDateTimeFormat.getPrimaryKey());
272        partyDetailValue.setPreferredCurrencyPK(preferredCurrency == null ? null : preferredCurrency.getPrimaryKey());
273
274        var printerGroupUseType = printerControl.getPrinterGroupUseTypeByName(PrinterConstants.PrinterGroupUseType_WAREHOUSE_INVENTORY_MOVE);
275        var partyPrinterGroupUseValue = printerControl.getPartyPrinterGroupUseValueForUpdate(party, printerGroupUseType);
276        partyPrinterGroupUseValue.setPrinterGroupPK(inventoryMovePrinterGroup.getPrimaryKey());
277        printerControl.updatePartyPrinterGroupUseFromValue(partyPrinterGroupUseValue, updatedBy);
278
279        printerGroupUseType = printerControl.getPrinterGroupUseTypeByName(PrinterConstants.PrinterGroupUseType_WAREHOUSE_PACKING_LIST);
280        partyPrinterGroupUseValue = printerControl.getPartyPrinterGroupUseValueForUpdate(party, printerGroupUseType);
281        partyPrinterGroupUseValue.setPrinterGroupPK(packingListPrinterGroup.getPrimaryKey());
282        printerControl.updatePartyPrinterGroupUseFromValue(partyPrinterGroupUseValue, updatedBy);
283
284        printerGroupUseType = printerControl.getPrinterGroupUseTypeByName(PrinterConstants.PrinterGroupUseType_WAREHOUSE_PICKLIST);
285        partyPrinterGroupUseValue = printerControl.getPartyPrinterGroupUseValueForUpdate(party, printerGroupUseType);
286        partyPrinterGroupUseValue.setPrinterGroupPK(picklistPrinterGroup.getPrimaryKey());
287        printerControl.updatePartyPrinterGroupUseFromValue(partyPrinterGroupUseValue, updatedBy);
288
289        printerGroupUseType = printerControl.getPrinterGroupUseTypeByName(PrinterConstants.PrinterGroupUseType_WAREHOUSE_SHIPPING_MANIFEST);
290        partyPrinterGroupUseValue = printerControl.getPartyPrinterGroupUseValueForUpdate(party, printerGroupUseType);
291        partyPrinterGroupUseValue.setPrinterGroupPK(shippingManifestPrinterGroup.getPrimaryKey());
292        printerControl.updatePartyPrinterGroupUseFromValue(partyPrinterGroupUseValue, updatedBy);
293
294        if(name != null) {
295            if(partyGroup != null) {
296                var partyGroupValue = partyControl.getPartyGroupValue(partyGroup);
297
298                partyGroupValue.setName(name);
299                partyControl.updatePartyGroupFromValue(partyGroupValue, updatedBy);
300            } else {
301                partyControl.createPartyGroup(party, name, updatedBy);
302            }
303        } else {
304            if(partyGroup != null) {
305                partyControl.deletePartyGroup(partyGroup, updatedBy);
306            }
307        }
308
309        WarehouseLogic.getInstance().updateWarehouseFromValue(this, warehouseValue, updatedBy);
310        partyControl.updatePartyFromValue(partyDetailValue, updatedBy);
311    }
312
313}