Subversion Repositories SmartDukaan

Rev

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

Rev Author Line No. Line
442 rajveer 1
'''
2
Created on 13-Sep-2010
3
 
4
@author: rajveer
5
'''
6
 
21096 amit.gupta 7
from collections import namedtuple
16025 amit.gupta 8
from elixir import session
9
from shop2020.clients.CatalogClient import CatalogClient
10
from shop2020.clients.InventoryClient import InventoryClient
20724 kshitij.so 11
from shop2020.clients.TransactionClient import TransactionClient
21096 amit.gupta 12
from shop2020.logistics.service.impl import BluedartService, DataService
644 chandransh 13
from shop2020.logistics.service.impl.DataService import Awb, AwbUpdate, Provider, \
16025 amit.gupta 14
    DeliveryEstimate, WarehouseAllocation, PublicHolidays, \
21096 amit.gupta 15
    ServiceableLocationDetails, PickupStore, Locations, ProviderCosting, \
16
    BluedartAttribute, PincodeStates
16025 amit.gupta 17
from shop2020.thriftpy.logistics.ttypes import LogisticsServiceException, \
21096 amit.gupta 18
    DeliveryType, LogisticsLocationInfo, LocationInfo, ProviderInfo, \
19
    DeliveryEstimateAndCosting
19413 amit.gupta 20
from shop2020.thriftpy.model.v1.inventory.ttypes import Warehouse, BillingType, \
16025 amit.gupta 21
    WarehouseType
442 rajveer 22
from shop2020.utils.Utils import log_entry, to_py_date, to_java_date
5964 amar.kumar 23
from sqlalchemy.sql import or_
16025 amit.gupta 24
import datetime
3355 chandransh 25
import logging
21096 amit.gupta 26
import math
13146 manish.sha 27
import os
16025 amit.gupta 28
import sys
29
import time
20724 kshitij.so 30
import traceback
19413 amit.gupta 31
 
3355 chandransh 32
logging.basicConfig(level=logging.DEBUG)
442 rajveer 33
 
19413 amit.gupta 34
PincodeProvider = namedtuple("PincodeProvider", ["dest_pin", "provider"])
35
 
3217 rajveer 36
warehouse_allocation_cache = {}
37
serviceable_location_cache = {}
38
delivery_estimate_cache = {}
16025 amit.gupta 39
warehouse_location_cache = {}
19413 amit.gupta 40
location_state={}
20275 amit.gupta 41
 
42
'Delhivery Bluedart, Fedex Surface, Fedex Air'
19413 amit.gupta 43
state_locations = {}
19421 manish.sha 44
provider_costing_sheet = {}
45
DELHIVERY = 3
6370 rajveer 46
 
19413 amit.gupta 47
#pincode location map is ab
48
#{'110001':{1:{"sameState":False, "providerInfo":{1:(1,1), 2:(1,1)}}},}
49
pincode_locations = {}
50
#{(dest_pin, provider):(otgAvailable,providerCodLimit, websiteCodLimit, storeCodLimit, providerPrepaidLimit)} 
51
serviceable_map = {}
52
 
53
#Need to identify a better way
54
statepinmap={'11':0, 
55
             '40':1,'41':1,'42':1,'43':1,'44':1,
56
             '56':2, '57':2, '58':2, '59':2,
57
             '12':3, '13':3, 
58
             '30':4, '31':4, '32':4, '33':4, '34':4,
59
             '36':6,'37':6,'38':6,'39':6
60
             }
61
 
3218 rajveer 62
'''
63
This class is for only data transfer. Never used outside this module.
64
'''
65
class _DeliveryEstimateObject:
6537 rajveer 66
    def __init__(self, delivery_time, delivery_delay, provider_id, codAllowed, otgAvailable):
3218 rajveer 67
        self.delivery_time = delivery_time
6537 rajveer 68
        self.delivery_delay = delivery_delay
3218 rajveer 69
        self.provider_id = provider_id
4866 rajveer 70
        self.codAllowed = codAllowed
6524 rajveer 71
        self.otgAvailable = otgAvailable
3218 rajveer 72
 
3187 rajveer 73
def initialize(dbname="logistics", db_hostname="localhost"):
442 rajveer 74
    log_entry("initialize@DataAccessor", "Initializing data service")
3187 rajveer 75
    DataService.initialize(dbname, db_hostname)
3218 rajveer 76
    print "Starting cache population at: " + str(datetime.datetime.now())
16025 amit.gupta 77
    #__cache_warehouse_allocation_table()
78
    __cache_warehouse_locations()
3217 rajveer 79
    __cache_serviceable_location_details_table()
80
    __cache_delivery_estimate_table()
20275 amit.gupta 81
    __cache_pincode_provider_serviceability()
19413 amit.gupta 82
    __cache_locations()
83
    __cache_pincode_estimates()    
19421 manish.sha 84
    __cache_courier_costing_table()
3217 rajveer 85
    close_session()
3218 rajveer 86
    print "Done cache population at: " + str(datetime.datetime.now())
442 rajveer 87
 
19413 amit.gupta 88
def __cache_locations():
89
    locations = Locations.query.all()
90
    for location in locations:
91
        location_state[location.id] = location.state_id
92
        if not state_locations.has_key(location.state_id):
93
            state_locations[location.state_id] = []
94
        state_locations[location.state_id] = state_locations[location.state_id].append(location.state_id)
95
 
96
def __cache_pincode_estimates():
97
    delivery_estimates = DeliveryEstimate.query.all()
98
    for delivery_estimate in delivery_estimates:
99
        if not pincode_locations.has_key(delivery_estimate.destination_pin):
100
            pincode_locations[delivery_estimate.destination_pin] = {}
101
        destination_pinMap = pincode_locations[delivery_estimate.destination_pin] 
102
        if not destination_pinMap.has_key(delivery_estimate.warehouse_location):
103
            destination_pinMap[delivery_estimate.warehouse_location] = {}
104
            state_id = location_state.get(delivery_estimate.warehouse_location)
105
            sameState = __getStateFromPin(delivery_estimate.destination_pin) == state_id
106
            destination_pinMap[delivery_estimate.warehouse_location]['sameState']=sameState
107
            destination_pinMap[delivery_estimate.warehouse_location]['providerInfo'] = {} 
108
        destination_pinMap[delivery_estimate.warehouse_location]['providerInfo'][delivery_estimate.provider_id] = delivery_estimate.delivery_time + delivery_estimate.delivery_delay
109
 
110
 
111
 
112
def __cache_pincode_provider_serviceability():
113
    pincode_providers = ServiceableLocationDetails.query.filter(ServiceableLocationDetails.exp==1)
114
    for pp in pincode_providers:
115
        serviceable_map[PincodeProvider(pp.dest_pincode, pp.provider_id)] = (pp.cod, pp.otgAvailable,pp.providerCodLimit, pp.websiteCodLimit, pp.storeCodLimit, pp.providerPrepaidLimit)
116
 
117
 
3217 rajveer 118
def __cache_delivery_estimate_table():
119
    delivery_estimates = DeliveryEstimate.query.all()
120
    for delivery_estimate in delivery_estimates:
7857 rajveer 121
        delivery_estimate_cache[delivery_estimate.destination_pin, delivery_estimate.provider_id, delivery_estimate.warehouse_location]\
19421 manish.sha 122
        =delivery_estimate.delivery_time, delivery_estimate.delivery_delay, delivery_estimate.providerZoneCode
3217 rajveer 123
 
124
def __cache_serviceable_location_details_table():
5964 amar.kumar 125
    serviceable_locations = ServiceableLocationDetails.query.filter(or_("exp!=0","cod!=0"))
3217 rajveer 126
    for serviceable_location in serviceable_locations:
22147 amit.gupta 127
        #Bluedart is temporarily not serviceable
128
        if serviceable_location.provider_id==1:
129
            continue
3217 rajveer 130
        try:
131
            provider_pincodes = serviceable_location_cache[serviceable_location.provider_id]
132
        except:
133
            provider_pincodes = {}
134
            serviceable_location_cache[serviceable_location.provider_id] = provider_pincodes 
19474 manish.sha 135
        provider_pincodes[serviceable_location.dest_pincode] = serviceable_location.dest_code, serviceable_location.exp, serviceable_location.cod, serviceable_location.otgAvailable, serviceable_location.websiteCodLimit, serviceable_location.storeCodLimit, serviceable_location.providerPrepaidLimit, serviceable_location.providerCodLimit
3217 rajveer 136
 
137
def __cache_warehouse_allocation_table():
138
    warehouse_allocations = WarehouseAllocation.query.all()
139
    for warehouse_allocation in warehouse_allocations:
140
        warehouse_allocation_cache[warehouse_allocation.pincode]=warehouse_allocation.primary_warehouse_location
141
 
16025 amit.gupta 142
def __cache_warehouse_locations():
143
    client = InventoryClient().get_client()
19413 amit.gupta 144
    #client.getAllWarehouses(True)
16025 amit.gupta 145
    for warehouse in client.getAllWarehouses(True):
146
        warehouse_location_cache[warehouse.billingWarehouseId]=warehouse.logisticsLocation
19421 manish.sha 147
 
148
def __cache_courier_costing_table():
149
    allCostings = ProviderCosting.query.all()
150
    for costing in allCostings:
151
        if provider_costing_sheet.has_key(costing.provider_id):
152
            costingMap = provider_costing_sheet.get(costing.provider_id)
153
            costingMap[costing.zoneCode] = costing
154
            provider_costing_sheet[costing.provider_id] = costingMap
155
        else:
156
            costingMap = {}
157
            costingMap[costing.zoneCode] = costing
158
            provider_costing_sheet[costing.provider_id] = costingMap
159
 
16025 amit.gupta 160
 
644 chandransh 161
def get_provider(provider_id):
766 rajveer 162
    provider =  Provider.get_by(id=provider_id)
163
    return provider
644 chandransh 164
 
165
def get_providers():
5387 rajveer 166
    providers = Provider.query.filter_by(isActive = 1).all()
19413 amit.gupta 167
    return providers
644 chandransh 168
 
19413 amit.gupta 169
#it would return only states where our warehouses are present else return -1
170
def __getStateFromPin(pin):
171
    if pin[:3] in ['744', '682']:
172
        return -1
173
    elif statepinmap.has_key(pin[:2]):
174
        return statepinmap[pin[:2]]
175
    else:
176
        return -1
177
 
178
 
179
def get_logistics_locations(destination_pin, selling_price_list):
180
    #pincode_locations = {1:{"sameState":False, "providerInfo":{<provider_id>:<delay_days>}},}
181
    #pp.otgAvailable,pp.providerCodLimit, pp.websiteCodLimit, pp.storeCodLimit, pp.providerPrepaidLimit
182
    returnMap = {}
183
    if pincode_locations.has_key(destination_pin):
184
        locations = pincode_locations[destination_pin]
185
        for item_selling_price in selling_price_list:
186
            returnMap[item_selling_price] = {}
187
            for location_id, value in locations.iteritems():
188
                #put weight logic here
189
                otgAvailable = False
190
                codAvailable = False
191
                minDelay = -1
192
                maxDelay = -1
193
                serviceable = False
194
                for provider_id, delay_days in value['providerInfo'].iteritems():
19420 amit.gupta 195
                    pp = PincodeProvider(destination_pin, provider_id)
196
                    if not serviceable_map.has_key(pp):
197
                        continue
198
                    iscod, isotg, providerCodLimit, websiteCodLimit, storeCodLimit, providerPrepaidLimit = serviceable_map[pp]  
19413 amit.gupta 199
                    if item_selling_price <= providerPrepaidLimit:
200
                        if not serviceable:
20275 amit.gupta 201
                            returnMap[item_selling_price][location_id] = LocationInfo(locationId = location_id, sameState=value['sameState'])
19413 amit.gupta 202
                            serviceable = True
203
                            minDelay = delay_days
204
                            maxDelay = delay_days
205
                        else:
206
                            minDelay = min(delay_days,minDelay)
207
                            maxDelay = max(delay_days,maxDelay)
208
                        iscod = iscod and item_selling_price <= min(providerCodLimit, websiteCodLimit)
209
                        isotg = (isotg and item_selling_price >= 2000)
210
                        otgAvailable = otgAvailable or isotg
211
                        codAvailable = codAvailable or iscod
212
                if serviceable:        
20275 amit.gupta 213
                    returnMap[item_selling_price][location_id].isOtg = otgAvailable
214
                    returnMap[item_selling_price][location_id].isCod = codAvailable
19413 amit.gupta 215
                    returnMap[item_selling_price][location_id].minDelay = minDelay
216
                    returnMap[item_selling_price][location_id].maxDelay = maxDelay
217
    return returnMap
218
 
7608 rajveer 219
def get_logistics_estimation(destination_pin, item_selling_price, weight, type, billingWarehouseId):
5692 rajveer 220
    logging.info("Getting logistics estimation for pincode:" + destination_pin )
1504 ankur.sing 221
 
7608 rajveer 222
    provider_id, codAllowed, otgAvailable = __get_logistics_provider_for_destination_pincode(destination_pin, item_selling_price, weight, type, billingWarehouseId)
9964 anupam.sin 223
 
17530 manish.sha 224
    logging.info("Provider Id:  " + str(provider_id) +" codAllowed: "+str(codAllowed)+" otgAvailable: "+str(otgAvailable)+ " item_selling_price: "+str(item_selling_price))
225
 
226
    if item_selling_price > 60000:# or item_selling_price <= 250:
9964 anupam.sin 227
        codAllowed = False
228
 
16025 amit.gupta 229
    warehouse_location = warehouse_location_cache.get(billingWarehouseId)
230
    if warehouse_location is None:
231
        warehouse_location = 0
7857 rajveer 232
 
3217 rajveer 233
    if not provider_id:
5692 rajveer 234
        raise LogisticsServiceException(101, "No provider assigned for pincode: " + str(destination_pin))
644 chandransh 235
    try:
16025 amit.gupta 236
        logging.info( "destination_pin %s, provider_id %s, warehouse_location %s"%(destination_pin, provider_id, warehouse_location))
19481 manish.sha 237
        logging.info( "Estimates %s, %s, %s"%(delivery_estimate_cache[destination_pin, provider_id, warehouse_location]))
7857 rajveer 238
        delivery_time = delivery_estimate_cache[destination_pin, provider_id, warehouse_location][0]
239
        delivery_delay = delivery_estimate_cache[destination_pin, provider_id, warehouse_location][1]
6537 rajveer 240
        delivery_estimate = _DeliveryEstimateObject(delivery_time, delivery_delay, provider_id, codAllowed, otgAvailable)
3218 rajveer 241
        return delivery_estimate
1504 ankur.sing 242
    except Exception as ex:
243
        print ex
644 chandransh 244
        raise LogisticsServiceException(103, "No Logistics partner listed for this destination pincode and the primary warehouse")
3150 rajveer 245
 
7608 rajveer 246
def __get_logistics_provider_for_destination_pincode(destination_pin, item_selling_price, weight, type, billingWarehouseId):
20641 amit.gupta 247
    #As of now we are dealing with Aramex and Bluedart. i.e. 1 and 2 and we have just one location i.e. gurgaon will generailise this 
248
    #Once bandwidth is available these things will be derived through improved logic.
249
    #As of now otg is set to False
250
    otg=False
21096 amit.gupta 251
    aramexServiceable = serviceable_location_cache.has_key(2) and serviceable_location_cache.get(2).has_key(destination_pin)
22147 amit.gupta 252
    blueDartServiceable =  serviceable_location_cache.has_key(1) and serviceable_location_cache.get(1).has_key(destination_pin)
253
 
254
    #blueDartServiceable =  False
21096 amit.gupta 255
    if blueDartServiceable and aramexServiceable:
256
        state = __getStateByPin(destination_pin)
257
        if state is None:
258
            state = 'DELHI'
259
        #Prioritise Bluedart in Gujarat and Rajasthan
260
        if state in ['GUJARAT', 'RAJASTHAN']:
261
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(1).get(destination_pin)
262
            if item_selling_price <= providerPrepaidLimit:
263
                iscod = iscod and item_selling_price <= websiteCodLimit
264
                if iscod:
265
                    return 1, True, otg
266
                else:
267
                    dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(2).get(destination_pin)
268
                    if item_selling_price <= providerPrepaidLimit:
269
                        iscod = iscod and item_selling_price <= websiteCodLimit
270
                        if iscod:
271
                            return 2, True, otg
272
                        else:
273
                            return 1, False, otg
274
        else:
275
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(2).get(destination_pin)
276
            if item_selling_price <= providerPrepaidLimit:
277
                iscod = iscod and item_selling_price <= websiteCodLimit
278
                if iscod:
279
                    return 2, True, otg
280
                else:
281
                    dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(1).get(destination_pin)
282
                    if item_selling_price <= providerPrepaidLimit:
283
                        iscod = iscod and item_selling_price <= websiteCodLimit
284
                        if iscod:
285
                            return 1, True, otg
286
                        else:
287
                            return 2, False, otg
288
 
289
    else:
22237 amit.gupta 290
        if blueDartServiceable:
291
            provider=1
292
        elif aramexServiceable:
293
            provider=2
294
        else:
295
            provider = None
20641 amit.gupta 296
 
22237 amit.gupta 297
        if provider:
22238 amit.gupta 298
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(provider).get(destination_pin)
22237 amit.gupta 299
            if item_selling_price <= providerPrepaidLimit:
300
                iscod = iscod and item_selling_price <= websiteCodLimit
301
                return provider, iscod, otg
302
 
20641 amit.gupta 303
 
304
    return None, False, False
305
 
21096 amit.gupta 306
def __getStateByPin(destination_pin):
307
    pinCodeState = PincodeStates.get_by(pin=destination_pin)
308
    if pinCodeState is not None:
309
        return pinCodeState.statename
310
    else:
311
        return None 
312
 
20641 amit.gupta 313
def __get_logistics_provider_for_destination_pincode_old(destination_pin, item_selling_price, weight, type, billingWarehouseId):
13357 manish.sha 314
    '''
315
    if serviceable_location_cache.get(6).has_key(destination_pin):
316
        if weight < 480 and serviceable_location_cache.get(3).has_key(destination_pin) and type == DeliveryType.PREPAID:
317
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit = serviceable_location_cache.get(3).get(destination_pin)
318
            if item_selling_price <= providerPrepaidLimit:
319
                iscod = iscod and item_selling_price <= websiteCodLimit
320
                otgAvailable = otgAvailable and item_selling_price >= 2000
321
                return 3, iscod, otgAvailable
322
        else:
323
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit = serviceable_location_cache.get(6).get(destination_pin)
324
            if item_selling_price <= providerPrepaidLimit:
325
                iscod = iscod and item_selling_price <= websiteCodLimit
326
                otgAvailable = otgAvailable and item_selling_price >= 2000
327
                return 6, iscod, otgAvailable
20641 amit.gupta 328
    '''        
329
    if serviceable_location_cache.has_key(3) and serviceable_location_cache.get(3).has_key(destination_pin):
330
        dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(3).get(destination_pin)
331
        if item_selling_price <= providerPrepaidLimit:
332
            iscod = iscod and item_selling_price <= websiteCodLimit
333
            otgAvailable = otgAvailable and item_selling_price >= 2000
334
            return 3, iscod, otgAvailable
8575 rajveer 335
 
17992 manish.sha 336
    if billingWarehouseId not in [12,13] and serviceable_location_cache.has_key(7) and serviceable_location_cache.get(7).has_key(destination_pin):
19533 manish.sha 337
        if item_selling_price < 3000 and serviceable_location_cache.has_key(1) and serviceable_location_cache.get(1).has_key(destination_pin):
19476 manish.sha 338
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(1).get(destination_pin)
8575 rajveer 339
            if item_selling_price <= providerPrepaidLimit:
340
                iscod = iscod and item_selling_price <= websiteCodLimit
341
                otgAvailable = otgAvailable and item_selling_price >= 2000
20275 amit.gupta 342
                if iscod:
343
                    return 1, iscod, otgAvailable
8575 rajveer 344
        else:
19476 manish.sha 345
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(7).get(destination_pin)
8575 rajveer 346
            if item_selling_price <= providerPrepaidLimit:
347
                iscod = iscod and item_selling_price <= websiteCodLimit
348
                otgAvailable = otgAvailable and item_selling_price >= 2000
20275 amit.gupta 349
                if iscod:
350
                    return 7, iscod, otgAvailable
19533 manish.sha 351
 
352
    if billingWarehouseId not in [12,13] and serviceable_location_cache.has_key(46) and serviceable_location_cache.get(46).has_key(destination_pin):
353
        if item_selling_price < 3000 and serviceable_location_cache.has_key(1) and serviceable_location_cache.get(1).has_key(destination_pin):
354
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(1).get(destination_pin)
355
            if item_selling_price <= providerPrepaidLimit:
356
                iscod = iscod and item_selling_price <= websiteCodLimit
357
                otgAvailable = otgAvailable and item_selling_price >= 2000
20275 amit.gupta 358
                if iscod:
359
                    return 1, iscod, otgAvailable
19533 manish.sha 360
        else:
361
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(46).get(destination_pin)
362
            if item_selling_price <= providerPrepaidLimit:
363
                iscod = iscod and item_selling_price <= websiteCodLimit
364
                otgAvailable = otgAvailable and item_selling_price >= 2000
20275 amit.gupta 365
                if iscod:
366
                    return 46, iscod, otgAvailable
8575 rajveer 367
 
19533 manish.sha 368
    if serviceable_location_cache.has_key(1) and serviceable_location_cache.get(1).has_key(destination_pin):
19476 manish.sha 369
        dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(1).get(destination_pin)
7627 rajveer 370
        if item_selling_price <= providerPrepaidLimit:
7608 rajveer 371
            iscod = iscod and item_selling_price <= websiteCodLimit
372
            otgAvailable = otgAvailable and item_selling_price >= 2000
20275 amit.gupta 373
            if iscod:
374
                return 1, iscod, otgAvailable
7981 rajveer 375
 
20275 amit.gupta 376
    if serviceable_location_cache.has_key(3) and serviceable_location_cache.get(3).has_key(destination_pin):
377
        dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(3).get(destination_pin)
378
        if item_selling_price <= providerPrepaidLimit:
379
            iscod = iscod and item_selling_price <= websiteCodLimit
380
            otgAvailable = otgAvailable and item_selling_price >= 2000
381
            return 3, iscod, otgAvailable
10185 amit.gupta 382
    return None, False, False    
5278 rajveer 383
 
6017 amar.kumar 384
def get_destination_code(providerId, pinCode):
385
    serviceableLocationDetail = ServiceableLocationDetails.query.filter_by(provider_id = providerId, dest_pincode = pinCode).one()
386
    return serviceableLocationDetail.dest_code
387
 
644 chandransh 388
def add_empty_AWBs(numbers, provider_id, type):
442 rajveer 389
    for number in numbers:
644 chandransh 390
        query = Awb.query.filter_by(awb_number = number, provider_id = provider_id)
444 rajveer 391
        try:
392
            query.one()
393
        except:    
644 chandransh 394
            awb = Awb()
444 rajveer 395
            awb.awb_number = number
644 chandransh 396
            awb.provider_id = provider_id
444 rajveer 397
            awb.is_available = True
644 chandransh 398
            awb.type = type
399
    session.commit()
442 rajveer 400
 
444 rajveer 401
def set_AWB_as_used(awb_number):
644 chandransh 402
    query = Awb.query.filter_by(awb_number = awb_number)
444 rajveer 403
    awb = query.one() 
404
    awb.is_available=False
405
    session.commit()
406
 
20924 kshitij.so 407
def get_awb(provider_id, logisticsTransactionId, type):
408
    query = Awb.query.with_lockmode("update").filter_by(provider_id = provider_id, is_available = True)  #check the provider thing
409
    if type == DeliveryType.PREPAID:
410
        query = query.filter_by(type="Prepaid")
411
    if type == DeliveryType.COD:
412
        query = query.filter_by(type="COD")
413
 
414
    additionalQuery = query
415
    query = query.filter_by(awbUsedFor=0)
416
 
417
    try:
418
        awb = query.first()
419
        if awb is None:
420
            additionalQuery = additionalQuery.filter_by(awbUsedFor=2)
421
            awb = additionalQuery.first()
422
        awb.is_available = False
423
        session.commit()
424
        return awb.awb_number
425
    except:
426
        raise LogisticsServiceException(103, "Unable to get an AWB for the given Provider: " + str(provider_id))
20724 kshitij.so 427
 
428
def get_empty_AWB(provider_id, logisticsTransactionId):
442 rajveer 429
    try:
20724 kshitij.so 430
        if logisticsTransactionId is None:
431
            return ""
432
        if provider_id ==1:
20745 kshitij.so 433
            bluedartAttribute = BluedartAttribute.get_by(logisticsTransactionId=logisticsTransactionId,name="awb")
434
            if bluedartAttribute is None:
435
                client = TransactionClient().get_client()
436
                orders_list = client.getGroupOrdersByLogisticsTxnId(logisticsTransactionId)
437
                bluedartResponse = BluedartService.generate_awb(orders_list)
438
                bluedartAttribute = BluedartAttribute()
439
                bluedartAttribute.logisticsTransactionId = logisticsTransactionId
440
                bluedartAttribute.name = "awb"
441
                bluedartAttribute.value = bluedartResponse.awbNo
442
                bluedartAttribute_destcode = BluedartAttribute()
443
                bluedartAttribute_destcode.logisticsTransactionId = logisticsTransactionId
444
                bluedartAttribute_destcode.name = "destCode"
445
                bluedartAttribute_destcode.value = bluedartResponse.destArea +"/"+ bluedartResponse.destLocation
446
                session.commit()
447
            return bluedartAttribute.value
20924 kshitij.so 448
        if provider_id  ==4:
449
            return get_awb(provider_id, logisticsTransactionId, DeliveryType.PREPAID)
442 rajveer 450
    except:
20724 kshitij.so 451
        traceback.print_exc()
644 chandransh 452
        raise LogisticsServiceException(103, "Unable to get an AWB for the given Provider: " + str(provider_id))
20724 kshitij.so 453
 
1137 chandransh 454
 
3103 chandransh 455
def get_free_awb_count(provider_id, type):
456
    count = Awb.query.filter_by(provider_id = provider_id, is_available = True, type=type).count()
1137 chandransh 457
    if count == None:
458
        count = 0
459
    return count
442 rajveer 460
 
644 chandransh 461
def get_shipment_info(awb_number, provider_id):
462
    awb = Awb.get_by(awb_number = awb_number, provider_id = provider_id)
463
    query = AwbUpdate.query.filter_by(awb = awb)
766 rajveer 464
    info = query.all()
465
    return info
466
 
6643 rajveer 467
def store_shipment_info(update):
468
    updates = AwbUpdate.query.filter_by(providerId = update.providerId, awbNumber  = update.awbNumber, location = update.location, date = to_py_date(update.date), status = update.status, description = update.description).all()
469
    if not updates:
470
        dupdate = AwbUpdate()
471
        dupdate.providerId = update.providerId
472
        dupdate.awbNumber  = update.awbNumber
473
        dupdate.location = update.location
474
        dupdate.date = to_py_date(update.date)
475
        dupdate.status = update.status
476
        dupdate.description = update.description
477
        session.commit()
478
 
1730 ankur.sing 479
def get_holidays(start_date, end_date):
480
    query = PublicHolidays.query
481
    if start_date != -1:
482
        query = query.filter(PublicHolidays.date >= to_py_date(start_date))
483
    if end_date != -1:
484
        query = query.filter(PublicHolidays.date <= to_py_date(end_date))
485
    holidays = query.all()
486
    holiday_dates = [to_java_date(datetime.datetime(*time.strptime(str(holiday.date), '%Y-%m-%d')[:3])) for holiday in holidays] 
487
    return holiday_dates
488
 
5527 anupam.sin 489
def get_provider_for_pickup_type(pickUp):
490
    return Provider.query.filter(Provider.pickup == pickUp).first().id
491
 
766 rajveer 492
def close_session():
493
    if session.is_active:
494
        print "session is active. closing it."
2823 chandransh 495
        session.close()
3376 rajveer 496
 
497
def is_alive():
498
    try:
499
        session.query(Awb.id).limit(1).one()
500
        return True
501
    except:
5555 rajveer 502
        return False
503
 
504
def get_all_pickup_stores():
5572 anupam.sin 505
    pickupStores = PickupStore.query.all()
506
    return pickupStores
5555 rajveer 507
 
508
def get_pickup_store(storeId):
5719 rajveer 509
    return PickupStore.query.filter_by(id = storeId).one()
510
 
511
def get_pickup_store_by_hotspot_id(hotspotId):
512
    return PickupStore.query.filter_by(hotspotId = hotspotId).one()
6322 amar.kumar 513
 
6524 rajveer 514
def add_pincode(provider, pincode, destCode, exp, cod, stationType, otgAvailable):
7914 rajveer 515
    provider = Provider.query.filter_by(id = provider).one()
6322 amar.kumar 516
    serviceableLocationDetails = ServiceableLocationDetails()
517
    serviceableLocationDetails.provider = provider
518
    serviceableLocationDetails.dest_pincode = pincode
519
    serviceableLocationDetails.dest_code = destCode
520
    serviceableLocationDetails.exp = exp
521
    serviceableLocationDetails.cod = cod
522
    serviceableLocationDetails.station_type = stationType
6524 rajveer 523
    serviceableLocationDetails.otgAvailable = otgAvailable
7733 manish.sha 524
    if provider.id == 1:
7627 rajveer 525
        codlimit = 10000
526
        prepaidlimit = 50000
7733 manish.sha 527
    elif provider.id == 3:
7627 rajveer 528
        codlimit = 25000
529
        prepaidlimit = 100000
7733 manish.sha 530
    elif provider.id == 6:
7627 rajveer 531
        codlimit = 25000
532
        prepaidlimit = 100000
533
    serviceableLocationDetails.providerPrepaidLimit = prepaidlimit
534
    serviceableLocationDetails.providerCodLimit = codlimit
535
    serviceableLocationDetails.websiteCodLimit = codlimit
536
    serviceableLocationDetails.storeCodLimit = codlimit
6322 amar.kumar 537
    session.commit()
538
 
6524 rajveer 539
def update_pincode(providerId, pincode, exp, cod, otgAvailable):
6615 amar.kumar 540
    serviceableLocationDetails = ServiceableLocationDetails.get_by(provider_id = providerId, dest_pincode = pincode)
6322 amar.kumar 541
    serviceableLocationDetails.exp = exp
542
    serviceableLocationDetails.cod = cod
6524 rajveer 543
    serviceableLocationDetails.otgAvailable = otgAvailable
7256 rajveer 544
    session.commit()
7567 rajveer 545
 
13146 manish.sha 546
def add_new_awbs(provider_id, isCod, awbs, awbUsedFor):
7567 rajveer 547
    provider = get_provider(provider_id)
548
    if isCod:
549
        dtype = 'Cod'
550
    else:
551
        dtype = 'Prepaid'
552
    for awb in awbs:
553
        a = Awb()
554
        a.type =  dtype
555
        a.is_available = True
556
        a.awb_number = awb
13146 manish.sha 557
        a.awbUsedFor = awbUsedFor
7567 rajveer 558
        a.provider = provider 
559
    session.commit()
7608 rajveer 560
    return True
7256 rajveer 561
 
562
def adjust_delivery_time(start_time, delivery_days):
563
    '''
564
    Returns the actual no. of days which will pass while 'delivery_days'
565
    no. of business days will pass since 'order_time'. 
566
    '''
567
    start_date = start_time.date()
568
    end_date = start_date + datetime.timedelta(days = delivery_days)
7272 amit.gupta 569
    holidays = get_holidays(to_java_date(start_time), -1)
7256 rajveer 570
    holidays = [to_py_date(holiday).date() for holiday in holidays]
571
 
572
    while start_date <= end_date:
573
        if start_date.weekday() == 6 or start_date in holidays:
574
            delivery_days = delivery_days + 1
575
            end_date = end_date + datetime.timedelta(days = 1)
576
        start_date = start_date + datetime.timedelta(days = 1)
577
 
578
    return delivery_days
7275 rajveer 579
 
580
def get_min_advance_amount(itemId, destination_pin, providerId, codAllowed):
581
    client = CatalogClient().get_client()
582
    sp = client.getStorePricing(itemId)
583
 
584
    if codAllowed:
585
        return sp.minAdvancePrice, True
586
    else:
20275 amit.gupta 587
        dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit  = serviceable_location_cache.get(providerId).get(destination_pin)
7275 rajveer 588
        if iscod:
589
            if providerId == 6:
7489 rajveer 590
                return max(sp.minAdvancePrice, sp.recommendedPrice - storeCodLimit), True
7275 rajveer 591
            if providerId == 3:
7489 rajveer 592
                return max(sp.minAdvancePrice, sp.recommendedPrice - storeCodLimit), True
7275 rajveer 593
            if providerId == 1:
7489 rajveer 594
                return max(sp.minAdvancePrice, sp.recommendedPrice - storeCodLimit), True
7275 rajveer 595
        else:
7425 rajveer 596
            return sp.recommendedPrice, False
7733 manish.sha 597
#Start:- Added by Manish Sharma for Multiple Pincode Updation on 05-Jul-2013
598
 
7786 manish.sha 599
def run_Logistics_Location_Info_Update(logisticsLocationInfoList, runCompleteUpdate):
600
    if runCompleteUpdate == True :
601
        serviceableLocationDetails = ServiceableLocationDetails.query.all()
602
        for serviceableLocationDetail in serviceableLocationDetails:
7841 manish.sha 603
            serviceableLocationDetail.exp = False
604
            serviceableLocationDetail.cod = False
7786 manish.sha 605
    for logisticsLocationInfo in logisticsLocationInfoList:
7841 manish.sha 606
        serviceableLocationDetail = ServiceableLocationDetails.get_by(provider_id = logisticsLocationInfo.providerId, dest_pincode = logisticsLocationInfo.pinCode)
7914 rajveer 607
        provider = Provider.query.filter_by(id = logisticsLocationInfo.providerId).one()
7841 manish.sha 608
        if serviceableLocationDetail:
609
            serviceableLocationDetail.exp = logisticsLocationInfo.expAvailable
610
            serviceableLocationDetail.cod = logisticsLocationInfo.codAvailable
611
            serviceableLocationDetail.otgAvailable = logisticsLocationInfo.otgAvailable
612
            serviceableLocationDetail.providerCodLimit = logisticsLocationInfo.codLimit
613
            serviceableLocationDetail.providerPrepaidLimit = logisticsLocationInfo.prepaidLimit
614
            serviceableLocationDetail.storeCodLimit = logisticsLocationInfo.codLimit
8219 manish.sha 615
            serviceableLocationDetail.websiteCodLimit = min(26000,logisticsLocationInfo.codLimit)
7841 manish.sha 616
        else:
617
            serviceableLocationDetail= ServiceableLocationDetails()
618
            serviceableLocationDetail.provider = provider
619
            serviceableLocationDetail.dest_pincode = logisticsLocationInfo.pinCode
620
            serviceableLocationDetail.dest_code = logisticsLocationInfo.destinationCode
621
            serviceableLocationDetail.exp = logisticsLocationInfo.expAvailable
622
            serviceableLocationDetail.cod = logisticsLocationInfo.codAvailable
623
            serviceableLocationDetail.station_type = 0
624
            serviceableLocationDetail.otgAvailable = logisticsLocationInfo.otgAvailable
625
            serviceableLocationDetail.providerCodLimit = logisticsLocationInfo.codLimit
626
            serviceableLocationDetail.providerPrepaidLimit = logisticsLocationInfo.prepaidLimit
627
            serviceableLocationDetail.storeCodLimit = logisticsLocationInfo.codLimit
8219 manish.sha 628
            serviceableLocationDetail.websiteCodLimit = min(26000,logisticsLocationInfo.codLimit)
7841 manish.sha 629
 
7870 rajveer 630
        deliveryEstimate = DeliveryEstimate.get_by(provider_id = logisticsLocationInfo.providerId, destination_pin = logisticsLocationInfo.pinCode, warehouse_location = logisticsLocationInfo.warehouseId) 
7841 manish.sha 631
        if deliveryEstimate:
632
            deliveryEstimate.warehouse_location= logisticsLocationInfo.warehouseId
633
            deliveryEstimate.delivery_time= logisticsLocationInfo.deliveryTime
634
            deliveryEstimate.delivery_delay= logisticsLocationInfo.delivery_delay
19421 manish.sha 635
            deliveryEstimate.providerZoneCode = logisticsLocationInfo.zoneCode
7841 manish.sha 636
        else:
637
            deliveryEstimate = DeliveryEstimate()
638
            deliveryEstimate.destination_pin= logisticsLocationInfo.pinCode
639
            deliveryEstimate.provider = provider
640
            deliveryEstimate.warehouse_location= logisticsLocationInfo.warehouseId
641
            deliveryEstimate.delivery_time= logisticsLocationInfo.deliveryTime
642
            deliveryEstimate.delivery_delay= logisticsLocationInfo.delivery_delay
19421 manish.sha 643
            deliveryEstimate.providerZoneCode = logisticsLocationInfo.zoneCode
7733 manish.sha 644
    session.commit()
7786 manish.sha 645
 
7733 manish.sha 646
#End:- Added by Manish Sharma for Multiple Pincode Updation on 05-Jul-2013             
7275 rajveer 647
 
12895 manish.sha 648
def get_first_delivery_estimate_for_wh_location(pincode, whLocation):
649
    delEstimate = DeliveryEstimate.query.filter(DeliveryEstimate.destination_pin == pincode).filter(DeliveryEstimate.warehouse_location == whLocation).first()
650
    if delEstimate is None:
651
        return -1
652
    else:
653
        return 1
13146 manish.sha 654
 
655
def get_provider_limit_details_for_pincode(provider, pincode):
656
    serviceAbleDetails = ServiceableLocationDetails.get_by(provider_id = provider, dest_pincode = pincode)
657
    returnDataMap = {}
658
    if serviceAbleDetails:
659
        returnDataMap["websiteCodLimit"] = str(serviceAbleDetails.websiteCodLimit)
19230 manish.sha 660
        returnDataMap["providerCodLimit"] = str(serviceAbleDetails.providerCodLimit)
13146 manish.sha 661
        returnDataMap["providerPrepaidLimit"] = str(serviceAbleDetails.providerPrepaidLimit)
662
 
663
    return returnDataMap
664
 
665
def get_new_empty_awb(providerId, type, orderQuantity):
666
    query = Awb.query.with_lockmode("update").filter_by(provider_id = providerId, is_available = True)  #check the provider thing
667
    if type == DeliveryType.PREPAID:
668
        query = query.filter_by(type="Prepaid")
669
    if type == DeliveryType.COD:
670
        query = query.filter_by(type="COD")
671
 
672
    additionalQuery = query
673
    if orderQuantity == 1:
674
        query = query.filter_by(awbUsedFor=0)
675
    if orderQuantity >1:
676
        query = query.filter_by(awbUsedFor=1) 
677
 
678
    try:
679
        awb = query.first()
680
        if awb is None:
681
            additionalQuery = additionalQuery.filter_by(awbUsedFor=2)
682
            awb = additionalQuery.first()
683
        awb.is_available = False
684
        session.commit()
685
        return awb.awb_number
686
    except:
687
        raise LogisticsServiceException(103, "Unable to get an AWB for the given Provider: " + str(providerId))
19421 manish.sha 688
 
19474 manish.sha 689
def get_costing_and_delivery_estimate_for_pincode(pincode, transactionAmount, isCod, weight, billingWarehouseId, isCompleteTxn):
690
    print pincode, transactionAmount, isCod, weight, billingWarehouseId
19421 manish.sha 691
    deliveryEstimate = {}
692
    logsiticsCosting = {}
693
    providerCostingMap = {}
694
    serviceability = {}
695
 
696
    for providerId in serviceable_location_cache.keys():
697
        if serviceable_location_cache.has_key(providerId) and serviceable_location_cache.get(providerId).has_key(pincode):
19474 manish.sha 698
            dest_code, exp, iscod, otgAvailable, websiteCodLimit, storeCodLimit, providerPrepaidLimit, providerCodLimit = serviceable_location_cache.get(providerId).get(pincode)
19421 manish.sha 699
            if isCod and iscod:
19474 manish.sha 700
                if not isCompleteTxn:
701
                    if transactionAmount <= providerCodLimit:
702
                        serviceability[providerId] = serviceable_location_cache.get(providerId).get(pincode)
703
                    else:
704
                        continue
705
                else:
706
                    serviceability[providerId] = serviceable_location_cache.get(providerId).get(pincode)
19421 manish.sha 707
            elif isCod and not iscod:
708
                continue
709
            else:
19474 manish.sha 710
                if not isCompleteTxn:
711
                    if transactionAmount <= providerPrepaidLimit:
712
                        serviceability[providerId] = serviceable_location_cache.get(providerId).get(pincode)
713
                    else:
714
                        continue
715
                else:
716
                    serviceability[providerId] = serviceable_location_cache.get(providerId).get(pincode)
19421 manish.sha 717
 
718
    warehouse_location = warehouse_location_cache.get(billingWarehouseId)
719
    if warehouse_location is None:
720
        warehouse_location = 0
721
 
722
    noCostFoundCount = 0
723
    if len(serviceability)>0:
724
        for providerId, serviceableDetails in serviceability.items():
725
            delivery_time = delivery_estimate_cache[pincode, providerId, warehouse_location][0]
726
            delivery_delay = delivery_estimate_cache[pincode, providerId, warehouse_location][1]
727
            zoneCode = delivery_estimate_cache[pincode, providerId, warehouse_location][2]
728
            sla = delivery_time + delivery_delay
729
            if deliveryEstimate.has_key(sla):
730
                estimate = deliveryEstimate.get(sla)
731
                estimate.append(providerId)
732
                deliveryEstimate[sla] = estimate
733
            else:
734
                estimate = []
735
                estimate.append(providerId)
736
                deliveryEstimate[sla] = estimate
737
 
738
            logisticsCost = 0
739
            codCollectionCharges = 0    
740
            logisticsCostObj = None 
741
            if provider_costing_sheet.has_key(providerId) and provider_costing_sheet.get(providerId).has_key(zoneCode):
742
                logisticsCostObj = provider_costing_sheet.get(providerId).get(zoneCode)
743
                logisticsCost = logisticsCostObj.initialLogisticsCost
744
                if weight > logisticsCostObj.initialWeightUpperLimit:
745
                    additionalWeight = weight-logisticsCostObj.initialWeightUpperLimit
19663 manish.sha 746
                    additionalWeight = round(additionalWeight,0)
19483 manish.sha 747
                    additionalCostMultiplier = math.ceil(additionalWeight/logisticsCostObj.additionalUnitWeight)
19421 manish.sha 748
                    additionalCost = additionalCostMultiplier*logisticsCostObj.additionalUnitLogisticsCost
749
                    logisticsCost = logisticsCost + additionalCost
750
                if isCod:
751
                    if logisticsCostObj.codCollectionFactor:
19474 manish.sha 752
                        codCollectionCharges = max(logisticsCostObj.minimumCodCollectionCharges, (transactionAmount*logisticsCostObj.codCollectionFactor)/100)
753
                        logisticsCost = logisticsCost + max(logisticsCostObj.minimumCodCollectionCharges, (transactionAmount*logisticsCostObj.codCollectionFactor)/100)
19421 manish.sha 754
                    else:
755
                        codCollectionCharges = logisticsCostObj.minimumCodCollectionCharges
756
                        logisticsCost = logisticsCost + logisticsCostObj.minimumCodCollectionCharges
757
 
19474 manish.sha 758
                if logsiticsCosting.has_key(round(logisticsCost,0)):
759
                    costingList = logsiticsCosting.get(round(logisticsCost,0))
19421 manish.sha 760
                    costingList.append(providerId)
19474 manish.sha 761
                    logsiticsCosting[round(logisticsCost,0)] = costingList
19421 manish.sha 762
                else:
763
                    costingList = []
764
                    costingList.append(providerId)
19474 manish.sha 765
                    logsiticsCosting[round(logisticsCost,0)] = costingList                    
19421 manish.sha 766
 
767
                providerCostingMap[providerId] = [logisticsCost,codCollectionCharges]
768
            else:
769
                noCostFoundCount = noCostFoundCount +1
770
                continue
771
    else:
19474 manish.sha 772
        print "No provider assigned for pincode: " + str(pincode)
19535 manish.sha 773
        raise LogisticsServiceException(103, "Unable to get Provider for given pincode: " + str(pincode)+" Amount:- "+str(transactionAmount)+" Weight:- "+ str(weight))
19421 manish.sha 774
 
775
 
776
    if noCostFoundCount == len(serviceability):
19474 manish.sha 777
        print "No Costing Found for this pincode: " + str(pincode) +" for any of the provider"
19535 manish.sha 778
        raise LogisticsServiceException(103, "Unable to get Provider for given pincode: " + str(pincode)+" Amount:- "+str(transactionAmount)+" Weight:- "+ str(weight)+". Due to no costing found")
19421 manish.sha 779
 
780
    allSla = sorted(deliveryEstimate.keys())
781
    if len(allSla)==1:
782
        allEligibleProviders = deliveryEstimate.get(allSla[0])
783
        if len(allEligibleProviders)==1:
19474 manish.sha 784
            try:
19421 manish.sha 785
                costingDetails = providerCostingMap.get(allEligibleProviders[0])
786
                delEstCostObj = DeliveryEstimateAndCosting()
787
                delEstCostObj.logistics_provider_id = allEligibleProviders[0]
788
                delEstCostObj.pincode = pincode
789
                delEstCostObj.deliveryTime = delivery_estimate_cache[pincode, allEligibleProviders[0], warehouse_location][0]
790
                delEstCostObj.delivery_delay = delivery_estimate_cache[pincode, allEligibleProviders[0], warehouse_location][1]
791
                delEstCostObj.codAllowed = serviceability[allEligibleProviders[0]][2]
792
                delEstCostObj.otgAvailable = serviceability[allEligibleProviders[0]][3]
793
                delEstCostObj.logisticsCost = costingDetails[0]-costingDetails[1]
794
                delEstCostObj.codCollectionCharges = costingDetails[1]
795
                return delEstCostObj
19474 manish.sha 796
            except:
19535 manish.sha 797
                raise LogisticsServiceException(103, "Unable to get Provider for given pincode: " + str(pincode)+" Amount:- "+str(transactionAmount)+" Weight:- "+ str(weight)+".")
19421 manish.sha 798
        else:
799
            costingListOrder = []
800
            for providerId in allEligibleProviders:
19474 manish.sha 801
                costingDetails = providerCostingMap.get(providerId)
802
                if costingDetails and costingDetails[0] not in costingListOrder:
803
                    costingListOrder.append(round(costingDetails[0],0))
804
 
805
            costingListOrder = sorted(costingListOrder)
806
            eligibleProviders = logsiticsCosting.get(costingListOrder[0])
807
            for providerId in eligibleProviders:
808
                if providerCostingMap.has_key(providerId):
809
                    costingDetails = providerCostingMap.get(providerId)
19421 manish.sha 810
                    delEstCostObj = DeliveryEstimateAndCosting()
19474 manish.sha 811
                    delEstCostObj.logistics_provider_id = providerId
19421 manish.sha 812
                    delEstCostObj.pincode = pincode
19474 manish.sha 813
                    delEstCostObj.deliveryTime = delivery_estimate_cache[pincode, providerId, warehouse_location][0]
814
                    delEstCostObj.delivery_delay = delivery_estimate_cache[pincode, providerId, warehouse_location][1]
815
                    delEstCostObj.codAllowed = serviceability[providerId][2]
816
                    delEstCostObj.otgAvailable = serviceability[providerId][3]
19421 manish.sha 817
                    delEstCostObj.logisticsCost = costingDetails[0]-costingDetails[1]
818
                    delEstCostObj.codCollectionCharges = costingDetails[1]
819
                    return delEstCostObj
19474 manish.sha 820
                else:
821
                    continue
19535 manish.sha 822
            raise LogisticsServiceException(103, "Unable to get Provider for given pincode: " + str(pincode)+" Amount:- "+str(transactionAmount)+" Weight:- "+ str(weight)+".")
19474 manish.sha 823
    else:
824
        allEligibleProviders = []
825
        virtualDelayCostMap = {}
826
        virtualCommercialsCostMap = {} 
827
        for sla in allSla:
828
            if sla-allSla[0]<=1:
829
                consideredProviders = deliveryEstimate.get(sla)
830
                for providerId in consideredProviders:
831
                    if isCod and providerId in [7,46]:
832
                        virtualCommercialsCostMap[providerId] = 10
833
                    if providerId not in allEligibleProviders:
834
                        allEligibleProviders.append(providerId)
835
                    virtualDelayCostMap[providerId] = 0
836
            elif sla-allSla[0]==2:
837
                consideredProviders = deliveryEstimate.get(sla)
838
                for providerId in consideredProviders:
839
                    if isCod and providerId in [7,46]:
840
                        virtualCommercialsCostMap[providerId] = 10
841
                    if providerId not in allEligibleProviders:
842
                        allEligibleProviders.append(providerId)
843
                    virtualDelayCostMap[providerId] = 20+round((0.3*transactionAmount)/100,0)
844
            elif sla-allSla[0]==3:
845
                consideredProviders = deliveryEstimate.get(sla)
846
                for providerId in consideredProviders:
847
                    if isCod and providerId in [7,46]:
848
                        virtualCommercialsCostMap[providerId] = 10
849
                    if providerId not in allEligibleProviders:
850
                        allEligibleProviders.append(providerId)
851
                    virtualDelayCostMap[providerId] = 40+round((0.6*transactionAmount)/100,0)
852
 
853
        costingListOrder = []
854
        costingListMap = {}
855
        for providerId in allEligibleProviders:
856
            costingDetails = providerCostingMap.get(providerId)
857
            if costingDetails:
858
                cost = round(costingDetails[0],0)
859
                if virtualDelayCostMap.has_key(providerId):
860
                    cost = cost + virtualDelayCostMap.get(providerId)
861
                if virtualCommercialsCostMap.has_key(providerId):
862
                    cost = cost + virtualCommercialsCostMap.get(providerId)
863
                if costingListMap.has_key(cost):
864
                    providers = costingListMap.get(cost)
865
                    providers.append(providerId)                       
866
                    costingListMap[cost] = providers 
867
                else:
868
                    providers = []
869
                    providers.append(providerId)                       
870
                    costingListMap[cost] = providers  
871
                if cost not in costingListOrder:
872
                    costingListOrder.append(cost)
873
 
874
        costingListOrder = sorted(costingListOrder)
875
 
876
        print costingListMap
877
        eligibleProviders = costingListMap.get(costingListOrder[0])
878
        for providerId in eligibleProviders:
879
            if providerCostingMap.has_key(providerId):
880
                costingDetails = providerCostingMap.get(providerId)
19421 manish.sha 881
                delEstCostObj = DeliveryEstimateAndCosting()
19474 manish.sha 882
                delEstCostObj.logistics_provider_id = providerId
19421 manish.sha 883
                delEstCostObj.pincode = pincode
19474 manish.sha 884
                delEstCostObj.deliveryTime = delivery_estimate_cache[pincode, providerId, warehouse_location][0]
885
                delEstCostObj.delivery_delay = delivery_estimate_cache[pincode, providerId, warehouse_location][1]
886
                delEstCostObj.codAllowed = serviceability[providerId][2]
887
                delEstCostObj.otgAvailable = serviceability[providerId][3]
19421 manish.sha 888
                delEstCostObj.logisticsCost = costingDetails[0]-costingDetails[1]
889
                delEstCostObj.codCollectionCharges = costingDetails[1]
890
                return delEstCostObj
19474 manish.sha 891
            else:
892
                continue
20745 kshitij.so 893
        raise LogisticsServiceException(103, "Unable to get Provider for given pincode: " + str(pincode)+" Amount:- "+str(transactionAmount)+" Weight:- "+ str(weight)+".")
894
 
895
def get_bluedart_attributes_for_logistics_txn_id(logisticsTxnId, name):
896
    bluedartAttr =  BluedartAttribute.get_by(logisticsTransactionId=logisticsTxnId,name=name)
897
    if bluedartAttr is None:
898
        raise LogisticsServiceException(103, "Unable to get bluedart attributes for logisticsTxnId "+logisticsTxnId+" and name "+name)
899
    return bluedartAttr