Subversion Repositories SmartDukaan

Rev

Rev 25640 | Rev 25647 | Go to most recent revision | Details | Compare with Previous | Last modification | View Log | RSS feed

Rev Author Line No. Line
23365 ashik.ali 1
package com.spice.profitmandi.service.order;
22859 ashik.ali 2
 
3
import java.time.LocalDate;
23202 ashik.ali 4
import java.time.LocalDateTime;
24271 amit.gupta 5
import java.time.LocalTime;
22859 ashik.ali 6
import java.util.ArrayList;
23655 amit.gupta 7
import java.util.Arrays;
22859 ashik.ali 8
import java.util.HashMap;
9
import java.util.HashSet;
10
import java.util.Iterator;
11
import java.util.List;
12
import java.util.Map;
13
import java.util.Set;
22955 ashik.ali 14
import java.util.function.Function;
15
import java.util.stream.Collectors;
22859 ashik.ali 16
 
23638 amit.gupta 17
import org.apache.logging.log4j.LogManager;
18
import org.apache.logging.log4j.Logger;
22859 ashik.ali 19
import org.json.JSONObject;
20
import org.springframework.beans.factory.annotation.Autowired;
23781 ashik.ali 21
import org.springframework.beans.factory.annotation.Qualifier;
22859 ashik.ali 22
import org.springframework.stereotype.Component;
23
 
24264 amit.gupta 24
import com.spice.profitmandi.common.enumuration.ItemType;
23202 ashik.ali 25
import com.spice.profitmandi.common.enumuration.SearchType;
22859 ashik.ali 26
import com.spice.profitmandi.common.exception.ProfitMandiBusinessException;
23638 amit.gupta 27
import com.spice.profitmandi.common.model.BadReturnRequest;
22859 ashik.ali 28
import com.spice.profitmandi.common.model.CartFofo;
29
import com.spice.profitmandi.common.model.CreateOrderRequest;
23638 amit.gupta 30
import com.spice.profitmandi.common.model.CreditNotePdfModel;
22859 ashik.ali 31
import com.spice.profitmandi.common.model.CustomAddress;
32
import com.spice.profitmandi.common.model.CustomCustomer;
33
import com.spice.profitmandi.common.model.CustomFofoOrderItem;
34
import com.spice.profitmandi.common.model.CustomInsurancePolicy;
35
import com.spice.profitmandi.common.model.CustomOrderItem;
36
import com.spice.profitmandi.common.model.CustomPaymentOption;
37
import com.spice.profitmandi.common.model.CustomRetailer;
23638 amit.gupta 38
import com.spice.profitmandi.common.model.FoiBadReturnRequest;
22859 ashik.ali 39
import com.spice.profitmandi.common.model.GadgetCopsInsuranceModel;
23172 ashik.ali 40
import com.spice.profitmandi.common.model.GstRate;
24440 amit.gupta 41
import com.spice.profitmandi.common.model.InsuranceModel;
22859 ashik.ali 42
import com.spice.profitmandi.common.model.ItemIdQuantityAvailability;
43
import com.spice.profitmandi.common.model.PdfModel;
44
import com.spice.profitmandi.common.model.PriceModel;
45
import com.spice.profitmandi.common.model.ProfitMandiConstants;
46
import com.spice.profitmandi.common.model.Quantity;
47
import com.spice.profitmandi.common.model.SerialNumberDetail;
24440 amit.gupta 48
import com.spice.profitmandi.common.model.WiseAppInsuaranceModel;
23650 amit.gupta 49
import com.spice.profitmandi.common.util.FormattingUtils;
22859 ashik.ali 50
import com.spice.profitmandi.common.util.InsuranceUtils;
51
import com.spice.profitmandi.common.util.StringUtils;
23172 ashik.ali 52
import com.spice.profitmandi.common.util.Utils;
22859 ashik.ali 53
import com.spice.profitmandi.dao.entity.catalog.Item;
25103 amit.gupta 54
import com.spice.profitmandi.dao.entity.catalog.TagListing;
22859 ashik.ali 55
import com.spice.profitmandi.dao.entity.dtr.InsurancePolicy;
23546 ashik.ali 56
import com.spice.profitmandi.dao.entity.dtr.PaymentOptionTransaction;
22859 ashik.ali 57
import com.spice.profitmandi.dao.entity.dtr.PolicyNumberGenerationSequence;
58
import com.spice.profitmandi.dao.entity.dtr.Retailer;
59
import com.spice.profitmandi.dao.entity.dtr.User;
60
import com.spice.profitmandi.dao.entity.fofo.CurrentInventorySnapshot;
61
import com.spice.profitmandi.dao.entity.fofo.Customer;
62
import com.spice.profitmandi.dao.entity.fofo.CustomerAddress;
23650 amit.gupta 63
import com.spice.profitmandi.dao.entity.fofo.CustomerCreditNote;
64
import com.spice.profitmandi.dao.entity.fofo.CustomerReturnItem;
22859 ashik.ali 65
import com.spice.profitmandi.dao.entity.fofo.FofoLineItem;
66
import com.spice.profitmandi.dao.entity.fofo.FofoOrder;
67
import com.spice.profitmandi.dao.entity.fofo.FofoOrderItem;
23202 ashik.ali 68
import com.spice.profitmandi.dao.entity.fofo.FofoStore;
25640 tejbeer 69
import com.spice.profitmandi.dao.entity.fofo.HygieneData;
22859 ashik.ali 70
import com.spice.profitmandi.dao.entity.fofo.InventoryItem;
71
import com.spice.profitmandi.dao.entity.fofo.InvoiceNumberGenerationSequence;
24470 tejbeer 72
import com.spice.profitmandi.dao.entity.fofo.LiveDemoSerialNumber;
22859 ashik.ali 73
import com.spice.profitmandi.dao.entity.fofo.ScanRecord;
24917 tejbeer 74
import com.spice.profitmandi.dao.entity.transaction.Order;
22859 ashik.ali 75
import com.spice.profitmandi.dao.entity.user.Address;
76
import com.spice.profitmandi.dao.entity.user.Counter;
77
import com.spice.profitmandi.dao.entity.user.PrivateDealUser;
24264 amit.gupta 78
import com.spice.profitmandi.dao.enumuration.catalog.SchemeType;
23546 ashik.ali 79
import com.spice.profitmandi.dao.enumuration.dtr.PaymentOptionReferenceType;
23650 amit.gupta 80
import com.spice.profitmandi.dao.enumuration.fofo.ReturnType;
22859 ashik.ali 81
import com.spice.profitmandi.dao.enumuration.fofo.ScanType;
23655 amit.gupta 82
import com.spice.profitmandi.dao.enumuration.fofo.SettlementType;
25640 tejbeer 83
 
22859 ashik.ali 84
import com.spice.profitmandi.dao.repository.catalog.ItemRepository;
24823 amit.gupta 85
import com.spice.profitmandi.dao.repository.catalog.TagListingRepository;
23202 ashik.ali 86
import com.spice.profitmandi.dao.repository.dtr.FofoStoreRepository;
22859 ashik.ali 87
import com.spice.profitmandi.dao.repository.dtr.InsurancePolicyRepository;
88
import com.spice.profitmandi.dao.repository.dtr.InsuranceProviderRepository;
23552 amit.gupta 89
import com.spice.profitmandi.dao.repository.dtr.PaymentOptionTransactionRepository;
22859 ashik.ali 90
import com.spice.profitmandi.dao.repository.dtr.PolicyNumberGenerationSequenceRepository;
91
import com.spice.profitmandi.dao.repository.dtr.RetailerRegisteredAddressRepository;
92
import com.spice.profitmandi.dao.repository.dtr.RetailerRepository;
93
import com.spice.profitmandi.dao.repository.dtr.UserAccountRepository;
94
import com.spice.profitmandi.dao.repository.dtr.UserRepository;
95
import com.spice.profitmandi.dao.repository.fofo.CurrentInventorySnapshotRepository;
96
import com.spice.profitmandi.dao.repository.fofo.CustomerAddressRepository;
23650 amit.gupta 97
import com.spice.profitmandi.dao.repository.fofo.CustomerCreditNoteRepository;
22859 ashik.ali 98
import com.spice.profitmandi.dao.repository.fofo.CustomerRepository;
23650 amit.gupta 99
import com.spice.profitmandi.dao.repository.fofo.CustomerReturnItemRepository;
22859 ashik.ali 100
import com.spice.profitmandi.dao.repository.fofo.FofoLineItemRepository;
101
import com.spice.profitmandi.dao.repository.fofo.FofoOrderItemRepository;
102
import com.spice.profitmandi.dao.repository.fofo.FofoOrderRepository;
25640 tejbeer 103
import com.spice.profitmandi.dao.repository.fofo.HygieneDataRepository;
22859 ashik.ali 104
import com.spice.profitmandi.dao.repository.fofo.InventoryItemRepository;
105
import com.spice.profitmandi.dao.repository.fofo.InvoiceNumberGenerationSequenceRepository;
24470 tejbeer 106
import com.spice.profitmandi.dao.repository.fofo.LiveDemoBillingRespository;
22859 ashik.ali 107
import com.spice.profitmandi.dao.repository.fofo.PaymentOptionRepository;
23566 amit.gupta 108
import com.spice.profitmandi.dao.repository.fofo.PurchaseReturnItemRepository;
22859 ashik.ali 109
import com.spice.profitmandi.dao.repository.fofo.ScanRecordRepository;
24854 amit.gupta 110
import com.spice.profitmandi.dao.repository.inventory.StateRepository;
24917 tejbeer 111
import com.spice.profitmandi.dao.repository.transaction.OrderRepository;
22859 ashik.ali 112
import com.spice.profitmandi.dao.repository.user.AddressRepository;
113
import com.spice.profitmandi.dao.repository.user.CounterRepository;
114
import com.spice.profitmandi.dao.repository.user.PrivateDealUserRepository;
24440 amit.gupta 115
import com.spice.profitmandi.service.integrations.zest.MobileInsurancePlan;
116
import com.spice.profitmandi.service.integrations.zest.ZestService;
23418 ashik.ali 117
import com.spice.profitmandi.service.inventory.InventoryService;
23655 amit.gupta 118
import com.spice.profitmandi.service.inventory.PurchaseReturnService;
22859 ashik.ali 119
import com.spice.profitmandi.service.pricing.PricingService;
120
import com.spice.profitmandi.service.scheme.SchemeService;
23655 amit.gupta 121
import com.spice.profitmandi.service.user.RetailerService;
23395 amit.gupta 122
import com.spice.profitmandi.service.wallet.WalletService;
22859 ashik.ali 123
 
23395 amit.gupta 124
import in.shop2020.model.v1.order.WalletReferenceType;
22859 ashik.ali 125
 
126
@Component
127
public class OrderServiceImpl implements OrderService {
128
 
23568 govind 129
	private static final Logger LOGGER = LogManager.getLogger(OrderServiceImpl.class);
22859 ashik.ali 130
 
131
	@Autowired
23781 ashik.ali 132
	@Qualifier("fofoInventoryItemRepository")
22859 ashik.ali 133
	private InventoryItemRepository inventoryItemRepository;
23650 amit.gupta 134
 
23395 amit.gupta 135
	@Autowired
24470 tejbeer 136
	private LiveDemoBillingRespository liveDemoBillingRespository;
24823 amit.gupta 137
 
24470 tejbeer 138
	@Autowired
23395 amit.gupta 139
	private WalletService walletService;
22859 ashik.ali 140
 
141
	@Autowired
23781 ashik.ali 142
	@Qualifier("fofoCurrentInventorySnapshotRepository")
22859 ashik.ali 143
	private CurrentInventorySnapshotRepository currentInventorySnapshotRepository;
144
 
145
	@Autowired
146
	private InvoiceNumberGenerationSequenceRepository invoiceNumberGenerationSequenceRepository;
147
 
148
	@Autowired
23655 amit.gupta 149
	private PurchaseReturnService purchaseReturnService;
150
 
151
	@Autowired
24440 amit.gupta 152
	private ZestService zestService;
153
 
154
	@Autowired
23655 amit.gupta 155
	private RetailerService retailerService;
156
 
157
	@Autowired
22859 ashik.ali 158
	private CustomerRepository customerRepository;
23650 amit.gupta 159
 
23566 amit.gupta 160
	@Autowired
161
	private PurchaseReturnItemRepository purchaseReturnItemRepository;
22859 ashik.ali 162
 
163
	@Autowired
164
	private AddressRepository addressRepository;
165
 
166
	@Autowired
167
	private FofoLineItemRepository fofoLineItemRepository;
168
 
169
	@Autowired
170
	private FofoOrderItemRepository fofoOrderItemRepository;
23650 amit.gupta 171
 
22859 ashik.ali 172
	@Autowired
173
	private PaymentOptionRepository paymentOptionRepository;
174
 
175
	@Autowired
23650 amit.gupta 176
	private CustomerReturnItemRepository customerReturnItemRepository;
177
 
178
	@Autowired
23781 ashik.ali 179
	@Qualifier("fofoScanRecordRepository")
22859 ashik.ali 180
	private ScanRecordRepository scanRecordRepository;
181
 
182
	@Autowired
183
	private FofoOrderRepository fofoOrderRepository;
184
 
185
	@Autowired
186
	private RetailerRepository retailerRepository;
187
 
188
	@Autowired
189
	private UserRepository userRepository;
190
 
191
	@Autowired
192
	private UserAccountRepository userAccountRepository;
193
 
194
	@Autowired
195
	private RetailerRegisteredAddressRepository retailerRegisteredAddressRepository;
196
 
197
	@Autowired
198
	private CustomerAddressRepository customerAddressRepository;
199
 
200
	@Autowired
23781 ashik.ali 201
	@Qualifier("catalogItemRepository")
22859 ashik.ali 202
	private ItemRepository itemRepository;
23650 amit.gupta 203
 
22859 ashik.ali 204
	@Autowired
205
	private InsuranceProviderRepository insuranceProviderRepository;
23650 amit.gupta 206
 
22859 ashik.ali 207
	@Autowired
208
	private InsurancePolicyRepository insurancePolicyRepository;
24917 tejbeer 209
 
24854 amit.gupta 210
	@Autowired
211
	private StateRepository stateRepository;
23650 amit.gupta 212
 
22859 ashik.ali 213
	@Autowired
214
	private PolicyNumberGenerationSequenceRepository policyNumberGenerationSequenceRepository;
23650 amit.gupta 215
 
22859 ashik.ali 216
	@Autowired
217
	private PricingService pricingService;
23650 amit.gupta 218
 
22859 ashik.ali 219
	@Autowired
220
	private PrivateDealUserRepository privateDealUserRepository;
23650 amit.gupta 221
 
22859 ashik.ali 222
	@Autowired
24823 amit.gupta 223
	private TagListingRepository tagListingRepository;
224
 
225
	@Autowired
22859 ashik.ali 226
	private CounterRepository counterRepository;
23650 amit.gupta 227
 
22859 ashik.ali 228
	@Autowired
23202 ashik.ali 229
	private FofoStoreRepository fofoStoreRepository;
23650 amit.gupta 230
 
23202 ashik.ali 231
	@Autowired
23546 ashik.ali 232
	private PaymentOptionTransactionRepository paymentOptionTransactionRepository;
23650 amit.gupta 233
 
23365 ashik.ali 234
	@Autowired
22859 ashik.ali 235
	private SchemeService schemeService;
23650 amit.gupta 236
 
23418 ashik.ali 237
	@Autowired
23781 ashik.ali 238
	@Qualifier("fofoInventoryService")
23418 ashik.ali 239
	private InventoryService inventoryService;
23650 amit.gupta 240
 
23418 ashik.ali 241
	@Autowired
23650 amit.gupta 242
	private CustomerCreditNoteRepository customerCreditNoteRepository;
243
 
24917 tejbeer 244
	@Autowired
245
	private OrderRepository orderRepository;
246
 
25640 tejbeer 247
	@Autowired
248
	private HygieneDataRepository hygieneDataRepository;
249
 
22859 ashik.ali 250
	@Override
24275 amit.gupta 251
	public int createOrder(CreateOrderRequest createOrderRequest, int fofoId, boolean accessoriesDeals)
252
			throws ProfitMandiBusinessException {
23650 amit.gupta 253
 
22872 ashik.ali 254
		CustomCustomer customCustomer = createOrderRequest.getCustomer();
255
 
23650 amit.gupta 256
		if (!StringUtils.isValidEmailAddress(customCustomer.getEmailId())) {
22872 ashik.ali 257
			LOGGER.error("invalid customer emailId {} ", customCustomer.getEmailId());
23650 amit.gupta 258
			throw new ProfitMandiBusinessException(ProfitMandiConstants.EMAIL_ID, customCustomer.getEmailId(),
259
					"VE_1016");
22872 ashik.ali 260
		}
261
 
23650 amit.gupta 262
		if (!StringUtils.isValidMobile(customCustomer.getMobileNumber())) {
22872 ashik.ali 263
			LOGGER.error("invalid customer mobileNumber {} ", customCustomer.getMobileNumber());
23650 amit.gupta 264
			throw new ProfitMandiBusinessException(ProfitMandiConstants.MOBILE_NUMBER, customCustomer.getMobileNumber(),
265
					"VE_1071");
22872 ashik.ali 266
		}
23650 amit.gupta 267
 
268
		if (!StringUtils.isValidGstNumber(customCustomer.getGstNumber())) {
23369 ashik.ali 269
			LOGGER.error("invalid customer gstNumber {} ", customCustomer.getGstNumber());
23650 amit.gupta 270
			throw new ProfitMandiBusinessException(ProfitMandiConstants.CUSTOMER_GST_NUMBER,
271
					customCustomer.getGstNumber(), "VE_1072");
23369 ashik.ali 272
		}
23650 amit.gupta 273
 
274
		Map<Integer, Integer> itemIdQuantity = new HashMap<>(); // this is for error
22872 ashik.ali 275
		Map<Integer, CustomFofoOrderItem> itemIdCustomFofoOrderItemMap = new HashMap<>();
23650 amit.gupta 276
		Map<Integer, Float> lineItemPrice = new HashMap<>(); // this is for pricing error
277
 
22859 ashik.ali 278
		float totalAmount = 0;
24226 amit.gupta 279
		boolean noGST = false;
23650 amit.gupta 280
		for (CustomFofoOrderItem customFofoOrderItem : createOrderRequest.getFofoOrderItems()) {
281
			// itemIds.add(customFofoOrderItem.getItemId());
282
			Set<String> serialNumbers = this
283
					.serialNumberDetailsToSerialNumbers(customFofoOrderItem.getSerialNumberDetails());
284
			if (!serialNumbers.isEmpty() && customFofoOrderItem.getQuantity() != serialNumbers.size()) {
22859 ashik.ali 285
				itemIdQuantity.put(customFofoOrderItem.getItemId(), customFofoOrderItem.getQuantity());
286
			}
23650 amit.gupta 287
			if (!(customFofoOrderItem.getSellingPrice() > 0)) {
22859 ashik.ali 288
				lineItemPrice.put(customFofoOrderItem.getItemId(), customFofoOrderItem.getSellingPrice());
23650 amit.gupta 289
			} else {
22863 ashik.ali 290
				totalAmount = totalAmount + customFofoOrderItem.getSellingPrice() * customFofoOrderItem.getQuantity();
291
				totalAmount = totalAmount - customFofoOrderItem.getDiscountAmount() * customFofoOrderItem.getQuantity();
23650 amit.gupta 292
				for (SerialNumberDetail serialNumberDetail : customFofoOrderItem.getSerialNumberDetails()) {
24440 amit.gupta 293
					if (serialNumberDetail.getAmount() > 0) {
22859 ashik.ali 294
						totalAmount = totalAmount + serialNumberDetail.getAmount();
295
					}
296
				}
297
			}
23650 amit.gupta 298
 
22872 ashik.ali 299
			itemIdCustomFofoOrderItemMap.put(customFofoOrderItem.getItemId(), customFofoOrderItem);
22859 ashik.ali 300
		}
23650 amit.gupta 301
		if (!itemIdQuantity.isEmpty()) {
22859 ashik.ali 302
			// if item quantity does not match with given serialnumbers size
303
			LOGGER.error("itemId's quantity should be equal to given serialnumber size {} ", itemIdQuantity);
22925 ashik.ali 304
			throw new ProfitMandiBusinessException("itemIdQuantity", itemIdQuantity, "FFORDR_1001");
23650 amit.gupta 305
			// return "error";
22859 ashik.ali 306
		}
23650 amit.gupta 307
 
24275 amit.gupta 308
		this.validatePaymentOptionsAndTotalAmount(createOrderRequest.getPaymentOptions(), totalAmount);
23650 amit.gupta 309
 
310
		if (!lineItemPrice.isEmpty()) {
22859 ashik.ali 311
			// given fofo line item price must be greater than zero
312
			LOGGER.error("requested itemId's selling price must greater than 0");
22925 ashik.ali 313
			throw new ProfitMandiBusinessException(ProfitMandiConstants.PRICE, lineItemPrice, "FFORDR_1002");
22859 ashik.ali 314
		}
315
 
23650 amit.gupta 316
		List<CurrentInventorySnapshot> currentInventorySnapshots = currentInventorySnapshotRepository
317
				.selectByFofoItemIds(fofoId, itemIdCustomFofoOrderItemMap.keySet());
318
 
22872 ashik.ali 319
		this.validateCurrentInventorySnapshotQuantities(currentInventorySnapshots, itemIdCustomFofoOrderItemMap);
22859 ashik.ali 320
 
22872 ashik.ali 321
		List<Item> items = itemRepository.selectByIds(itemIdCustomFofoOrderItemMap.keySet());
23650 amit.gupta 322
		if (items.size() != itemIdCustomFofoOrderItemMap.keySet().size()) {
22872 ashik.ali 323
			LOGGER.error("Requested ItemIds not found in catalog");
23650 amit.gupta 324
			// invalid itemIds
325
			throw new ProfitMandiBusinessException("invalidItemIds", itemIdCustomFofoOrderItemMap.keySet(),
326
					"FFORDR_1003");
22872 ashik.ali 327
		}
23650 amit.gupta 328
 
329
		Map<Integer, Item> itemMap = this.toItemMap(items);
330
 
22859 ashik.ali 331
		Set<Integer> nonSerializedItemIds = new HashSet<>();
332
		Set<String> serialNumbers = new HashSet<>();
24440 amit.gupta 333
		Map<String, InsuranceModel> insuranceSerialNumberMap = new HashMap<>();
23650 amit.gupta 334
		for (CustomFofoOrderItem customFofoOrderItem : createOrderRequest.getFofoOrderItems()) {
22872 ashik.ali 335
			Item item = itemMap.get(customFofoOrderItem.getItemId());
24275 amit.gupta 336
			noGST = item.getHsnCode().equals("NOGST");
23650 amit.gupta 337
			if (item.getType().equals(ItemType.SERIALIZED)) {
338
				for (SerialNumberDetail serialNumberDetail : customFofoOrderItem.getSerialNumberDetails()) {
22859 ashik.ali 339
					serialNumbers.add(serialNumberDetail.getSerialNumber());
24440 amit.gupta 340
					if (serialNumberDetail.getAmount() > 0) {
341
						InsuranceModel im = new InsuranceModel();
342
						im.setBrand(item.getBrand());
343
						im.setModelName(item.getModelName());
344
						im.setInsuranceAmount(serialNumberDetail.getAmount());
345
						im.setDeviceSellingPrice(customFofoOrderItem.getSellingPrice());
346
						im.setInsuranceId(serialNumberDetail.getInsurance() + "");
347
						insuranceSerialNumberMap.put(serialNumberDetail.getSerialNumber(), im);
22859 ashik.ali 348
					}
349
				}
23650 amit.gupta 350
			} else {
22872 ashik.ali 351
				nonSerializedItemIds.add(customFofoOrderItem.getItemId());
22859 ashik.ali 352
			}
353
		}
23650 amit.gupta 354
 
22859 ashik.ali 355
		Map<Integer, Set<InventoryItem>> serializedInventoryItemMap = new HashMap<>();
356
		Map<Integer, Set<InventoryItem>> nonSerializedInventoryItemMap = new HashMap<>();
23650 amit.gupta 357
		// Map<String, Float> serialNumberItemPrice = new HashMap<>();
358
 
359
		if (!serialNumbers.isEmpty()) {
360
			List<InventoryItem> serializedInventoryItems = inventoryItemRepository.selectByFofoIdSerialNumbers(fofoId,
23968 amit.gupta 361
					serialNumbers, false);
23397 amit.gupta 362
			LOGGER.info("serializedInventoryItems {}", serializedInventoryItems);
23650 amit.gupta 363
			for (InventoryItem inventoryItem : serializedInventoryItems) {
364
				if (inventoryItem.getGoodQuantity() == 1) {
365
					if (serializedInventoryItemMap.containsKey(inventoryItem.getItemId())) {
23397 amit.gupta 366
						serializedInventoryItemMap.get(inventoryItem.getItemId()).add(inventoryItem);
23650 amit.gupta 367
					} else {
23397 amit.gupta 368
						Set<InventoryItem> itemIdInventoryItems = new HashSet<>();
369
						itemIdInventoryItems.add(inventoryItem);
370
						serializedInventoryItemMap.put(inventoryItem.getItemId(), itemIdInventoryItems);
371
					}
372
				}
373
			}
374
		}
23418 ashik.ali 375
 
23650 amit.gupta 376
		if (!nonSerializedItemIds.isEmpty()) {
377
			List<InventoryItem> nonSerializedInventoryItems = inventoryItemRepository.selectByFofoIdItemIds(fofoId,
378
					nonSerializedItemIds);
22872 ashik.ali 379
			LOGGER.info("nonSerializedInventoryItems {}", nonSerializedInventoryItems);
23650 amit.gupta 380
			for (InventoryItem it : nonSerializedInventoryItems) {
381
				if (it.getGoodQuantity() > 0) {
382
					if (nonSerializedInventoryItemMap.containsKey(it.getItemId())) {
22859 ashik.ali 383
						nonSerializedInventoryItemMap.get(it.getItemId()).add(it);
23650 amit.gupta 384
					} else {
22859 ashik.ali 385
						Set<InventoryItem> tmp = new HashSet<>();
386
						tmp.add(it);
387
						nonSerializedInventoryItemMap.put(it.getItemId(), tmp);
388
					}
389
				}
390
			}
391
		}
23650 amit.gupta 392
 
22872 ashik.ali 393
		this.validateItemsSerializedNonSerialized(items, itemIdCustomFofoOrderItemMap);
22859 ashik.ali 394
 
395
		Map<Integer, Set<InventoryItem>> inventoryItemsToBill = new HashMap<>();
23650 amit.gupta 396
		Map<Integer, Integer> inventoryItemIdQuantityUsed = new HashMap<>(); // to keep track of inventoryitem quanity
397
																				// used for scan records insertion
22859 ashik.ali 398
 
399
		LOGGER.info("itemMap keys {}", itemMap.keySet());
23650 amit.gupta 400
		// Lets reduce quantity and decide what inventory items to use.
401
		for (Item item : items) {
402
			if (item.getType().equals(ItemType.SERIALIZED)) {
403
				// TODO:handle null
404
				if (serializedInventoryItemMap.get(item.getId()) == null
405
						|| itemIdCustomFofoOrderItemMap.get(item.getId()).getSerialNumberDetails()
406
								.size() != serializedInventoryItemMap.get(item.getId()).size()) {
24440 amit.gupta 407
 
22872 ashik.ali 408
					LOGGER.error("itemId {} => mismatch size of requested serial numbers", item.getId());
24440 amit.gupta 409
					List<String> invalidSerialNumbers = itemIdCustomFofoOrderItemMap.get(item.getId())
410
							.getSerialNumberDetails().stream().map(x -> x.getSerialNumber())
411
							.collect(Collectors.toList());
412
					throw new ProfitMandiBusinessException("invalidSerialNumbers", invalidSerialNumbers, "FFORDR_1004");
22872 ashik.ali 413
				}
24470 tejbeer 414
				List<String> serialNumberList = liveDemoBillingRespository.selectAllSerialNumber();
24823 amit.gupta 415
 
22859 ashik.ali 416
				Set<InventoryItem> inventoryItemsSerializedserialized = serializedInventoryItemMap.get(item.getId());
23650 amit.gupta 417
				for (InventoryItem inventoryItem : inventoryItemsSerializedserialized) {
22872 ashik.ali 418
					inventoryItem.setGoodQuantity(0);
419
					inventoryItemIdQuantityUsed.put(inventoryItem.getId(), 1);
24823 amit.gupta 420
					if (serialNumberList.contains(inventoryItem.getSerialNumber())) {
421
						LiveDemoSerialNumber liveDemoSerialNumber = liveDemoBillingRespository
422
								.selectBySerialNumber(inventoryItem.getSerialNumber());
24470 tejbeer 423
						liveDemoBillingRespository.delete(liveDemoSerialNumber);
424
					}
22859 ashik.ali 425
				}
426
				inventoryItemsToBill.put(item.getId(), inventoryItemsSerializedserialized);
23650 amit.gupta 427
			} else {
22859 ashik.ali 428
				Set<InventoryItem> inventoryItemsNonSerialized = nonSerializedInventoryItemMap.get(item.getId());
22872 ashik.ali 429
				int quantityToBill = itemIdCustomFofoOrderItemMap.get(item.getId()).getQuantity();
22859 ashik.ali 430
				int totalLeft = quantityToBill;
431
				Set<InventoryItem> inventoryItemsNonSerializedUsed = new HashSet<>();
23650 amit.gupta 432
				if (inventoryItemsNonSerialized != null) {
433
					for (InventoryItem inventoryItem : inventoryItemsNonSerialized) {
434
						if (totalLeft > 0) {
22859 ashik.ali 435
							int toUse = Math.min(totalLeft, inventoryItem.getGoodQuantity());
436
							inventoryItemIdQuantityUsed.put(inventoryItem.getId(), toUse);
23650 amit.gupta 437
							inventoryItem.setGoodQuantity(inventoryItem.getGoodQuantity() - toUse);
22859 ashik.ali 438
							totalLeft = totalLeft - toUse;
439
							inventoryItemsNonSerializedUsed.add(inventoryItem);
440
						}
441
					}
442
				}
23650 amit.gupta 443
 
444
				if (totalLeft > 0) {
445
					// not enough quanity for non-serialized
22859 ashik.ali 446
					LOGGER.error("not enough quanity for non-serialized");
23650 amit.gupta 447
					throw new ProfitMandiBusinessException("notEnoughQuantityForNonSerialized", totalLeft,
448
							"FFORDR_1005");
22859 ashik.ali 449
				}
450
				inventoryItemsToBill.put(item.getId(), inventoryItemsNonSerializedUsed);
451
			}
452
		}
23650 amit.gupta 453
 
454
		Map<Integer, PriceModel> itemIdMopPriceMap = pricingService
455
				.getPurchasePriceMopPriceNotFound(itemIdCustomFofoOrderItemMap.keySet(), fofoId);
24275 amit.gupta 456
		if (accessoriesDeals) {
23823 amit.gupta 457
			this.validateDpPrice(itemIdMopPriceMap, itemIdCustomFofoOrderItemMap);
458
		} else {
459
			this.validateMopPrice(itemIdMopPriceMap, itemIdCustomFofoOrderItemMap);
460
		}
23650 amit.gupta 461
 
23202 ashik.ali 462
		String fofoStoreCode = this.getFofoStoreCode(fofoId);
24226 amit.gupta 463
		String documentNumber = null;
24275 amit.gupta 464
		if (noGST) {
24226 amit.gupta 465
			documentNumber = this.getSecurityDepositNumber(fofoId, fofoStoreCode);
24275 amit.gupta 466
 
24226 amit.gupta 467
		} else {
468
			documentNumber = this.getInvoiceNumber(fofoId, fofoStoreCode);
469
		}
22859 ashik.ali 470
 
471
		Customer customer = this.createAndGetCustomer(customCustomer);
23650 amit.gupta 472
 
23191 ashik.ali 473
		CustomerAddress customerAddress = this.createCustomerAddress(customCustomer.getAddress(), customer.getId());
23650 amit.gupta 474
 
475
		FofoOrder fofoOrder = this.createAndGetFofoOrder(customer.getId(), customCustomer.getGstNumber(), fofoId,
24226 amit.gupta 476
				documentNumber, totalAmount, customerAddress.getId());
23650 amit.gupta 477
 
25644 tejbeer 478
		List<FofoOrderItem> fofoItems = fofoOrderItemRepository.selectByOrderId(fofoOrder.getId());
25640 tejbeer 479
 
25644 tejbeer 480
		for (FofoOrderItem fofoItem : fofoItems) {
481
			Item orderItem = itemRepository.selectById(fofoItem.getItemId());
482
			if (orderItem.getCategoryId() == ProfitMandiConstants.MOBILE_CATEGORY_ID) {
483
				this.createAndGetHygieneData(fofoOrder.getId(), fofoOrder.getFofoId());
484
			}
485
		}
486
 
23612 amit.gupta 487
		this.createPaymentOptions(fofoOrder, createOrderRequest.getPaymentOptions());
23650 amit.gupta 488
 
23172 ashik.ali 489
		int retailerAddressId = retailerRegisteredAddressRepository.selectAddressIdByRetailerId(fofoId);
23650 amit.gupta 490
 
23172 ashik.ali 491
		Address retailerAddress = addressRepository.selectById(retailerAddressId);
23650 amit.gupta 492
 
23172 ashik.ali 493
		Integer stateId = null;
23650 amit.gupta 494
		if (customerAddress.getState().equals(retailerAddress.getState())) {
495
			try {
23172 ashik.ali 496
				stateId = Long.valueOf(Utils.getStateInfo(customerAddress.getState()).getId()).intValue();
23650 amit.gupta 497
			} catch (Exception e) {
23172 ashik.ali 498
				LOGGER.error("Unable to get state rates");
499
			}
500
		}
23650 amit.gupta 501
 
502
		for (CustomFofoOrderItem customFofoOrderItem : createOrderRequest.getFofoOrderItems()) {
503
			FofoOrderItem fofoOrderItem = this.createAndGetFofoOrderItem(customFofoOrderItem, fofoOrder.getId(),
504
					itemMap, inventoryItemsToBill.get(customFofoOrderItem.getItemId()), stateId);
505
 
22859 ashik.ali 506
			Set<InventoryItem> inventoryItems = inventoryItemsToBill.get(customFofoOrderItem.getItemId());
23650 amit.gupta 507
 
22859 ashik.ali 508
			this.createFofoLineItem(fofoOrderItem.getId(), inventoryItems, inventoryItemIdQuantityUsed);
23650 amit.gupta 509
 
510
			this.updateCurrentInventorySnapshot(currentInventorySnapshots, fofoId, customFofoOrderItem.getItemId(),
511
					customFofoOrderItem.getQuantity());
512
 
24275 amit.gupta 513
			this.updateInventoryItemsAndScanRecord(inventoryItems, fofoId, inventoryItemIdQuantityUsed,
514
					fofoOrder.getId());
22859 ashik.ali 515
		}
23650 amit.gupta 516
 
22859 ashik.ali 517
		// insurance calculation is insurance flag is enabled
24440 amit.gupta 518
		//
519
		if (!insuranceSerialNumberMap.isEmpty()) {
520
			LOGGER.info("Processing insurane for serialNumbers");
23650 amit.gupta 521
 
24440 amit.gupta 522
			LocalDate customerDateOfBirth = LocalDate.from(createOrderRequest.getCustomer().getDateOfBirth());
23650 amit.gupta 523
 
24440 amit.gupta 524
			for (Map.Entry<String, InsuranceModel> entry : insuranceSerialNumberMap.entrySet()) {
525
				InsuranceModel insuranceModel = entry.getValue();
526
				MobileInsurancePlan mobileInsurancePlan = zestService.getAllPlansMap()
527
						.get(insuranceModel.getInsuranceId());
528
				InsurancePolicy insurancePolicy = this.createInsurancePolicy(fofoOrder.getInvoiceNumber(), fofoId,
529
						insuranceModel.getInsuranceAmount() - mobileInsurancePlan.getPartnerCommission(),
530
						insuranceModel.getInsuranceAmount(), insuranceModel.getDeviceSellingPrice(), entry.getKey(),
531
						insuranceModel.getModelName(), insuranceModel.getBrand(), customer, customerDateOfBirth,
24823 amit.gupta 532
						customerAddress,
533
						mobileInsurancePlan.getProductName() + " for " + mobileInsurancePlan.getDuration() + " Months");
23650 amit.gupta 534
 
24440 amit.gupta 535
				String walletDescription = null;
536
				if (mobileInsurancePlan.getProviderId().equals("0")) {
537
					insurancePolicy.setProviderId(1);
538
					int policyNumberGenerationSequence = this.createPolicyNumberGenerationSequence().getSequence();
539
					insurancePolicy.setPolicyNumber(StringUtils.generatePolicyNumber(
540
							ProfitMandiConstants.POLICY_NUMBER_PREFIX, policyNumberGenerationSequence));
541
					GadgetCopsInsuranceModel gadgetCopsInsuranceModel = this.createGadgetCopsInsuranceModel(
542
							entry.getValue().getBrand(), entry.getValue().getModelName(), entry.getKey(),
543
							customerDateOfBirth, customer, customerAddress, insurancePolicy);
23650 amit.gupta 544
 
24440 amit.gupta 545
					try {
546
						InsuranceUtils.submitToGadgetCops(gadgetCopsInsuranceModel);
547
						insurancePolicy.setPosted(true);
548
						walletDescription = "Sale of " + insurancePolicy.getPolicyNumber() + " for "
549
								+ fofoOrder.getInvoiceNumber();
550
					} catch (ProfitMandiBusinessException profitMandiBusinessException) {
551
						LOGGER.info("Unable to submit insurance policy details to {}", insuranceModel.getProviderName(),
552
								profitMandiBusinessException);
553
						throw new ProfitMandiBusinessException("Insurance", mobileInsurancePlan.getProductName(),
554
								"Could not generate insurance for Gadget Cop");
555
					}
556
				} else {
557
					try {
558
						WiseAppInsuaranceModel wiseAppInsuaranceModel = this
559
								.createWiseAppInsuranceModel(mobileInsurancePlan, insurancePolicy, customCustomer);
560
						String wiseAppInsuranceCode = zestService.createInsurance(wiseAppInsuaranceModel);
561
						insurancePolicy.setPolicyNumber(wiseAppInsuranceCode);
562
						// TODO: remove hardcoding
563
						insurancePolicy.setProviderId(2);
564
						walletDescription = "Sale of " + insurancePolicy.getProductName() + " against "
565
								+ fofoOrder.getInvoiceNumber();
566
					} catch (ProfitMandiBusinessException pbe) {
567
						pbe.printStackTrace();
568
						throw new ProfitMandiBusinessException("Insurance", mobileInsurancePlan.getProductName(),
569
								pbe.getMessage());
570
					}
571
				}
23650 amit.gupta 572
				walletService.consumeAmountFromWallet(fofoId, insurancePolicy.getId(),
23395 amit.gupta 573
						WalletReferenceType.DAMAGE_PROTECTION, walletDescription, insurancePolicy.getPurchaseAmount());
22859 ashik.ali 574
				insurancePolicyRepository.persist(insurancePolicy);
575
			}
576
		}
25640 tejbeer 577
		// schemeService.processSchemeOut(fofoOrder.getId(), fofoId);
22859 ashik.ali 578
		return fofoOrder.getId();
579
	}
23650 amit.gupta 580
 
25640 tejbeer 581
	private HygieneData createAndGetHygieneData(int id, int fofoId) {
582
		HygieneData hygieneData = new HygieneData();
583
		hygieneData.setOrderId(id);
584
		hygieneData.setFofoId(fofoId);
585
		hygieneData.setCreatedTimestamp(LocalDateTime.now());
586
		hygieneDataRepository.persist(hygieneData);
587
 
588
		return hygieneData;
589
	}
590
 
24440 amit.gupta 591
	private WiseAppInsuaranceModel createWiseAppInsuranceModel(MobileInsurancePlan mobileInsurancePlan,
592
			InsurancePolicy insurancePolicy, CustomCustomer customer) throws ProfitMandiBusinessException {
593
		WiseAppInsuaranceModel wiseAppInsuranceModel = new WiseAppInsuaranceModel();
594
		CustomAddress address = customer.getAddress();
595
 
596
		String sAddress = (address.getLine1() + " " + address.getLine2()).replaceAll("  ", " ");
597
		wiseAppInsuranceModel.setAddress(sAddress);
598
		wiseAppInsuranceModel.setBrand(insurancePolicy.getBrand());
599
		wiseAppInsuranceModel.setBalanceType("4");
600
		wiseAppInsuranceModel.setProduct(mobileInsurancePlan.getProductId());
601
		wiseAppInsuranceModel
602
				.setName((insurancePolicy.getCustomerFirstName() + " " + insurancePolicy.getCustomerLastName()));
603
		wiseAppInsuranceModel.setCity(address.getCity());
604
		wiseAppInsuranceModel.setDob(StringUtils.toHyphenatedString(customer.getDateOfBirth()));
605
		wiseAppInsuranceModel.setDuration(mobileInsurancePlan.getDuration());
606
		wiseAppInsuranceModel.setPincode(address.getPinCode());
607
		wiseAppInsuranceModel.setEmail(customer.getEmailId());
24450 amit.gupta 608
		wiseAppInsuranceModel.setDeviceType(mobileInsurancePlan.getDeviceTypeId());
24440 amit.gupta 609
		wiseAppInsuranceModel.setImeiNo(insurancePolicy.getSerialNumber());
610
		wiseAppInsuranceModel.setPlanValue(String.valueOf(insurancePolicy.getSaleAmount()));
611
		wiseAppInsuranceModel.setRetailerId(zestService.getWiseAppPartnerCode(insurancePolicy.getRetailerId()));
612
		wiseAppInsuranceModel.setDuration(mobileInsurancePlan.getDuration());
613
		wiseAppInsuranceModel.setGender(customer.getGender());
614
		wiseAppInsuranceModel.setInvoiceNo(insurancePolicy.getInvoiceNumber());
615
		wiseAppInsuranceModel.setNumber(insurancePolicy.getCustomerMobileNumber());
616
		wiseAppInsuranceModel
617
				.setPurchaseDate(StringUtils.toHyphenatedString(insurancePolicy.getCreateTimestamp().toLocalDate()));
618
		wiseAppInsuranceModel.setModel(insurancePolicy.getModelName());
619
		wiseAppInsuranceModel.setHandSetValue(String.valueOf(insurancePolicy.getSellingPrice()));
620
		wiseAppInsuranceModel.setInsurerCompany(mobileInsurancePlan.getProviderId());
621
		return wiseAppInsuranceModel;
622
	}
623
 
24807 amit.gupta 624
	@Override
625
	public String getInvoiceNumber(int fofoId, String fofoStoreCode) {
24236 amit.gupta 626
		InvoiceNumberGenerationSequence invoiceNumberGenerationSequence = null;
627
		try {
628
			invoiceNumberGenerationSequence = invoiceNumberGenerationSequenceRepository.selectByFofoId(fofoId);
629
			invoiceNumberGenerationSequence.setSequence(invoiceNumberGenerationSequence.getSequence() + 1);
630
		} catch (ProfitMandiBusinessException profitMandiBusinessException) {
631
			invoiceNumberGenerationSequence = new InvoiceNumberGenerationSequence();
632
			invoiceNumberGenerationSequence.setFofoId(fofoId);
633
			invoiceNumberGenerationSequence.setPrefix(fofoStoreCode);
634
			invoiceNumberGenerationSequence.setSequence(1);
635
		}
636
		invoiceNumberGenerationSequenceRepository.persist(invoiceNumberGenerationSequence);
637
		return invoiceNumberGenerationSequence.getPrefix() + "/" + invoiceNumberGenerationSequence.getSequence();
638
	}
24275 amit.gupta 639
 
640
	private String getSecurityDepositNumber(int fofoId, String fofoStoreCode) {
24226 amit.gupta 641
		InvoiceNumberGenerationSequence invoiceNumberGenerationSequence = null;
642
		try {
643
			invoiceNumberGenerationSequence = invoiceNumberGenerationSequenceRepository.selectByFofoId(fofoId);
24275 amit.gupta 644
			invoiceNumberGenerationSequence
645
					.setChallanNumberSequence(invoiceNumberGenerationSequence.getChallanNumberSequence() + 1);
24226 amit.gupta 646
		} catch (ProfitMandiBusinessException profitMandiBusinessException) {
647
			invoiceNumberGenerationSequence = new InvoiceNumberGenerationSequence();
648
			invoiceNumberGenerationSequence.setFofoId(fofoId);
649
			invoiceNumberGenerationSequence.setPrefix(fofoStoreCode);
650
			invoiceNumberGenerationSequence.setChallanNumberSequence(1);
651
		}
652
		invoiceNumberGenerationSequenceRepository.persist(invoiceNumberGenerationSequence);
24275 amit.gupta 653
		return invoiceNumberGenerationSequence.getPrefix() + "/SEC"
654
				+ invoiceNumberGenerationSequence.getChallanNumberSequence();
24226 amit.gupta 655
	}
656
 
23650 amit.gupta 657
	private Set<String> serialNumberDetailsToSerialNumbers(Set<SerialNumberDetail> serialNumberDetails) {
23377 ashik.ali 658
		Set<String> serialNumbers = new HashSet<>();
23650 amit.gupta 659
		for (SerialNumberDetail serialNumberDetail : serialNumberDetails) {
660
			if (serialNumberDetail.getSerialNumber() != null && !serialNumberDetail.getSerialNumber().isEmpty()) {
23377 ashik.ali 661
				serialNumbers.add(serialNumberDetail.getSerialNumber());
662
			}
663
		}
664
		return serialNumbers;
665
	}
23650 amit.gupta 666
 
22859 ashik.ali 667
	@Override
23596 ashik.ali 668
	public PdfModel getInvoicePdfModel(int orderId) throws ProfitMandiBusinessException {
669
		FofoOrder fofoOrder = fofoOrderRepository.selectByOrderId(orderId);
670
		return this.getInvoicePdfModel(fofoOrder);
671
	}
23650 amit.gupta 672
 
673
	private PdfModel getInvoicePdfModel(FofoOrder fofoOrder) throws ProfitMandiBusinessException {
674
 
675
		List<PaymentOptionTransaction> paymentOptionTransactions = paymentOptionTransactionRepository
676
				.selectByReferenceIdAndType(fofoOrder.getId(), PaymentOptionReferenceType.ORDER);
677
 
23552 amit.gupta 678
		List<CustomPaymentOption> paymentOptions = new ArrayList<>();
679
 
22859 ashik.ali 680
		PdfModel pdfModel = new PdfModel();
24823 amit.gupta 681
		pdfModel.setCancelled(fofoOrder.getCancelledTimestamp() != null);
23650 amit.gupta 682
		for (PaymentOptionTransaction paymentOptionTransaction : paymentOptionTransactions) {
23552 amit.gupta 683
			CustomPaymentOption cpi = new CustomPaymentOption();
684
			cpi.setAmount(paymentOptionTransaction.getAmount());
23650 amit.gupta 685
			cpi.setPaymentOption(
686
					paymentOptionRepository.selectById(paymentOptionTransaction.getPaymentOptionId()).getName());
23558 amit.gupta 687
			paymentOptions.add(cpi);
23552 amit.gupta 688
		}
24215 amit.gupta 689
		List<FofoOrderItem> fofoOrderItems = this.getByOrderId(fofoOrder.getId());
690
 
691
		pdfModel.setTitle("Retailer Invoice");
24275 amit.gupta 692
		if (fofoOrderItems.stream().findAny().get().getHsnCode().equals("NOGST")) {
24215 amit.gupta 693
			pdfModel.setTitle("Security Deposit Receipt");
694
		}
23552 amit.gupta 695
		pdfModel.setPaymentOptions(paymentOptions);
24215 amit.gupta 696
		pdfModel.setAuther("SmartDukaan");
24400 amit.gupta 697
		pdfModel.setInvoiceDate(FormattingUtils.formatDate(fofoOrder.getCreateTimestamp()));
23650 amit.gupta 698
 
22859 ashik.ali 699
		// insurance calculation
23650 amit.gupta 700
		List<InsurancePolicy> insurancePolicies = insurancePolicyRepository
701
				.selectByRetailerIdInvoiceNumber(fofoOrder.getFofoId(), fofoOrder.getInvoiceNumber());
22859 ashik.ali 702
		Set<CustomInsurancePolicy> customInsurancePolicies = new HashSet<>();
703
		final float totalInsuranceTaxRate = 18;
23650 amit.gupta 704
		for (InsurancePolicy insurancePolicy : insurancePolicies) {
22859 ashik.ali 705
			float taxableInsurancePrice = insurancePolicy.getSaleAmount() / (1 + totalInsuranceTaxRate / 100);
706
			CustomInsurancePolicy customInsurancePolicy = new CustomInsurancePolicy();
23650 amit.gupta 707
			customInsurancePolicy.setDescription("Damage Protection Plan for device IMEI #"
708
					+ insurancePolicy.getSerialNumber() + "\n Certificate No. " + insurancePolicy.getPolicyNumber());
22859 ashik.ali 709
			customInsurancePolicy.setHsnCode("998716");
710
			customInsurancePolicy.setRate(taxableInsurancePrice);
711
			customInsurancePolicy.setIgstRate(18);
23650 amit.gupta 712
			customInsurancePolicy.setIgstAmount(taxableInsurancePrice * 18 / 100);
22936 amit.gupta 713
			customInsurancePolicy.setCgstRate(9);
23650 amit.gupta 714
			customInsurancePolicy.setCgstAmount(taxableInsurancePrice * 9 / 100);
22859 ashik.ali 715
			customInsurancePolicy.setSgstRate(9);
23650 amit.gupta 716
			customInsurancePolicy.setSgstAmount(taxableInsurancePrice * 9 / 100);
22859 ashik.ali 717
			customInsurancePolicy.setNetAmount(insurancePolicy.getSaleAmount());
718
			customInsurancePolicies.add(customInsurancePolicy);
719
		}
720
		pdfModel.setInsurancePolicies(customInsurancePolicies);
23001 amit.gupta 721
		List<String> tncs = new ArrayList<>();
722
		tncs.add("I agree that goods received are in good working condition");
723
		tncs.add("Goods once sold cannot be exchanged or taken back");
724
		tncs.add("Warranty for the goods received by me is the responsibility of the manufacturer only.");
23650 amit.gupta 725
		if (pdfModel.getInsurancePolicies() != null && pdfModel.getInsurancePolicies().size() > 0) {
726
			tncs.add("Damage protection provided is the responisibility of Protection Provider only");
727
		}
23001 amit.gupta 728
		pdfModel.setTncs(tncs);
24275 amit.gupta 729
 
23655 amit.gupta 730
		pdfModel.setCustomer(getCustomCustomer(fofoOrder));
22859 ashik.ali 731
		pdfModel.setInvoiceNumber(fofoOrder.getInvoiceNumber());
732
		pdfModel.setTotalAmount(fofoOrder.getTotalAmount());
23650 amit.gupta 733
 
23596 ashik.ali 734
		Retailer retailer = retailerRepository.selectById(fofoOrder.getFofoId());
22859 ashik.ali 735
		PrivateDealUser privateDealUser = null;
23650 amit.gupta 736
		try {
22859 ashik.ali 737
			privateDealUser = privateDealUserRepository.selectById(retailer.getId());
23650 amit.gupta 738
		} catch (ProfitMandiBusinessException profitMandiBusinessException) {
22859 ashik.ali 739
			LOGGER.error("Private Deal User not found : ", profitMandiBusinessException);
740
		}
23650 amit.gupta 741
 
22859 ashik.ali 742
		User user = userRepository.selectById(userAccountRepository.selectUserIdByRetailerId(retailer.getId()));
743
		CustomRetailer customRetailer = new CustomRetailer();
744
		customRetailer.setBusinessName(retailer.getName());
745
		customRetailer.setMobileNumber(user.getMobileNumber());
23650 amit.gupta 746
		// customRetailer.setTinNumber(retailer.getNumber());
747
		if (privateDealUser == null) {
22859 ashik.ali 748
			customRetailer.setGstNumber(null);
23650 amit.gupta 749
		} else {
750
			if (null != privateDealUser.getCounterId()) {
22859 ashik.ali 751
				Counter counter = counterRepository.selectById(privateDealUser.getCounterId());
752
				customRetailer.setGstNumber(counter.getGstin());
23650 amit.gupta 753
			} else {
22859 ashik.ali 754
				customRetailer.setGstNumber(null);
755
			}
756
		}
23650 amit.gupta 757
		Address retailerAddress = addressRepository
758
				.selectById(retailerRegisteredAddressRepository.selectAddressIdByRetailerId(retailer.getId()));
22859 ashik.ali 759
		customRetailer.setAddress(this.createCustomAddress(retailerAddress));
760
		pdfModel.setRetailer(customRetailer);
23650 amit.gupta 761
 
22859 ashik.ali 762
		Set<CustomOrderItem> customerFofoOrderItems = new HashSet<>();
23650 amit.gupta 763
		for (FofoOrderItem fofoOrderItem : fofoOrderItems) {
22859 ashik.ali 764
			CustomOrderItem customFofoOrderItem = new CustomOrderItem();
23650 amit.gupta 765
			float totalTaxRate = fofoOrderItem.getIgstRate() + fofoOrderItem.getSgstRate()
766
					+ fofoOrderItem.getCgstRate();
22859 ashik.ali 767
			float taxableSellingPrice = fofoOrderItem.getSellingPrice() / (1 + totalTaxRate / 100);
768
			float taxableDiscountPrice = fofoOrderItem.getDiscount() / (1 + totalTaxRate / 100);
23650 amit.gupta 769
 
22859 ashik.ali 770
			customFofoOrderItem.setAmount(fofoOrderItem.getQuantity() * (taxableSellingPrice - taxableDiscountPrice));
23650 amit.gupta 771
			customFofoOrderItem.setDescription(fofoOrderItem.getBrand() + " " + fofoOrderItem.getModelName() + " "
772
					+ fofoOrderItem.getModelNumber() + "-" + fofoOrderItem.getColor());
23377 ashik.ali 773
			Set<String> serialNumbers = this.toSerialNumbers(fofoOrderItem.getFofoLineItems());
23650 amit.gupta 774
			// LOGGER.info("serialNumbers {}", serialNumbers);
775
			// LOGGER.info("serialNumbers is empty {}", serialNumbers.isEmpty());
776
			if (!serialNumbers.isEmpty()) {
777
				customFofoOrderItem.setDescription(
778
						customFofoOrderItem.getDescription() + "\n IMEIS - " + String.join(", ", serialNumbers));
23377 ashik.ali 779
			}
22859 ashik.ali 780
			customFofoOrderItem.setRate(taxableSellingPrice);
781
			customFofoOrderItem.setDiscount(taxableDiscountPrice);
782
			customFofoOrderItem.setQuantity(fofoOrderItem.getQuantity());
23650 amit.gupta 783
			customFofoOrderItem.setNetAmount(
784
					(fofoOrderItem.getSellingPrice() - fofoOrderItem.getDiscount()) * fofoOrderItem.getQuantity());
22859 ashik.ali 785
			float igstAmount = (customFofoOrderItem.getAmount() * fofoOrderItem.getIgstRate()) / 100;
786
			float cgstAmount = (customFofoOrderItem.getAmount() * fofoOrderItem.getCgstRate()) / 100;
787
			float sgstAmount = (customFofoOrderItem.getAmount() * fofoOrderItem.getSgstRate()) / 100;
788
			customFofoOrderItem.setIgstRate(fofoOrderItem.getIgstRate());
789
			customFofoOrderItem.setIgstAmount(igstAmount);
790
			customFofoOrderItem.setCgstRate(fofoOrderItem.getCgstRate());
791
			customFofoOrderItem.setCgstAmount(cgstAmount);
792
			customFofoOrderItem.setSgstRate(fofoOrderItem.getSgstRate());
793
			customFofoOrderItem.setSgstAmount(sgstAmount);
794
			customFofoOrderItem.setHsnCode(fofoOrderItem.getHsnCode());
795
			customerFofoOrderItems.add(customFofoOrderItem);
796
		}
797
		pdfModel.setOrderItems(customerFofoOrderItems);
24917 tejbeer 798
		String partnerAddressStateCode = stateRepository.selectByName(pdfModel.getRetailer().getAddress().getState())
799
				.getCode();
800
		String customerAddressStateCode = stateRepository.selectByName(pdfModel.getCustomer().getAddress().getState())
801
				.getCode();
24854 amit.gupta 802
		pdfModel.setPartnerAddressStateCode(partnerAddressStateCode);
803
		pdfModel.setCustomerAddressStateCode(customerAddressStateCode);
22859 ashik.ali 804
		return pdfModel;
23650 amit.gupta 805
 
22859 ashik.ali 806
	}
23650 amit.gupta 807
 
23655 amit.gupta 808
	private CustomCustomer getCustomCustomer(FofoOrder fofoOrder) throws ProfitMandiBusinessException {
809
		Customer customer = customerRepository.selectById(fofoOrder.getCustomerId());
810
		CustomCustomer customCustomer = new CustomCustomer();
811
		customCustomer.setFirstName(customer.getFirstName());
812
		customCustomer.setLastName(customer.getLastName());
813
		customCustomer.setEmailId(customer.getEmailId());
814
		customCustomer.setMobileNumber(customer.getMobileNumber());
815
		customCustomer.setGstNumber(fofoOrder.getCustomerGstNumber());
816
		CustomerAddress customerAddress = customerAddressRepository.selectById(fofoOrder.getCustomerAddressId());
817
		customCustomer.setAddress(this.createCustomAddress(customerAddress));
818
		return customCustomer;
819
	}
820
 
23596 ashik.ali 821
	@Override
822
	public PdfModel getInvoicePdfModel(int fofoId, int orderId) throws ProfitMandiBusinessException {
823
		FofoOrder fofoOrder = fofoOrderRepository.selectByFofoIdAndOrderId(fofoId, orderId);
824
		return this.getInvoicePdfModel(fofoOrder);
825
	}
23650 amit.gupta 826
 
22859 ashik.ali 827
	public String getBillingAddress(CustomerAddress customerAddress) {
828
		StringBuilder address = new StringBuilder();
829
		if ((customerAddress.getLine1() != null) && (!customerAddress.getLine1().isEmpty())) {
830
			address.append(customerAddress.getLine1());
831
			address.append(", ");
832
		}
833
 
834
		if ((customerAddress.getLine2() != null) && (!customerAddress.getLine2().isEmpty())) {
835
			address.append(customerAddress.getLine2());
836
			address.append(", ");
837
		}
838
 
839
		if ((customerAddress.getLandmark() != null) && (!customerAddress.getLandmark().isEmpty())) {
840
			address.append(customerAddress.getLandmark());
841
			address.append(", ");
842
		}
843
 
844
		if ((customerAddress.getCity() != null) && (!customerAddress.getCity().isEmpty())) {
845
			address.append(customerAddress.getCity());
846
			address.append(", ");
847
		}
848
 
849
		if ((customerAddress.getState() != null) && (!customerAddress.getState().isEmpty())) {
850
			address.append(customerAddress.getState());
851
		}
852
 
853
		if ((customerAddress.getPinCode() != null) && (!customerAddress.getPinCode().isEmpty())) {
854
			address.append("- ");
855
			address.append(customerAddress.getPinCode());
856
		}
857
 
858
		return address.toString();
859
	}
23650 amit.gupta 860
 
22859 ashik.ali 861
	@Override
23650 amit.gupta 862
	public List<CartFofo> cartCheckout(String cartJson) throws ProfitMandiBusinessException {
863
		try {
22859 ashik.ali 864
			JSONObject cartObject = new JSONObject(cartJson);
865
			Iterator<?> keys = cartObject.keys();
23650 amit.gupta 866
 
22859 ashik.ali 867
			Set<Integer> itemIds = new HashSet<>();
868
			List<CartFofo> cartItems = new ArrayList<CartFofo>();
23650 amit.gupta 869
 
870
			while (keys.hasNext()) {
871
				String key = (String) keys.next();
872
				if (cartObject.get(key) instanceof JSONObject) {
22859 ashik.ali 873
					LOGGER.info(cartObject.get(key).toString());
874
				}
875
				CartFofo cf = new CartFofo();
876
				cf.setItemId(cartObject.getJSONObject(key).getInt("itemId"));
877
				cf.setQuantity(cartObject.getJSONObject(key).getInt("quantity"));
23650 amit.gupta 878
 
879
				if (cf.getQuantity() <= 0) {
22859 ashik.ali 880
					continue;
881
				}
882
				cartItems.add(cf);
883
				itemIds.add(cartObject.getJSONObject(key).getInt("itemId"));
884
			}
23650 amit.gupta 885
			Map<Integer, Item> itemMap = new HashMap<Integer, Item>();
886
			if (itemIds.size() > 0) {
22859 ashik.ali 887
				List<Item> items = itemRepository.selectByIds(itemIds);
23650 amit.gupta 888
				for (Item i : items) {
22859 ashik.ali 889
					itemMap.put(i.getId(), i);
890
				}
23650 amit.gupta 891
 
22859 ashik.ali 892
			}
23650 amit.gupta 893
			for (CartFofo cf : cartItems) {
22859 ashik.ali 894
				Item i = itemMap.get(cf.getItemId());
23650 amit.gupta 895
				if (i == null) {
22859 ashik.ali 896
					continue;
897
				}
23650 amit.gupta 898
				cf.setDisplayName(getValidName(i.getBrand()) + " " + getValidName(i.getModelName()) + " "
899
						+ getValidName(i.getModelNumber()) + " " + getValidName(i.getColor()).replaceAll("\\s+", " "));
22859 ashik.ali 900
				cf.setItemType(i.getType());
901
			}
902
			return cartItems;
23650 amit.gupta 903
		} catch (Exception e) {
22859 ashik.ali 904
			LOGGER.error("Unable to Prepare cart to place order...", e);
22925 ashik.ali 905
			throw new ProfitMandiBusinessException("cartData", cartJson, "FFORDR_1006");
22859 ashik.ali 906
		}
907
	}
23650 amit.gupta 908
 
23202 ashik.ali 909
	@Override
23650 amit.gupta 910
	public Map<String, Object> getSaleHistory(int fofoId, SearchType searchType, String searchValue,
23891 amit.gupta 911
			LocalDateTime startDate, LocalDateTime endDate, int offset, int limit) throws ProfitMandiBusinessException {
23202 ashik.ali 912
		long countItems = 0;
913
		List<FofoOrder> fofoOrders = new ArrayList<>();
23650 amit.gupta 914
 
915
		if (searchType == SearchType.CUSTOMER_MOBILE_NUMBER && !searchValue.isEmpty()) {
24275 amit.gupta 916
			fofoOrders = fofoOrderRepository.selectByFofoIdAndCustomerMobileNumber(fofoId, searchValue, null, null,
917
					offset, limit);
918
			countItems = fofoOrderRepository.selectCountByCustomerMobileNumber(fofoId, searchValue, null, null);
23650 amit.gupta 919
		} else if (searchType == SearchType.CUSTOMER_NAME && !searchValue.isEmpty()) {
24275 amit.gupta 920
			fofoOrders = fofoOrderRepository.selectByFofoIdAndCustomerName(fofoId, searchValue, null, null, offset,
921
					limit);
23973 govind 922
			countItems = fofoOrderRepository.selectCountByCustomerName(fofoId, searchValue, null, null);
23650 amit.gupta 923
		} else if (searchType == SearchType.IMEI && !searchValue.isEmpty()) {
24275 amit.gupta 924
			fofoOrders = fofoOrderRepository.selectByFofoIdAndSerialNumber(fofoId, searchValue, null, null, offset,
925
					limit);
23973 govind 926
			countItems = fofoOrderRepository.selectCountBySerialNumber(fofoId, searchValue, null, null);
23650 amit.gupta 927
		} else if (searchType == SearchType.ITEM_NAME && !searchValue.isEmpty()) {
24275 amit.gupta 928
			fofoOrders = fofoOrderRepository.selectByFofoIdAndItemName(fofoId, searchValue, null, null, offset, limit);
929
			countItems = fofoOrderRepository.selectCountByItemName(fofoId, searchValue, null, null);
23953 amit.gupta 930
		} else if (searchType == SearchType.INVOICE_NUMBER && !searchValue.isEmpty()) {
931
			fofoOrders = Arrays.asList(fofoOrderRepository.selectByFofoIdAndInvoiceNumber(fofoId, searchValue));
932
			countItems = fofoOrders.size();
24275 amit.gupta 933
		} else if (searchType == SearchType.DATE_RANGE) {
23891 amit.gupta 934
			fofoOrders = fofoOrderRepository.selectByFofoId(fofoId, startDate, endDate, offset, limit);
935
			countItems = fofoOrderRepository.selectCountByFofoId(fofoId, startDate, endDate);
23202 ashik.ali 936
		}
937
		Map<String, Object> map = new HashMap<>();
23650 amit.gupta 938
 
23202 ashik.ali 939
		map.put("saleHistories", fofoOrders);
940
		map.put("start", offset + 1);
941
		map.put("size", countItems);
942
		map.put("searchType", searchType);
23351 ashik.ali 943
		map.put("searchTypes", SearchType.values());
23891 amit.gupta 944
		map.put("startDate", startDate);
23973 govind 945
		map.put("searchValue", searchValue);
23891 amit.gupta 946
		map.put(ProfitMandiConstants.END_TIME, endDate);
23650 amit.gupta 947
		if (fofoOrders.size() < limit) {
23202 ashik.ali 948
			map.put("end", offset + fofoOrders.size());
23650 amit.gupta 949
		} else {
23202 ashik.ali 950
			map.put("end", offset + limit);
951
		}
952
		return map;
953
	}
954
 
955
	@Override
23650 amit.gupta 956
	public Map<String, Object> getSaleHistoryPaginated(int fofoId, SearchType searchType, String searchValue,
23891 amit.gupta 957
			LocalDateTime startDate, LocalDateTime endDate, int offset, int limit) throws ProfitMandiBusinessException {
23202 ashik.ali 958
		List<FofoOrder> fofoOrders = new ArrayList<>();
23650 amit.gupta 959
 
960
		if (searchType == SearchType.CUSTOMER_MOBILE_NUMBER && !searchValue.isEmpty()) {
23891 amit.gupta 961
			fofoOrders = fofoOrderRepository.selectByFofoIdAndCustomerMobileNumber(fofoId, searchValue, startDate,
962
					endDate, offset, limit);
23650 amit.gupta 963
		} else if (searchType == SearchType.CUSTOMER_NAME && !searchValue.isEmpty()) {
24275 amit.gupta 964
			fofoOrders = fofoOrderRepository.selectByFofoIdAndCustomerName(fofoId, searchValue, startDate, endDate,
965
					offset, limit);
23650 amit.gupta 966
		} else if (searchType == SearchType.IMEI && !searchValue.isEmpty()) {
24275 amit.gupta 967
			fofoOrders = fofoOrderRepository.selectByFofoIdAndSerialNumber(fofoId, searchValue, startDate, endDate,
968
					offset, limit);
23650 amit.gupta 969
		} else if (searchType == SearchType.ITEM_NAME && !searchValue.isEmpty()) {
24275 amit.gupta 970
			fofoOrders = fofoOrderRepository.selectByFofoIdAndItemName(fofoId, searchValue, startDate, endDate, offset,
971
					limit);
972
 
973
		} else if (searchType == SearchType.DATE_RANGE) {
23891 amit.gupta 974
			fofoOrders = fofoOrderRepository.selectByFofoId(fofoId, startDate, endDate, offset, limit);
23202 ashik.ali 975
		}
976
		Map<String, Object> map = new HashMap<>();
977
		map.put("saleHistories", fofoOrders);
23973 govind 978
		map.put("searchType", searchType);
979
		map.put("searchTypes", SearchType.values());
980
		map.put("startDate", startDate);
981
		map.put("searchValue", searchValue);
982
		map.put(ProfitMandiConstants.END_TIME, endDate);
23202 ashik.ali 983
		return map;
984
	}
23650 amit.gupta 985
 
986
	private String getFofoStoreCode(int fofoId) throws ProfitMandiBusinessException {
23202 ashik.ali 987
		FofoStore fofoStore = fofoStoreRepository.selectByRetailerId(fofoId);
23370 ashik.ali 988
		return fofoStore.getCode();
23202 ashik.ali 989
	}
23650 amit.gupta 990
 
991
	private CustomerAddress createCustomerAddress(CustomAddress customAddress, int customerId) {
23191 ashik.ali 992
		CustomerAddress customerAddress = null;
23650 amit.gupta 993
		try {
994
			// CustomAddress customAddress = customCustomer.getAddress();
995
			customerAddress = customerAddressRepository.selectByParams(customAddress.getName(),
996
					customAddress.getLine1(), customAddress.getLine2(), customAddress.getLandmark(),
997
					customAddress.getCity(), customAddress.getPinCode(), customAddress.getState(),
998
					customAddress.getPhoneNumber(), customAddress.getCountry(), customerId);
999
		} catch (ProfitMandiBusinessException profitMandiBusinessException) {
23596 ashik.ali 1000
			LOGGER.warn("Customer address not found with [{}]", customAddress);
23191 ashik.ali 1001
			customerAddress = new CustomerAddress();
1002
			this.setCustomerAddress(customerAddress, customAddress);
1003
			customerAddress.setCustomerId(customerId);
24466 amit.gupta 1004
			customerAddressRepository.persist(customerAddress);
23191 ashik.ali 1005
		}
1006
		return customerAddress;
1007
	}
23650 amit.gupta 1008
 
1009
	private String getValidName(String name) {
1010
		return name != null ? name : "";
22859 ashik.ali 1011
	}
23650 amit.gupta 1012
 
1013
	private Set<String> toSerialNumbers(Set<FofoLineItem> fofoLineItems) {
23377 ashik.ali 1014
		Set<String> serialNumbers = new HashSet<>();
23650 amit.gupta 1015
		for (FofoLineItem fofoLineItem : fofoLineItems) {
1016
			if (fofoLineItem.getSerialNumber() != null && !fofoLineItem.getSerialNumber().isEmpty()) {
23377 ashik.ali 1017
				serialNumbers.add(fofoLineItem.getSerialNumber());
22955 ashik.ali 1018
			}
23377 ashik.ali 1019
		}
1020
		return serialNumbers;
22859 ashik.ali 1021
	}
23650 amit.gupta 1022
 
1023
	private PolicyNumberGenerationSequence createPolicyNumberGenerationSequence() {
22859 ashik.ali 1024
		PolicyNumberGenerationSequence policyNumberGenerationSequence = null;
23650 amit.gupta 1025
		try {
22859 ashik.ali 1026
			policyNumberGenerationSequence = policyNumberGenerationSequenceRepository.select();
1027
			policyNumberGenerationSequence.setSequence(policyNumberGenerationSequence.getSequence() + 1);
1028
			policyNumberGenerationSequenceRepository.persist(policyNumberGenerationSequence);
23650 amit.gupta 1029
		} catch (ProfitMandiBusinessException profitMandiBusinessException) {
22859 ashik.ali 1030
			policyNumberGenerationSequence = new PolicyNumberGenerationSequence();
1031
			policyNumberGenerationSequence.setSequence(1);
1032
			policyNumberGenerationSequenceRepository.persist(policyNumberGenerationSequence);
1033
		}
1034
		return policyNumberGenerationSequence;
1035
	}
23650 amit.gupta 1036
 
1037
	private GadgetCopsInsuranceModel createGadgetCopsInsuranceModel(String brand, String modelName, String serialNumber,
1038
			LocalDate customerDateOfBirth, Customer customer, CustomerAddress customerAddress,
1039
			InsurancePolicy insurancePolicy) {
22859 ashik.ali 1040
		GadgetCopsInsuranceModel gadgetCopsInsuranceModel = new GadgetCopsInsuranceModel();
1041
		gadgetCopsInsuranceModel.setBrand(brand);
1042
		gadgetCopsInsuranceModel.setModelName(modelName);
1043
		gadgetCopsInsuranceModel.setSerialNumber(serialNumber);
1044
		gadgetCopsInsuranceModel.setCustomerFirstName(customer.getFirstName());
1045
		gadgetCopsInsuranceModel.setCustomerLastName(customer.getLastName());
1046
		gadgetCopsInsuranceModel.setCustomerDateOfBirth(customerDateOfBirth);
1047
		gadgetCopsInsuranceModel.setCustomerMobileNumber(customer.getMobileNumber());
1048
		gadgetCopsInsuranceModel.setCustomerEmailId(customer.getEmailId());
1049
		gadgetCopsInsuranceModel.setCustomerAddress1(customerAddress.getLine1());
1050
		gadgetCopsInsuranceModel.setCustomerAddress2(customerAddress.getLine2());
1051
		gadgetCopsInsuranceModel.setCustomerCity(customerAddress.getCity());
1052
		gadgetCopsInsuranceModel.setCustomerPinCode(customerAddress.getPinCode());
1053
		gadgetCopsInsuranceModel.setCustomerState(customerAddress.getState());
1054
		gadgetCopsInsuranceModel.setPrice(insurancePolicy.getSellingPrice());
1055
		gadgetCopsInsuranceModel.setInvoiceNumber(insurancePolicy.getInvoiceNumber());
1056
		gadgetCopsInsuranceModel.setPolicyNumber(insurancePolicy.getPolicyNumber());
1057
		return gadgetCopsInsuranceModel;
1058
	}
23650 amit.gupta 1059
 
1060
	private InsurancePolicy createInsurancePolicy(String invoiceNumber, int retailerId, float purchaseAmount,
1061
			float saleAmount, float sellingPrice, String serialNumber, String modelName, String brand,
24440 amit.gupta 1062
			Customer customer, LocalDate customerDateOfBirth, CustomerAddress customerAddress, String productName) {
22859 ashik.ali 1063
		InsurancePolicy insurancePolicy = new InsurancePolicy();
23394 amit.gupta 1064
		insurancePolicy.setInvoiceNumber(invoiceNumber);
22859 ashik.ali 1065
		insurancePolicy.setRetailerId(retailerId);
1066
		insurancePolicy.setPurchaseAmount(purchaseAmount);
1067
		insurancePolicy.setSaleAmount(saleAmount);
1068
		insurancePolicy.setSellingPrice(sellingPrice);
1069
		insurancePolicy.setSerialNumber(serialNumber);
1070
		insurancePolicy.setModelName(modelName);
1071
		insurancePolicy.setBrand(brand);
1072
		insurancePolicy.setCustomerFirstName(customer.getFirstName());
1073
		insurancePolicy.setCustomerLastName(customer.getLastName());
1074
		insurancePolicy.setCustomerMobileNumber(customer.getMobileNumber());
1075
		insurancePolicy.setCustomerEmailId(customer.getEmailId());
1076
		insurancePolicy.setCustomerDateOfBirth(customerDateOfBirth);
1077
		insurancePolicy.setCustomerAddress1(customerAddress.getLine1());
1078
		insurancePolicy.setCustomerAddress2(customerAddress.getLine2());
1079
		insurancePolicy.setCustomerCity(customerAddress.getCity());
1080
		insurancePolicy.setCustomerPinCode(customerAddress.getPinCode());
1081
		insurancePolicy.setCustomerState(customerAddress.getState());
24440 amit.gupta 1082
		insurancePolicy.setProductName(productName);
22859 ashik.ali 1083
		return insurancePolicy;
1084
	}
23650 amit.gupta 1085
 
23823 amit.gupta 1086
	private void validateDpPrice(Map<Integer, PriceModel> itemIdMopPriceMap,
1087
			Map<Integer, CustomFofoOrderItem> itemIdCustomFofoLineItemMap) throws ProfitMandiBusinessException {
1088
		for (Map.Entry<Integer, CustomFofoOrderItem> entry : itemIdCustomFofoLineItemMap.entrySet()) {
1089
			int itemId = entry.getKey();
1090
			CustomFofoOrderItem customFofoOrderItem = entry.getValue();
1091
			PriceModel priceModel = itemIdMopPriceMap.get(itemId);
25494 amit.gupta 1092
			if (customFofoOrderItem.getSerialNumberDetails().stream()
25499 amit.gupta 1093
					.filter(x -> org.apache.commons.lang.StringUtils.isNotEmpty(x.getSerialNumber()))
25494 amit.gupta 1094
					.collect(Collectors.toList()).size() > 0) {
24275 amit.gupta 1095
				if (priceModel.getPrice() > customFofoOrderItem.getSellingPrice()) {
25495 amit.gupta 1096
					throw new ProfitMandiBusinessException("Selling Price for ",
24275 amit.gupta 1097
							itemRepository.selectById(itemId).getItemDescription(), "FFORDR_1010");
23823 amit.gupta 1098
				}
1099
			} else {
24275 amit.gupta 1100
				if (priceModel.getPurchasePrice() > customFofoOrderItem.getSellingPrice()) {
1101
					throw new ProfitMandiBusinessException("Selling Price",
1102
							itemRepository.selectById(itemId).getItemDescription(),
1103
							"Selling Price should not be less than DP");
23823 amit.gupta 1104
				}
1105
			}
1106
		}
1107
	}
24275 amit.gupta 1108
 
23650 amit.gupta 1109
	private void validateMopPrice(Map<Integer, PriceModel> itemIdMopPriceMap,
1110
			Map<Integer, CustomFofoOrderItem> itemIdCustomFofoLineItemMap) throws ProfitMandiBusinessException {
22859 ashik.ali 1111
		Map<Integer, Float> invalidMopItemIdPriceMap = new HashMap<>();
23650 amit.gupta 1112
		for (Map.Entry<Integer, PriceModel> entry : itemIdMopPriceMap.entrySet()) {
22872 ashik.ali 1113
			CustomFofoOrderItem customFofoOrderItem = itemIdCustomFofoLineItemMap.get(entry.getKey());
25102 amit.gupta 1114
			if (customFofoOrderItem.getSellingPrice() < entry.getValue().getPrice()) {
22872 ashik.ali 1115
				invalidMopItemIdPriceMap.put(entry.getKey(), customFofoOrderItem.getSellingPrice());
22859 ashik.ali 1116
			}
1117
		}
23650 amit.gupta 1118
 
1119
		if (!invalidMopItemIdPriceMap.isEmpty()) {
1120
			LOGGER.error("Invalid itemIds selling prices{} should be greater than mop prices {}",
1121
					invalidMopItemIdPriceMap, itemIdMopPriceMap);
22925 ashik.ali 1122
			throw new ProfitMandiBusinessException("invalidMopItemIdPrice", invalidMopItemIdPriceMap, "FFORDR_1010");
22859 ashik.ali 1123
		}
23650 amit.gupta 1124
 
22859 ashik.ali 1125
	}
23650 amit.gupta 1126
 
1127
	private void updateInventoryItemsAndScanRecord(Set<InventoryItem> inventoryItems, int fofoId,
24264 amit.gupta 1128
			Map<Integer, Integer> inventoryItemQuantityUsed, int fofoOrderId) {
23650 amit.gupta 1129
		for (InventoryItem inventoryItem : inventoryItems) {
22859 ashik.ali 1130
			inventoryItem.setLastScanType(ScanType.SALE);
1131
			inventoryItemRepository.persist(inventoryItem);
1132
			ScanRecord scanRecord = new ScanRecord();
1133
			scanRecord.setInventoryItemId(inventoryItem.getId());
1134
			scanRecord.setFofoId(fofoId);
24264 amit.gupta 1135
			scanRecord.setOrderId(fofoOrderId);
23650 amit.gupta 1136
			// correct this
22859 ashik.ali 1137
			scanRecord.setQuantity(inventoryItemQuantityUsed.get(inventoryItem.getId()));
1138
			scanRecord.setType(ScanType.SALE);
1139
			scanRecordRepository.persist(scanRecord);
23566 amit.gupta 1140
			purchaseReturnItemRepository.deleteById(inventoryItem.getId());
23650 amit.gupta 1141
 
22859 ashik.ali 1142
		}
1143
	}
23650 amit.gupta 1144
 
1145
	private void createFofoLineItem(int fofoOrderItemId, Set<InventoryItem> inventoryItems,
1146
			Map<Integer, Integer> inventoryItemIdQuantityUsed) {
1147
		for (InventoryItem inventoryItem : inventoryItems) {
22859 ashik.ali 1148
			FofoLineItem fofoLineItem = new FofoLineItem();
1149
			fofoLineItem.setFofoOrderItemId(fofoOrderItemId);
1150
			fofoLineItem.setSerialNumber(inventoryItem.getSerialNumber());
1151
			fofoLineItem.setInventoryItemId(inventoryItem.getId());
1152
			fofoLineItem.setQuantity(inventoryItemIdQuantityUsed.get(inventoryItem.getId()));
1153
			fofoLineItemRepository.persist(fofoLineItem);
1154
		}
1155
	}
23650 amit.gupta 1156
 
1157
	private FofoOrderItem createAndGetFofoOrderItem(CustomFofoOrderItem customFofoOrderItem, int fofoOrderId,
1158
			Map<Integer, Item> itemMap, Set<InventoryItem> inventoryItems, Integer stateId)
1159
			throws ProfitMandiBusinessException {
22859 ashik.ali 1160
		FofoOrderItem fofoOrderItem = new FofoOrderItem();
1161
		fofoOrderItem.setItemId(customFofoOrderItem.getItemId());
1162
		fofoOrderItem.setQuantity(customFofoOrderItem.getQuantity());
1163
		fofoOrderItem.setSellingPrice(customFofoOrderItem.getSellingPrice());
1164
		fofoOrderItem.setOrderId(fofoOrderId);
25103 amit.gupta 1165
		TagListing tl = tagListingRepository.selectByItemId(customFofoOrderItem.getItemId());
25162 amit.gupta 1166
		// In case listing gets removed rebill it using the selling price
1167
		if (tl != null) {
25103 amit.gupta 1168
			fofoOrderItem.setDp(tl.getSellingPrice());
1169
		} else {
1170
			fofoOrderItem.setDp(customFofoOrderItem.getSellingPrice());
1171
		}
22859 ashik.ali 1172
		fofoOrderItem.setDiscount(customFofoOrderItem.getDiscountAmount());
24823 amit.gupta 1173
 
22859 ashik.ali 1174
		Item item = itemMap.get(customFofoOrderItem.getItemId());
23172 ashik.ali 1175
		Map<Integer, GstRate> itemIdStateTaxRateMap = null;
1176
		Map<Integer, Float> itemIdIgstTaxRateMap = null;
23650 amit.gupta 1177
		if (stateId != null) {
23172 ashik.ali 1178
			itemIdStateTaxRateMap = Utils.getStateTaxRate(new ArrayList<>(itemMap.keySet()), stateId);
23650 amit.gupta 1179
		} else {
23172 ashik.ali 1180
			itemIdIgstTaxRateMap = Utils.getIgstTaxRate(new ArrayList<>(itemMap.keySet()));
1181
		}
23650 amit.gupta 1182
		for (InventoryItem inventoryItem : inventoryItems) {
1183
			if (stateId == null) {
23172 ashik.ali 1184
				fofoOrderItem.setIgstRate(itemIdIgstTaxRateMap.get(inventoryItem.getItemId()));
23650 amit.gupta 1185
			} else {
23172 ashik.ali 1186
				fofoOrderItem.setCgstRate(itemIdStateTaxRateMap.get(inventoryItem.getItemId()).getCgstRate());
1187
				fofoOrderItem.setSgstRate(itemIdStateTaxRateMap.get(inventoryItem.getItemId()).getSgstRate());
1188
			}
23650 amit.gupta 1189
 
22859 ashik.ali 1190
			fofoOrderItem.setHsnCode(inventoryItem.getHsnCode());
1191
			break;
1192
		}
1193
		fofoOrderItem.setBrand(item.getBrand());
1194
		fofoOrderItem.setModelName(item.getModelName());
1195
		fofoOrderItem.setModelNumber(item.getModelNumber());
1196
		fofoOrderItem.setColor(item.getColor());
1197
		fofoOrderItemRepository.persist(fofoOrderItem);
1198
		return fofoOrderItem;
1199
	}
23650 amit.gupta 1200
 
1201
	private void updateCurrentInventorySnapshot(List<CurrentInventorySnapshot> currentInventorySnapshots, int fofoId,
1202
			int itemId, int quantity) throws ProfitMandiBusinessException {
1203
		for (CurrentInventorySnapshot currentInventorySnapshot : currentInventorySnapshots) {
1204
			if (currentInventorySnapshot.getItemId() == itemId && currentInventorySnapshot.getFofoId() == fofoId) {
1205
				currentInventorySnapshotRepository.updateAvailabilityByItemIdAndFofoId(itemId, fofoId,
1206
						currentInventorySnapshot.getAvailability() - quantity);
22859 ashik.ali 1207
			}
1208
		}
1209
	}
23650 amit.gupta 1210
 
1211
	private void createPaymentOptions(FofoOrder fofoOrder, Set<CustomPaymentOption> customPaymentOptions)
1212
			throws ProfitMandiBusinessException {
1213
		for (CustomPaymentOption customPaymentOption : customPaymentOptions) {
1214
			if (customPaymentOption.getAmount() > 0) {
23546 ashik.ali 1215
				PaymentOptionTransaction paymentOptionTransaction = new PaymentOptionTransaction();
23612 amit.gupta 1216
				paymentOptionTransaction.setReferenceId(fofoOrder.getId());
23546 ashik.ali 1217
				paymentOptionTransaction.setPaymentOptionId(customPaymentOption.getPaymentOptionId());
1218
				paymentOptionTransaction.setReferenceType(PaymentOptionReferenceType.ORDER);
1219
				paymentOptionTransaction.setAmount(customPaymentOption.getAmount());
23612 amit.gupta 1220
				paymentOptionTransaction.setFofoId(fofoOrder.getFofoId());
23546 ashik.ali 1221
				paymentOptionTransactionRepository.persist(paymentOptionTransaction);
23371 ashik.ali 1222
			}
22859 ashik.ali 1223
		}
1224
	}
23650 amit.gupta 1225
 
24275 amit.gupta 1226
	private FofoOrder createAndGetFofoOrder(int customerId, String customerGstNumber, int fofoId, String documentNumber,
1227
			float totalAmount, int customerAddressId) {
22859 ashik.ali 1228
		FofoOrder fofoOrder = new FofoOrder();
23369 ashik.ali 1229
		fofoOrder.setCustomerGstNumber(customerGstNumber);
22859 ashik.ali 1230
		fofoOrder.setCustomerId(customerId);
1231
		fofoOrder.setFofoId(fofoId);
24226 amit.gupta 1232
		fofoOrder.setInvoiceNumber(documentNumber);
22859 ashik.ali 1233
		fofoOrder.setTotalAmount(totalAmount);
1234
		fofoOrder.setCustomerAddressId(customerAddressId);
1235
		fofoOrderRepository.persist(fofoOrder);
1236
		return fofoOrder;
1237
	}
23650 amit.gupta 1238
 
1239
	private Customer createAndGetCustomer(CustomCustomer customCustomer) throws ProfitMandiBusinessException {
25169 amit.gupta 1240
		List<Customer> customers = customerRepository.selectAllByMobileNumber(customCustomer.getMobileNumber());
1241
		List<Customer> filtered = customers.stream()
1242
				.filter(x -> x.getEmailId().equals(customCustomer.getEmailId())
1243
						&& x.getFirstName().equals(customCustomer.getFirstName())
1244
						&& x.getLastName().equals(customCustomer.getLastName()))
1245
				.collect(Collectors.toList());
1246
		if (filtered.size() > 0) {
1247
			return filtered.get(0);
22859 ashik.ali 1248
		}
25169 amit.gupta 1249
		Customer customer = new Customer();
23190 ashik.ali 1250
		customer.setFirstName(customCustomer.getFirstName());
1251
		customer.setLastName(customCustomer.getLastName());
1252
		customer.setEmailId(customCustomer.getEmailId());
1253
		customer.setMobileNumber(customCustomer.getMobileNumber());
1254
		customerRepository.persist(customer);
22859 ashik.ali 1255
		return customer;
1256
	}
23650 amit.gupta 1257
 
1258
	private void validateItemsSerializedNonSerialized(List<Item> items,
1259
			Map<Integer, CustomFofoOrderItem> customFofoOrderItemMap) throws ProfitMandiBusinessException {
1260
		List<Integer> invalidItemIdSerialNumbers = new ArrayList<Integer>();
22859 ashik.ali 1261
		List<Integer> itemIdNonSerializedSerialNumbers = new ArrayList<Integer>();
23650 amit.gupta 1262
		for (Item i : items) {
22872 ashik.ali 1263
			CustomFofoOrderItem customFofoOrderItem = customFofoOrderItemMap.get(i.getId());
23650 amit.gupta 1264
			if (i.getType().equals(ItemType.SERIALIZED)) {
1265
				if (customFofoOrderItem == null || customFofoOrderItem.getSerialNumberDetails().isEmpty()) {
22872 ashik.ali 1266
					invalidItemIdSerialNumbers.add(i.getId());
22859 ashik.ali 1267
				}
23650 amit.gupta 1268
			} else {
1269
				Set<String> serialNumbers = this
1270
						.serialNumberDetailsToSerialNumbers(customFofoOrderItem.getSerialNumberDetails());
1271
				if (customFofoOrderItem == null || !serialNumbers.isEmpty()) {
22872 ashik.ali 1272
					itemIdNonSerializedSerialNumbers.add(i.getId());
22859 ashik.ali 1273
				}
1274
			}
1275
		}
1276
 
23650 amit.gupta 1277
		if (!invalidItemIdSerialNumbers.isEmpty()) {
22859 ashik.ali 1278
			LOGGER.error("Invalid itemId's serialNumbers for serialized{}", invalidItemIdSerialNumbers);
1279
			// itemId's are serialized you are saying these are not serialized
23650 amit.gupta 1280
			throw new ProfitMandiBusinessException("invalidItemIdSerialNumbers", invalidItemIdSerialNumbers,
1281
					"FFORDR_1013");
22859 ashik.ali 1282
		}
1283
 
23650 amit.gupta 1284
		if (!itemIdNonSerializedSerialNumbers.isEmpty()) {
22859 ashik.ali 1285
			LOGGER.error("Invalid itemId's serialNumbers for non serialized{}", itemIdNonSerializedSerialNumbers);
1286
			// itemId's are non serialized you are saying these are serialized
23650 amit.gupta 1287
			throw new ProfitMandiBusinessException("itemIdNonSerializedSerialNumbers", itemIdNonSerializedSerialNumbers,
1288
					"FFORDR_1014");
22859 ashik.ali 1289
		}
1290
	}
23650 amit.gupta 1291
 
1292
	private void validateCurrentInventorySnapshotQuantities(List<CurrentInventorySnapshot> currentInventorySnapshots,
1293
			Map<Integer, CustomFofoOrderItem> itemIdCustomFofoOrderItemMap) throws ProfitMandiBusinessException {
1294
		if (itemIdCustomFofoOrderItemMap.keySet().size() != currentInventorySnapshots.size()) {
22859 ashik.ali 1295
			throw new ProfitMandiBusinessException("quantiiesSize", currentInventorySnapshots.size(), "");
1296
		}
23650 amit.gupta 1297
		List<ItemIdQuantityAvailability> itemIdQuantityAvailabilities = new ArrayList<>(); // this is for error
1298
		LOGGER.info("currentInventorySnapshots " + currentInventorySnapshots);
22872 ashik.ali 1299
		LOGGER.info("CustomFofoLineItemMap {}", itemIdCustomFofoOrderItemMap);
23650 amit.gupta 1300
		for (CurrentInventorySnapshot currentInventorySnapshot : currentInventorySnapshots) {
1301
			CustomFofoOrderItem customFofoOrderItem = itemIdCustomFofoOrderItemMap
1302
					.get(currentInventorySnapshot.getItemId());
22872 ashik.ali 1303
			LOGGER.info("customFofoOrderItem {}", customFofoOrderItem);
23650 amit.gupta 1304
			if (customFofoOrderItem.getQuantity() > currentInventorySnapshot.getAvailability()) {
1305
				ItemIdQuantityAvailability itemIdQuantityAvailability = new ItemIdQuantityAvailability();
1306
				itemIdQuantityAvailability.setItemId(customFofoOrderItem.getItemId());
1307
				Quantity quantity = new Quantity();
1308
				quantity.setAvailable(currentInventorySnapshot.getAvailability());
1309
				quantity.setRequested(customFofoOrderItem.getQuantity());
1310
				itemIdQuantityAvailability.setQuantity(quantity);
1311
				itemIdQuantityAvailabilities.add(itemIdQuantityAvailability);
1312
			}
22859 ashik.ali 1313
		}
1314
 
23650 amit.gupta 1315
		if (!itemIdQuantityAvailabilities.isEmpty()) {
22859 ashik.ali 1316
			// itemIdQuantity request is not valid
23650 amit.gupta 1317
			LOGGER.error("Requested quantities should not be greater than currently available quantities {}",
1318
					itemIdQuantityAvailabilities);
1319
			throw new ProfitMandiBusinessException("itemIdQuantityAvailabilities", itemIdQuantityAvailabilities,
1320
					"FFORDR_1015");
22859 ashik.ali 1321
		}
1322
	}
23650 amit.gupta 1323
 
1324
	private int getItemIdFromSerialNumber(Map<Integer, CustomFofoOrderItem> itemIdCustomFofoOrderItemMap,
1325
			String serialNumber) {
22872 ashik.ali 1326
		int itemId = 0;
23650 amit.gupta 1327
		for (Map.Entry<Integer, CustomFofoOrderItem> entry : itemIdCustomFofoOrderItemMap.entrySet()) {
22872 ashik.ali 1328
			Set<SerialNumberDetail> serialNumberDetails = entry.getValue().getSerialNumberDetails();
23650 amit.gupta 1329
			for (SerialNumberDetail serialNumberDetail : serialNumberDetails) {
1330
				if (serialNumberDetail.getSerialNumber().equals(serialNumber)) {
22872 ashik.ali 1331
					itemId = entry.getKey();
1332
					break;
1333
				}
22859 ashik.ali 1334
			}
1335
		}
22872 ashik.ali 1336
		return itemId;
22859 ashik.ali 1337
	}
23650 amit.gupta 1338
 
1339
	private Map<Integer, Item> toItemMap(List<Item> items) {
22955 ashik.ali 1340
		Function<Item, Integer> itemIdFunction = new Function<Item, Integer>() {
1341
			@Override
1342
			public Integer apply(Item item) {
1343
				return item.getId();
1344
			}
1345
		};
1346
		Function<Item, Item> itemFunction = new Function<Item, Item>() {
1347
			@Override
1348
			public Item apply(Item item) {
1349
				return item;
1350
			}
1351
		};
1352
		return items.stream().collect(Collectors.toMap(itemIdFunction, itemFunction));
22859 ashik.ali 1353
	}
1354
 
23650 amit.gupta 1355
	private void setCustomerAddress(CustomerAddress customerAddress, CustomAddress customAddress) {
22859 ashik.ali 1356
		customerAddress.setName(customAddress.getName());
1357
		customerAddress.setLine1(customAddress.getLine1());
1358
		customerAddress.setLine2(customAddress.getLine2());
1359
		customerAddress.setLandmark(customAddress.getLandmark());
1360
		customerAddress.setCity(customAddress.getCity());
1361
		customerAddress.setPinCode(customAddress.getPinCode());
1362
		customerAddress.setState(customAddress.getState());
1363
		customerAddress.setCountry(customAddress.getCountry());
1364
		customerAddress.setPhoneNumber(customAddress.getPhoneNumber());
1365
	}
1366
 
23650 amit.gupta 1367
	private CustomAddress createCustomAddress(Address address) {
22859 ashik.ali 1368
		CustomAddress customAddress = new CustomAddress();
1369
		customAddress.setName(address.getName());
1370
		customAddress.setLine1(address.getLine1());
1371
		customAddress.setLine2(address.getLine2());
1372
		customAddress.setLandmark(address.getLandmark());
1373
		customAddress.setCity(address.getCity());
1374
		customAddress.setPinCode(address.getPinCode());
1375
		customAddress.setState(address.getState());
1376
		customAddress.setCountry(address.getCountry());
1377
		customAddress.setPhoneNumber(address.getPhoneNumber());
1378
		return customAddress;
1379
	}
1380
 
23650 amit.gupta 1381
	private CustomAddress createCustomAddress(CustomerAddress customerAddress) {
22859 ashik.ali 1382
		CustomAddress customAddress = new CustomAddress();
1383
		customAddress.setName(customerAddress.getName());
1384
		customAddress.setLine1(customerAddress.getLine1());
1385
		customAddress.setLine2(customerAddress.getLine2());
1386
		customAddress.setLandmark(customerAddress.getLandmark());
1387
		customAddress.setCity(customerAddress.getCity());
1388
		customAddress.setPinCode(customerAddress.getPinCode());
1389
		customAddress.setState(customerAddress.getState());
1390
		customAddress.setCountry(customerAddress.getCountry());
1391
		customAddress.setPhoneNumber(customerAddress.getPhoneNumber());
1392
		return customAddress;
1393
	}
1394
 
23650 amit.gupta 1395
	private void validatePaymentOptionsAndTotalAmount(Set<CustomPaymentOption> customPaymentOptions, float totalAmount)
1396
			throws ProfitMandiBusinessException {
23365 ashik.ali 1397
		Set<Integer> paymentOptionIds = new HashSet<>();
23650 amit.gupta 1398
 
22859 ashik.ali 1399
		float calculatedAmount = 0;
23650 amit.gupta 1400
		for (CustomPaymentOption customPaymentOption : customPaymentOptions) {
23365 ashik.ali 1401
			paymentOptionIds.add(customPaymentOption.getPaymentOptionId());
1402
			calculatedAmount = calculatedAmount + customPaymentOption.getAmount();
22859 ashik.ali 1403
		}
23650 amit.gupta 1404
		if (calculatedAmount != totalAmount) {
1405
			LOGGER.warn("Error occured while validating payment options amount[{}] != TotalAmount [{}]",
1406
					calculatedAmount, totalAmount);
1407
			throw new ProfitMandiBusinessException(ProfitMandiConstants.PAYMENT_OPTION_CALCULATED_AMOUNT,
1408
					calculatedAmount, "FFORDR_1016");
22859 ashik.ali 1409
		}
23650 amit.gupta 1410
 
23365 ashik.ali 1411
		List<Integer> foundPaymentOptionIds = paymentOptionRepository.selectIdsByIds(paymentOptionIds);
23650 amit.gupta 1412
		if (foundPaymentOptionIds.size() != paymentOptionIds.size()) {
23365 ashik.ali 1413
			paymentOptionIds.removeAll(foundPaymentOptionIds);
23650 amit.gupta 1414
			throw new ProfitMandiBusinessException(ProfitMandiConstants.PAYMENT_OPTION_ID, paymentOptionIds,
1415
					"FFORDR_1017");
23365 ashik.ali 1416
		}
22859 ashik.ali 1417
	}
23650 amit.gupta 1418
 
22925 ashik.ali 1419
	@Override
1420
	public List<FofoOrderItem> getByOrderId(int orderId) throws ProfitMandiBusinessException {
1421
		List<FofoOrderItem> fofoOrderItems = fofoOrderItemRepository.selectByOrderId(orderId);
23650 amit.gupta 1422
		if (!fofoOrderItems.isEmpty()) {
22925 ashik.ali 1423
			List<FofoOrderItem> newFofoOrderItems = new ArrayList<>();
23650 amit.gupta 1424
			Map<Integer, Set<FofoLineItem>> fofoOrderItemIdFofoLineItemsMap = this
1425
					.toFofoOrderItemIdFofoLineItems(fofoOrderItems);
22925 ashik.ali 1426
			Iterator<FofoOrderItem> fofoOrderItemsIterator = fofoOrderItems.iterator();
23650 amit.gupta 1427
			while (fofoOrderItemsIterator.hasNext()) {
22925 ashik.ali 1428
				FofoOrderItem fofoOrderItem = fofoOrderItemsIterator.next();
1429
				fofoOrderItem.setFofoLineItems(fofoOrderItemIdFofoLineItemsMap.get(fofoOrderItem.getId()));
1430
				newFofoOrderItems.add(fofoOrderItem);
1431
				fofoOrderItemsIterator.remove();
1432
			}
1433
			fofoOrderItems = newFofoOrderItems;
1434
		}
1435
		return fofoOrderItems;
1436
	}
23650 amit.gupta 1437
 
1438
	private Set<Integer> toFofoOrderItemIds(List<FofoOrderItem> fofoOrderItems) {
22955 ashik.ali 1439
		Function<FofoOrderItem, Integer> fofoOrderItemToFofoOrderItemIdFunction = new Function<FofoOrderItem, Integer>() {
1440
			@Override
1441
			public Integer apply(FofoOrderItem fofoOrderItem) {
1442
				return fofoOrderItem.getId();
1443
			}
1444
		};
1445
		return fofoOrderItems.stream().map(fofoOrderItemToFofoOrderItemIdFunction).collect(Collectors.toSet());
22925 ashik.ali 1446
	}
23650 amit.gupta 1447
 
1448
	private Map<Integer, Set<FofoLineItem>> toFofoOrderItemIdFofoLineItems(List<FofoOrderItem> fofoOrderItems) {
22925 ashik.ali 1449
		Set<Integer> fofoOrderItemIds = this.toFofoOrderItemIds(fofoOrderItems);
1450
		List<FofoLineItem> fofoLineItems = fofoLineItemRepository.selectByFofoOrderItemIds(fofoOrderItemIds);
1451
		Map<Integer, Set<FofoLineItem>> fofoOrderItemIdFofoLineItemsMap = new HashMap<>();
23650 amit.gupta 1452
		for (FofoLineItem fofoLineItem : fofoLineItems) {
1453
			if (!fofoOrderItemIdFofoLineItemsMap.containsKey(fofoLineItem.getFofoOrderItemId())) {
22925 ashik.ali 1454
				Set<FofoLineItem> fofoLineItems2 = new HashSet<>();
1455
				fofoLineItems2.add(fofoLineItem);
1456
				fofoOrderItemIdFofoLineItemsMap.put(fofoLineItem.getFofoOrderItemId(), fofoLineItems2);
23650 amit.gupta 1457
			} else {
22925 ashik.ali 1458
				fofoOrderItemIdFofoLineItemsMap.get(fofoLineItem.getFofoOrderItemId()).add(fofoLineItem);
1459
			}
1460
		}
1461
		return fofoOrderItemIdFofoLineItemsMap;
1462
	}
23650 amit.gupta 1463
 
23418 ashik.ali 1464
	@Override
23650 amit.gupta 1465
	public void updateCustomerDetails(CustomCustomer customCustomer, String invoiceNumber)
1466
			throws ProfitMandiBusinessException {
23582 ashik.ali 1467
		FofoOrder fofoOrder = fofoOrderRepository.selectByInvoiceNumber(invoiceNumber);
1468
		Customer customer = customerRepository.selectById(fofoOrder.getCustomerId());
1469
		customer.setFirstName(customCustomer.getFirstName());
1470
		customer.setLastName(customCustomer.getLastName());
24121 govind 1471
		customer.setMobileNumber(customCustomer.getMobileNumber());
1472
		customer.setEmailId(customCustomer.getEmailId());
23582 ashik.ali 1473
		customerRepository.persist(customer);
1474
		CustomerAddress customerAddress = customerAddressRepository.selectById(fofoOrder.getCustomerAddressId());
25101 amit.gupta 1475
		if (!customerAddress.getState().equals(customCustomer.getAddress().getState())) {
1476
			List<FofoOrderItem> fofoOrderItems = fofoOrderItemRepository.selectByOrderId(fofoOrder.getId());
1477
			resetTaxation(fofoOrder.getFofoId(), customerAddress, fofoOrderItems);
1478
		}
23582 ashik.ali 1479
		this.setCustomerAddress(customerAddress, customCustomer.getAddress());
1480
		customerAddressRepository.persist(customerAddress);
24121 govind 1481
		fofoOrder.setCustomerGstNumber(customCustomer.getGstNumber());
23582 ashik.ali 1482
	}
23418 ashik.ali 1483
 
25101 amit.gupta 1484
	private void resetTaxation(int fofoId, CustomerAddress customerAddress, List<FofoOrderItem> fofoOrderItems)
1485
			throws ProfitMandiBusinessException {
1486
		int retailerAddressId = retailerRegisteredAddressRepository.selectAddressIdByRetailerId(fofoId);
1487
 
1488
		Address retailerAddress = addressRepository.selectById(retailerAddressId);
1489
 
1490
		Integer stateId = null;
1491
		if (customerAddress.getState().equals(retailerAddress.getState())) {
1492
			try {
1493
				stateId = Long.valueOf(Utils.getStateInfo(customerAddress.getState()).getId()).intValue();
1494
			} catch (Exception e) {
1495
				LOGGER.error("Unable to get state rates");
1496
			}
1497
		}
1498
		List<Integer> itemIds = fofoOrderItems.stream().map(x -> x.getItemId()).collect(Collectors.toList());
1499
		final Map<Integer, GstRate> gstRates;
1500
		if (stateId != null) {
1501
			gstRates = Utils.getStateTaxRate(itemIds, stateId);
1502
		} else {
1503
			gstRates = new HashMap<>();
1504
			Utils.getIgstTaxRate(itemIds).entrySet().forEach(x -> {
1505
				GstRate gstRate = new GstRate();
1506
				gstRate.setIgstRate(x.getValue());
1507
				gstRate.setCgstRate(0f);
1508
				gstRate.setSgstRate(0f);
1509
				gstRates.put(x.getKey(), gstRate);
1510
 
1511
			});
1512
		}
1513
		for (FofoOrderItem fofoOrderItem : fofoOrderItems) {
1514
			GstRate rate = gstRates.get(fofoOrderItem.getItemId());
1515
			fofoOrderItem.setCgstRate(rate.getCgstRate());
1516
			fofoOrderItem.setSgstRate(rate.getSgstRate());
1517
			fofoOrderItem.setIgstRate(rate.getIgstRate());
1518
		}
1519
	}
1520
 
23638 amit.gupta 1521
	@Override
24275 amit.gupta 1522
	public CustomerCreditNote badReturn(int fofoId, FoiBadReturnRequest foiBadReturnRequest)
1523
			throws ProfitMandiBusinessException {
23655 amit.gupta 1524
		FofoOrderItem foi = fofoOrderItemRepository.selectById(foiBadReturnRequest.getFofoOrderItemId());
23650 amit.gupta 1525
		FofoOrder fofoOrder = fofoOrderRepository.selectByOrderId(foi.getOrderId());
23655 amit.gupta 1526
		if (fofoOrder.getFofoId() != fofoId) {
23638 amit.gupta 1527
			throw new ProfitMandiBusinessException("Partner Auth", "", "Invalid Order");
1528
		}
23655 amit.gupta 1529
		int billedQty = foi.getQuantity() - customerReturnItemRepository.selectAllByOrderItemId(foi.getId()).size();
24275 amit.gupta 1530
		if (foiBadReturnRequest.getMarkedBadArr().size() > billedQty) {
23655 amit.gupta 1531
			throw new ProfitMandiBusinessException("Cant bad return more than what is billed", "", "Invalid Quantity");
1532
		}
23650 amit.gupta 1533
		List<CustomerReturnItem> customerReturnItems = new ArrayList<>();
23655 amit.gupta 1534
		for (BadReturnRequest badReturnRequest : foiBadReturnRequest.getMarkedBadArr()) {
23650 amit.gupta 1535
			CustomerReturnItem customerReturnItem = new CustomerReturnItem();
1536
			customerReturnItem.setFofoId(fofoId);
23655 amit.gupta 1537
			customerReturnItem.setFofoOrderItemId(foiBadReturnRequest.getFofoOrderItemId());
24264 amit.gupta 1538
			customerReturnItem.setFofoOrderId(fofoOrder.getId());
23655 amit.gupta 1539
			customerReturnItem.setRemarks(badReturnRequest.getRemarks());
23650 amit.gupta 1540
			customerReturnItem.setInventoryItemId(badReturnRequest.getInventoryItemId());
1541
			customerReturnItem.setQuantity(1);
1542
			customerReturnItem.setType(ReturnType.BAD);
24275 amit.gupta 1543
			// customerReturnItemRepository.persist(customerReturnItem);
23650 amit.gupta 1544
			inventoryService.saleReturnInventoryItem(customerReturnItem);
1545
			customerReturnItems.add(customerReturnItem);
23638 amit.gupta 1546
		}
23655 amit.gupta 1547
		CustomerCreditNote creditNote = generateCreditNote(fofoOrder, customerReturnItems);
24275 amit.gupta 1548
		for (CustomerReturnItem customerReturnItem : customerReturnItems) {
1549
			purchaseReturnService.returnInventoryItem(fofoId, false, customerReturnItem.getInventoryItemId(),
1550
					ReturnType.BAD);
23655 amit.gupta 1551
		}
24275 amit.gupta 1552
		return creditNote;
23638 amit.gupta 1553
	}
1554
 
24275 amit.gupta 1555
	private CustomerCreditNote generateCreditNote(FofoOrder fofoOrder, List<CustomerReturnItem> customerReturnItems)
1556
			throws ProfitMandiBusinessException {
23650 amit.gupta 1557
 
23638 amit.gupta 1558
		InvoiceNumberGenerationSequence sequence = invoiceNumberGenerationSequenceRepository
23650 amit.gupta 1559
				.selectByFofoId(fofoOrder.getFofoId());
1560
		sequence.setCreditNoteSequence(sequence.getCreditNoteSequence() + 1);
23638 amit.gupta 1561
		invoiceNumberGenerationSequenceRepository.persist(sequence);
24275 amit.gupta 1562
 
23655 amit.gupta 1563
		String creditNoteNumber = sequence.getPrefix() + "/" + sequence.getCreditNoteSequence();
23650 amit.gupta 1564
		CustomerCreditNote creditNote = new CustomerCreditNote();
1565
		creditNote.setCreditNoteNumber(creditNoteNumber);
1566
		creditNote.setFofoId(fofoOrder.getFofoId());
23655 amit.gupta 1567
		creditNote.setFofoOrderId(fofoOrder.getId());
1568
		creditNote.setFofoOrderItemId(customerReturnItems.get(0).getFofoOrderItemId());
1569
		creditNote.setSettlementType(SettlementType.UNSETTLED);
23650 amit.gupta 1570
		customerCreditNoteRepository.persist(creditNote);
24275 amit.gupta 1571
 
23650 amit.gupta 1572
		for (CustomerReturnItem customerReturnItem : customerReturnItems) {
1573
			customerReturnItem.setCreditNoteId(creditNote.getId());
1574
			customerReturnItemRepository.persist(customerReturnItem);
23638 amit.gupta 1575
		}
24275 amit.gupta 1576
		// this.returnInventoryItems(inventoryItems, debitNote);
23638 amit.gupta 1577
 
23655 amit.gupta 1578
		return creditNote;
23650 amit.gupta 1579
	}
24275 amit.gupta 1580
 
23655 amit.gupta 1581
	@Override
1582
	public CreditNotePdfModel getCreditNotePdfModel(int customerCreditNoteId) throws ProfitMandiBusinessException {
1583
		CustomerCreditNote creditNote = customerCreditNoteRepository.selectById(customerCreditNoteId);
1584
		return getCreditNotePdfModel(creditNote);
1585
	}
24275 amit.gupta 1586
 
1587
	private CreditNotePdfModel getCreditNotePdfModel(CustomerCreditNote creditNote)
1588
			throws ProfitMandiBusinessException {
23655 amit.gupta 1589
		FofoOrder fofoOrder = fofoOrderRepository.selectByOrderId(creditNote.getFofoOrderId());
24275 amit.gupta 1590
		List<CustomerReturnItem> customerReturnItems = customerReturnItemRepository
1591
				.selectAllByCreditNoteId(creditNote.getId());
23655 amit.gupta 1592
		CustomCustomer customCustomer = getCustomCustomer(fofoOrder);
24275 amit.gupta 1593
 
23655 amit.gupta 1594
		Set<CustomOrderItem> customerFofoOrderItems = new HashSet<>();
24275 amit.gupta 1595
		CustomRetailer customRetailer = retailerService.getFofoRetailers(Arrays.asList(fofoOrder.getFofoId()))
1596
				.get(fofoOrder.getFofoId());
23655 amit.gupta 1597
 
1598
		FofoOrderItem fofoOrderItem = fofoOrderItemRepository.selectById(creditNote.getFofoOrderItemId());
1599
		float totalTaxRate = fofoOrderItem.getIgstRate() + fofoOrderItem.getSgstRate() + fofoOrderItem.getCgstRate();
1600
		float taxableSellingPrice = fofoOrderItem.getSellingPrice() / (1 + totalTaxRate / 100);
1601
		float taxableDiscountPrice = fofoOrderItem.getDiscount() / (1 + totalTaxRate / 100);
1602
 
1603
		CustomOrderItem customFofoOrderItem = new CustomOrderItem();
1604
		customFofoOrderItem.setAmount(customerReturnItems.size() * (taxableSellingPrice - taxableDiscountPrice));
1605
		customFofoOrderItem.setDescription(fofoOrderItem.getBrand() + " " + fofoOrderItem.getModelName() + " "
1606
				+ fofoOrderItem.getModelNumber() + "-" + fofoOrderItem.getColor());
24275 amit.gupta 1607
 
1608
		if (ItemType.SERIALIZED.equals(itemRepository.selectById(fofoOrderItem.getItemId()).getType())) {
23655 amit.gupta 1609
			Set<Integer> inventoryItemIds = customerReturnItems.stream().map(x -> x.getInventoryItemId())
1610
					.collect(Collectors.toSet());
1611
			List<String> serialNumbers = inventoryItemRepository.selectByIds(inventoryItemIds).stream()
1612
					.map(x -> x.getSerialNumber()).collect(Collectors.toList());
1613
			customFofoOrderItem.setDescription(
1614
					customFofoOrderItem.getDescription() + "\n IMEIS - " + String.join(", ", serialNumbers));
1615
		}
24275 amit.gupta 1616
 
23655 amit.gupta 1617
		customFofoOrderItem.setRate(taxableSellingPrice);
1618
		customFofoOrderItem.setDiscount(taxableDiscountPrice);
1619
		customFofoOrderItem.setQuantity(customerReturnItems.size());
24275 amit.gupta 1620
		customFofoOrderItem.setNetAmount(
1621
				(fofoOrderItem.getSellingPrice() - fofoOrderItem.getDiscount()) * customFofoOrderItem.getQuantity());
23655 amit.gupta 1622
 
1623
		float igstAmount = (customFofoOrderItem.getAmount() * fofoOrderItem.getIgstRate()) / 100;
1624
		float cgstAmount = (customFofoOrderItem.getAmount() * fofoOrderItem.getCgstRate()) / 100;
1625
		float sgstAmount = (customFofoOrderItem.getAmount() * fofoOrderItem.getSgstRate()) / 100;
1626
		LOGGER.info("fofoOrderItem - {}", fofoOrderItem);
1627
		customFofoOrderItem.setIgstRate(fofoOrderItem.getIgstRate());
1628
		customFofoOrderItem.setIgstAmount(igstAmount);
1629
		customFofoOrderItem.setCgstRate(fofoOrderItem.getCgstRate());
1630
		customFofoOrderItem.setCgstAmount(cgstAmount);
1631
		customFofoOrderItem.setSgstRate(fofoOrderItem.getSgstRate());
1632
		customFofoOrderItem.setSgstAmount(sgstAmount);
1633
		customFofoOrderItem.setHsnCode(fofoOrderItem.getHsnCode());
23721 amit.gupta 1634
		customFofoOrderItem.setOrderId(1);
23655 amit.gupta 1635
		customerFofoOrderItems.add(customFofoOrderItem);
24275 amit.gupta 1636
 
23650 amit.gupta 1637
		PdfModel pdfModel = new PdfModel();
1638
		pdfModel.setAuther("NSSPL");
23655 amit.gupta 1639
		pdfModel.setCustomer(customCustomer);
1640
		pdfModel.setInvoiceNumber(fofoOrder.getInvoiceNumber());
1641
		pdfModel.setInvoiceDate(FormattingUtils.formatDate(fofoOrder.getCreateTimestamp()));
1642
		pdfModel.setTitle("Credit Note");
1643
		pdfModel.setRetailer(customRetailer);
1644
		pdfModel.setTotalAmount(customFofoOrderItem.getNetAmount());
1645
		pdfModel.setOrderItems(customerFofoOrderItems);
24275 amit.gupta 1646
 
23650 amit.gupta 1647
		CreditNotePdfModel creditNotePdfModel = new CreditNotePdfModel();
1648
		creditNotePdfModel.setCreditNoteDate(FormattingUtils.formatDate(creditNote.getCreateTimestamp()));
1649
		creditNotePdfModel.setCreditNoteNumber(creditNote.getCreditNoteNumber());
1650
		creditNotePdfModel.setPdfModel(pdfModel);
1651
		return creditNotePdfModel;
1652
	}
23638 amit.gupta 1653
 
24275 amit.gupta 1654
	// This will remove the order and maintain order record and reverse inventory
1655
	// and scheme
24264 amit.gupta 1656
	@Override
1657
	public void cancelOrder(List<String> invoiceNumbers) throws Exception {
24275 amit.gupta 1658
		for (String invoiceNumber : invoiceNumbers) {
24264 amit.gupta 1659
			FofoOrder fofoOrder = fofoOrderRepository.selectByInvoiceNumber(invoiceNumber);
1660
			fofoOrder.setCancelledTimestamp(LocalDateTime.now());
1661
			fofoOrderRepository.persist(fofoOrder);
24275 amit.gupta 1662
			List<PaymentOptionTransaction> paymentTransactions = paymentOptionTransactionRepository
1663
					.selectByReferenceIdAndType(fofoOrder.getId(), PaymentOptionReferenceType.ORDER);
24264 amit.gupta 1664
			for (PaymentOptionTransaction paymentOptionTransaction : paymentTransactions) {
1665
				paymentOptionTransactionRepository.delete(paymentOptionTransaction);
1666
			}
1667
			List<FofoOrderItem> fois = fofoOrderItemRepository.selectByOrderId(fofoOrder.getId());
1668
			List<InventoryItem> inventoryItems = new ArrayList<>();
24275 amit.gupta 1669
			fois.stream().forEach(x -> {
1670
				x.getFofoLineItems().stream().forEach(y -> {
24264 amit.gupta 1671
					inventoryService.rollbackInventory(y.getInventoryItemId(), y.getQuantity(), fofoOrder.getFofoId());
1672
					inventoryItems.add(inventoryItemRepository.selectById(y.getInventoryItemId()));
1673
				});
1674
			});
1675
			String reversalReason = "Order Rolledback/Cancelled for Invoice Number " + invoiceNumber;
1676
			schemeService.reverseSchemes(inventoryItems, fofoOrder.getId(), reversalReason, SchemeType.OUT);
1677
		}
1678
	}
1679
 
24271 amit.gupta 1680
	@Override
1681
	public float getSales(int fofoId, LocalDateTime startDate, LocalDateTime endDate) {
24287 amit.gupta 1682
		Float sales = fofoOrderRepository.selectSaleSumGroupByFofoIds(startDate, endDate).get(fofoId);
24285 amit.gupta 1683
		return sales == null ? 0f : sales;
24271 amit.gupta 1684
	}
1685
 
1686
	@Override
1687
	public float getSales(int fofoId, LocalDate onDate) {
24285 amit.gupta 1688
		LocalDateTime startTime = LocalDateTime.of(onDate, LocalTime.MIDNIGHT);
1689
		LocalDateTime endTime = LocalDateTime.of(onDate, LocalTime.MIDNIGHT).plusDays(1);
1690
		return this.getSales(fofoId, startTime, endTime);
24271 amit.gupta 1691
	}
1692
 
1693
	@Override
1694
	public float getSales(LocalDateTime onDate) {
1695
		// TODO Auto-generated method stub
1696
		return 0;
1697
	}
1698
 
1699
	@Override
1700
	public float getSales(LocalDateTime startDate, LocalDateTime endDate) {
1701
		// TODO Auto-generated method stub
1702
		return 0;
1703
	}
1704
 
24917 tejbeer 1705
	@Override
1706
	public boolean notifyColorChange(int orderId, int itemId) throws ProfitMandiBusinessException {
1707
		Order order = orderRepository.selectById(orderId);
25101 amit.gupta 1708
		inventoryService.reservationCount(itemId, order.getLineItem().getItemId(), order.getFulfilmentWarehouseId(),
1709
				order.getLineItem().getQuantity());
1710
 
1711
		order.getLineItem().setItemId(itemId);
1712
		Item item = itemRepository.selectById(itemId);
24917 tejbeer 1713
		order.getLineItem().setColor(item.getColor());
1714
		return true;
1715
	}
1716
 
25083 amit.gupta 1717
	@Override
1718
	public FofoOrder getOrderByInventoryItemId(int inventoryItemId) throws Exception {
1719
		List<FofoLineItem> lineItems = fofoLineItemRepository.selectByInventoryItemId(inventoryItemId);
25101 amit.gupta 1720
		if (lineItems.size() > 0) {
25083 amit.gupta 1721
			FofoOrderItem fofoOrderItem = fofoOrderItemRepository.selectById(lineItems.get(0).getFofoOrderItemId());
1722
			fofoOrderItem.setFofoLineItems(new HashSet<>(lineItems));
1723
			FofoOrder fofoOrder = fofoOrderRepository.selectByOrderId(fofoOrderItem.getOrderId());
1724
			fofoOrder.setOrderItem(fofoOrderItem);
1725
			return fofoOrder;
1726
		} else {
1727
			throw new Exception(String.format("Could not find inventoryItemId - %s", inventoryItemId));
1728
		}
1729
	}
1730
 
22859 ashik.ali 1731
}