Subversion Repositories SmartDukaan

Rev

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

Rev Author Line No. Line
557 chandransh 1
'''
2
Created on 10-May-2010
3
 
4
@author: ashish
5
'''
6
from elixir import *
3554 varun.gupt 7
from shop2020.model.v1.user.impl.Dataservice import Cart, Line, Address, User, Discount
2026 varun.gupt 8
from shop2020.thriftpy.model.v1.user.ttypes import CartStatus, LineStatus, ShoppingCartException,\
9
    PromotionException
557 chandransh 10
import datetime
576 chandransh 11
from shop2020.utils.Utils import to_py_date, to_java_date
557 chandransh 12
 
576 chandransh 13
from shop2020.thriftpy.model.v1.order.ttypes import Transaction as TTransaction,\
685 chandransh 14
    TransactionStatus as TTransactionStatus, Order as TOrder, LineItem as TLineItem, OrderStatus 
557 chandransh 15
 
576 chandransh 16
from shop2020.thriftpy.model.v1.catalog.ttypes import Item as TItem
844 chandransh 17
from shop2020.thriftpy.logistics.ttypes import LogisticsInfo as TLogisticsInfo,\
4642 mandeep.dh 18
    LogisticsServiceException, DeliveryType
576 chandransh 19
 
20
from shop2020.clients.TransactionClient import TransactionClient
3133 rajveer 21
from shop2020.clients.CatalogClient import CatalogClient
576 chandransh 22
from shop2020.clients.LogisticsClient import LogisticsClient
23
from shop2020.model.v1 import user
1976 varun.gupt 24
from shop2020.clients.PromotionClient import PromotionClient
2026 varun.gupt 25
from shop2020.model.v1.user.impl import UserDataAccessors
576 chandransh 26
 
557 chandransh 27
def get_cart(user_id):
28
    query = Cart.query.filter_by(user_id=user_id)      
29
    query = query.filter_by(cart_status = CartStatus.ACTIVE)
30
    try:
31
        cart = query.one()
32
    except:
33
        return None
34
#        raise ShoppingCartException(101, "Cart does not exist")
35
    return cart
36
 
37
def get_cart_by_id(id):
38
    cart = Cart.get_by(id=id)
39
    return cart
40
 
41
def create_cart(user_id):
42
    cart = get_cart(user_id)
43
    if not cart: 
44
        cart = Cart()
45
        cart.user_id = user_id
46
        cart.created_on = datetime.datetime.now()
47
        cart.updated_on = datetime.datetime.now()
48
        cart.cart_status = CartStatus.ACTIVE
49
        session.commit()
50
    return cart
51
 
52
def get_cart_by_user_id_and_status(user_id, status):
53
    query = Cart.query.filter_by(user_id=user_id)
54
    if status:
55
        query = query.filter_by(cart_status=status)
56
    carts = query.all()
57
    return carts
58
 
59
def get_carts_by_status(status):
60
    return Cart.query.filter_by(cart_status=status).all()
61
 
62
def get_carts_between(start_time, end_time, status):
63
    init_time = to_py_date(start_time)
64
    finish_time = to_py_date(end_time)
65
 
66
    query = Cart.query
67
    if status:
68
        query = query.filter(Cart.cart_status==status)
69
    if init_time:
70
        query = query.filter(Cart.created_on >= init_time)
71
    if finish_time:
72
        query = query.filter(Cart.created_on <= finish_time)
73
 
74
    carts = query.all()
75
    return carts
76
 
643 chandransh 77
def get_line(item_id, cart_id, status, single):
557 chandransh 78
    #get cart first 
79
    try:
80
        found_cart = Cart.get_by(id=cart_id)
81
    except:
82
        raise ShoppingCartException(101, "cart not found ")
643 chandransh 83
    query = Line.query.filter_by(cart = found_cart, item_id = item_id)
557 chandransh 84
 
85
    if status:
86
        query = query.filter_by(line_status = status)
87
    else:
88
        query = query.filter_by(line_status = LineStatus.LINE_ACTIVE)
89
    try:
90
        if single:
91
            return query.one()
92
        else:
93
            return query.all()
94
    except:
95
        return None
96
 
97
def change_cart_status(cart_id, status):
98
    cart = get_cart_by_id(id)
99
    if not cart:
100
        raise ShoppingCartException(101, "no cart attached to this id")
101
    if not status:
102
        raise ShoppingCartException(101, "invalid status")
690 chandransh 103
    cart.cart_status = status
557 chandransh 104
    session.commit()
105
 
3557 rajveer 106
def add_item_to_cart(cart_id, item_id, quantity, sourceId):
557 chandransh 107
    if not item_id:
108
        raise ShoppingCartException(101, "item_id cannot be null")
109
 
110
    if not quantity:
111
        raise ShoppingCartException(101, "quantity cannot be null")    
643 chandransh 112
 
2983 chandransh 113
    cart = Cart.get_by(id = cart_id)    
557 chandransh 114
    if not cart:
115
        raise ShoppingCartException(101, "no cart attached to this id")
2983 chandransh 116
    retval = ""
3133 rajveer 117
    inventory_client = CatalogClient().get_client()
3557 rajveer 118
    item = inventory_client.getItemForSource(item_id, sourceId)
2983 chandransh 119
    item_shipping_info = inventory_client.isActive(item_id)
120
    if not item_shipping_info.isActive:
2035 rajveer 121
        return inventory_client.getItemStatusDescription(item_id)
557 chandransh 122
 
643 chandransh 123
    current_time = datetime.datetime.now()
124
    cart.updated_on = current_time
125
    line = get_line(item_id, cart_id, None,True)
126
    if line:
127
        #change the quantity only
128
        line.quantity = quantity
685 chandransh 129
        line.updated_on = current_time
643 chandransh 130
    else:
131
        line = Line()
132
        line.cart = cart
133
        line.item_id = item_id
134
        line.quantity = quantity
135
        line.created_on = current_time
136
        line.updated_on = current_time
3557 rajveer 137
        line.actual_price = item.sellingPrice
643 chandransh 138
        line.line_status = LineStatus.LINE_ACTIVE
557 chandransh 139
    session.commit()
2983 chandransh 140
    return retval
557 chandransh 141
 
142
def delete_item_from_cart(cart_id, item_id):
143
    if not item_id:
144
        raise ShoppingCartException(101, "item_id cannot be null")
685 chandransh 145
    cart = Cart.get_by(id = cart_id)
146
    if not cart:
147
        raise ShoppingCartException(101, "no cart attached to this id")
643 chandransh 148
    item = get_line(item_id, cart_id, None, True)
3554 varun.gupt 149
    count_deleted_discounts = delete_discounts_for_line(item)
557 chandransh 150
    item.delete()
685 chandransh 151
    current_time = datetime.datetime.now()
152
    cart.updated_on = current_time
557 chandransh 153
    session.commit()
154
 
3554 varun.gupt 155
def delete_discounts_for_line(item_line):
156
    count_deleted = Discount.query.filter_by(line = item_line).delete()
157
    session.commit()
158
    return count_deleted
159
 
160
def delete_discounts_from_cart(cart_id, cart = None):
161
    if cart is None:
162
        if cart_id is None:
163
            raise ShoppingCartException(101, 'cart_id and cart, both cannot be null')
164
        else:
165
            cart = Cart.get_by(id = cart_id)
166
 
167
    if cart.lines:
168
        for line in cart.lines:
169
            delete_discounts_for_line(line)
170
 
171
def save_discounts(discounts):
172
    if not discounts:
173
        raise ShoppingCartException(101, 'discounts be null')
174
 
175
    if len(discounts) > 0:
176
        cart = Cart.get_by(id = discounts[0].cart_id)
177
 
178
        for t_discount in discounts:
179
            line = Line.query.filter_by(cart = cart, item_id = t_discount.item_id).first()
180
            if line is not None:
181
                discount = Discount()
182
                discount.line = line
183
                discount.discount = t_discount.discount
184
                discount.quantity = t_discount.quantity
185
                session.commit()
186
 
557 chandransh 187
def change_item_status(cart_id, item_id, status):
188
    if not status:
189
        raise ShoppingCartException(101, "Status cannot be made null")
685 chandransh 190
    line = get_line(item_id, cart_id, None, True)
191
    if line:
192
        line.line_status = status
193
        current_time = datetime.datetime.now()
194
        line.updated_on = current_time
195
        line.cart.updated_on = current_time
557 chandransh 196
        session.commit()
197
    else:
685 chandransh 198
        raise ShoppingCartException(101, "Unable to probe the line you desired")
557 chandransh 199
 
200
def add_address_to_cart(cart_id, address_id):
201
    if not cart_id:
202
        raise ShoppingCartException(101, "cart id cannot be made null")
203
 
204
    if not address_id:
205
        raise ShoppingCartException(101, "address id cannot be made null")
206
 
207
    cart = get_cart_by_id(cart_id)
208
    if not cart:
209
        raise ShoppingCartException(101, "no cart for this id")
576 chandransh 210
 
211
    address = Address.get_by(id=address_id)
212
    if not address:
213
        raise ShoppingCartException(101, "No address for this id")
214
 
557 chandransh 215
    cart.address_id = address_id
685 chandransh 216
    current_time = datetime.datetime.now()
716 rajveer 217
    #cart.updated_on = current_time
557 chandransh 218
    session.commit()
219
 
1976 varun.gupt 220
def apply_coupon_to_cart(cart_id, coupon_code, total_price, discounted_price):
221
    cart = get_cart_by_id(cart_id)
222
    if not cart:
223
        raise ShoppingCartException(101, "no cart attached to this id")
224
    cart.total_price = total_price
225
    cart.discounted_price = discounted_price
226
    cart.coupon_code = coupon_code
227
    session.commit()
228
 
229
def remove_coupon(cart_id):
230
    cart = get_cart_by_id(cart_id)
231
    if not cart:
232
        raise ShoppingCartException(101, "no cart attached to this id")
2261 varun.gupt 233
 
234
    #Resetting discounted price of each line in cart to Null
235
    for line in cart.lines:
236
        line.discounted_price = None
237
 
3619 chandransh 238
    delete_discounts_from_cart(cart.id, cart=cart)
1976 varun.gupt 239
    cart.discounted_price = None
240
    cart.coupon_code = None
241
    session.commit()
242
 
3858 vikas 243
def commit_cart(cart_id, sessionSource, sessionTime, firstSource, firstSourceTime):   
690 chandransh 244
    cart = get_cart_by_id(cart_id)   
557 chandransh 245
    #now we have a cart. Need to create a transaction with it
576 chandransh 246
    txn = TTransaction()
247
    txn.shoppingCartid = cart_id
248
    txn.customer_id = cart.user_id
249
    txn.createdOn = to_java_date(datetime.datetime.now())
250
    txn.transactionStatus = TTransactionStatus.INIT
251
    txn.statusDescription = "New Order"
2219 varun.gupt 252
    txn.coupon_code = cart.coupon_code
2815 vikas 253
    txn.sessionSource = sessionSource
254
    txn.sessionStartTime = sessionTime
3858 vikas 255
    txn.firstSource = firstSource
256
    txn.firstSourceTime = firstSourceTime
557 chandransh 257
 
576 chandransh 258
    txn.orders = create_orders(cart)
259
 
260
    transaction_client = TransactionClient().get_client()
261
    txn_id = transaction_client.createTransaction(txn)
262
    session.commit()
263
 
685 chandransh 264
    #new_cart = create_cart(cart.user_id)
265
    #user = User.get_by(id=cart.user_id)
266
    #user.active_cart_id = new_cart.id
267
    #session.commit()
576 chandransh 268
    return txn_id
269
 
270
def create_orders(cart):
557 chandransh 271
    cart_lines = cart.lines
576 chandransh 272
    orders = []
273
 
557 chandransh 274
    for line in cart_lines:
576 chandransh 275
        if line.line_status == LineStatus.LINE_ACTIVE:
3554 varun.gupt 276
            quantity_remaining_for_order = line.quantity
277
 
278
            for discount in line.discounts:
279
                i = 0
280
                while i < discount.quantity:
281
                    t_line_item = create_line_item(line.item_id, line.actual_price - discount.discount)
282
                    t_order = create_order(cart.user_id, cart.address_id, t_line_item)
283
                    orders.append(t_order)
284
                    i += 1
285
                quantity_remaining_for_order -= discount.quantity
286
 
576 chandransh 287
            i = 0
3554 varun.gupt 288
            while i < quantity_remaining_for_order:
289
                t_line_item = create_line_item(line.item_id, line.actual_price)
576 chandransh 290
                t_order = create_order(cart.user_id, cart.address_id, t_line_item)
291
                orders.append(t_order)
292
                i += 1
293
    return orders
294
 
295
def create_order(user_id, address_id, t_line_item):
296
    user = User.get_by(id=user_id)
297
    address = Address.get_by(id=address_id)
298
    t_order = TOrder()
557 chandransh 299
 
576 chandransh 300
    t_order.customer_id = user.id
301
    t_order.customer_email = user.email
302
 
910 rajveer 303
    t_order.customer_name = address.name
576 chandransh 304
    t_order.customer_pincode = address.pin
738 chandransh 305
    t_order.customer_address1 = address.line_1
306
    t_order.customer_address2 = address.line_2
669 chandransh 307
    t_order.customer_city = address.city
308
    t_order.customer_state = address.state
576 chandransh 309
    t_order.customer_mobilenumber = address.phone
310
 
311
    t_order.total_amount = t_line_item.total_price
1976 varun.gupt 312
 
576 chandransh 313
    t_order.total_weight = t_line_item.total_weight
314
    t_order.lineitems = [t_line_item]
315
 
690 chandransh 316
    t_order.status = OrderStatus.PAYMENT_PENDING
970 chandransh 317
    t_order.statusDescription = "Payment Pending"
576 chandransh 318
    t_order.created_timestamp = to_java_date(datetime.datetime.now())
319
 
320
    return t_order
321
 
3768 vikas 322
def create_line_item(item_id, final_price, quantity=1):
3133 rajveer 323
    inventory_client = CatalogClient().get_client()
636 rajveer 324
    item = inventory_client.getItem(item_id)
576 chandransh 325
    t_line_item = TLineItem()
963 chandransh 326
    t_line_item.productGroup = item.productGroup
327
    t_line_item.brand = item.brand
636 rajveer 328
    t_line_item.model_number = item.modelNumber
669 chandransh 329
    if item.color is None or item.color == "NA":
330
        t_line_item.color = ""
331
    else:
917 chandransh 332
        t_line_item.color = item.color
963 chandransh 333
    t_line_item.model_name = item.modelName
636 rajveer 334
    t_line_item.extra_info = item.featureDescription
702 chandransh 335
    t_line_item.item_id = item.id
3768 vikas 336
    t_line_item.quantity = quantity
1983 varun.gupt 337
 
3554 varun.gupt 338
    t_line_item.unit_price = final_price
3768 vikas 339
    t_line_item.total_price = final_price * quantity
1983 varun.gupt 340
 
636 rajveer 341
    t_line_item.unit_weight = item.weight
4172 rajveer 342
    t_line_item.total_weight = item.weight if item.weight is None else item.weight * quantity
343
    t_line_item.dealText = item.bestDealText
4295 varun.gupt 344
 
4312 rajveer 345
    if item.warrantyPeriod:
346
        #Computing Manufacturer Warranty expiry date
347
        today = datetime.date.today()
348
        expiry_year = today.year + int((today.month + item.warrantyPeriod) / 12)
349
        expiry_month = (today.month + item.warrantyPeriod) % 12
350
 
4295 varun.gupt 351
        try:
4312 rajveer 352
            expiry_date = datetime.datetime(expiry_year, expiry_month, today.day, 23, 59, 59, 999999)
4295 varun.gupt 353
        except ValueError:
354
            try:
4312 rajveer 355
                expiry_date = datetime.date(expiry_year, expiry_month, (today.day - 1), 23, 59, 59, 999999)
4295 varun.gupt 356
            except ValueError:
4312 rajveer 357
                try:
358
                    expiry_date = datetime.date(expiry_year, expiry_month, (today.day - 2), 23, 59, 59, 999999)
359
                except ValueError:
360
                    expiry_date = datetime.date(expiry_year, expiry_month, (today.day - 3), 23, 59, 59, 999999)
361
 
362
        t_line_item.warrantry_expiry_timestamp = to_java_date(expiry_date)
363
 
576 chandransh 364
    return t_line_item
365
 
3557 rajveer 366
def validate_cart(cartId, sourceId):
3133 rajveer 367
    inventory_client = CatalogClient().get_client()
576 chandransh 368
    logistics_client = LogisticsClient().get_client()
1976 varun.gupt 369
    promotion_client = PromotionClient().get_client()
1466 ankur.sing 370
    retval = ""
557 chandransh 371
    # No need to validate duplicate items since there are only two ways
372
    # to add items to a cart and both of them check whether the item being
373
    # added is a duplicate of an already existing item.
563 chandransh 374
    cart = Cart.get_by(id=cartId)
375
    cart_lines = cart.lines
776 rajveer 376
    customer_pincode = None
690 chandransh 377
    current_time = datetime.datetime.now()
576 chandransh 378
    if cart.address_id:
379
        address = Address.get_by(id=cart.address_id)
380
        customer_pincode = address.pin
776 rajveer 381
    if not customer_pincode:
785 rajveer 382
        user = User.get_by(active_cart_id = cartId)
383
        default_address_id = user.default_address_id
776 rajveer 384
        if default_address_id:
385
            address = Address.get_by(id = default_address_id)
386
            customer_pincode = address.pin
387
    if not customer_pincode:
388
        #FIXME should not be hard coded. May be we can pick from config server.
389
        customer_pincode = "110001"
1976 varun.gupt 390
    cart.total_price = 0
563 chandransh 391
    for line in cart_lines:
612 chandransh 392
        old_estimate = line.estimate
636 rajveer 393
        item_id = line.item_id
3557 rajveer 394
        item = inventory_client.getItemForSource(item_id, sourceId)
2983 chandransh 395
        item_shipping_info = inventory_client.isActive(item_id) 
396
        if item_shipping_info.isActive:
397
            if item_shipping_info.isRisky and item_shipping_info.quantity < line.quantity:
398
                line.quantity = 1
399
                retval = "Try adding a smaller quantity of " + item.brand + " " + item.modelNumber + " (" + item.color + ")"
400
 
2139 chandransh 401
            line.actual_price = item.sellingPrice 
402
            cart.total_price = cart.total_price + (line.actual_price * line.quantity)
776 rajveer 403
            try:
4642 mandeep.dh 404
                item_delivery_estimate = logistics_client.getLogisticsEstimation(item_id, customer_pincode, DeliveryType.PREPAID).deliveryTime
844 chandransh 405
            except LogisticsServiceException:
406
                item_delivery_estimate = -1
407
                #TODO Use the exception clause to set the retval appropriately
408
            except :
409
                item_delivery_estimate = -1
776 rajveer 410
            if old_estimate != item_delivery_estimate:
411
                line.estimate = item_delivery_estimate
412
                cart.updated_on = current_time
1466 ankur.sing 413
                if old_estimate != None:
414
                    retval = "Delivery Estimates updated."
576 chandransh 415
        else:
563 chandransh 416
            line.delete()
1466 ankur.sing 417
            retval = "Some items have been removed from the cart."
716 rajveer 418
    if cart.checked_out_on is not None:
419
        if cart.updated_on > cart.checked_out_on:
844 chandransh 420
            cart.checked_out_on = None
1466 ankur.sing 421
            if retval == "":
422
                retval = "Your cart has been updated after the last checkout."
612 chandransh 423
    session.commit()
1976 varun.gupt 424
 
425
    if cart.coupon_code is not None:
2026 varun.gupt 426
        try:
427
            updated_cart = promotion_client.applyCoupon(cart.coupon_code, cart.id)
428
            for t_line in updated_cart.lines:
1976 varun.gupt 429
            #Find the line in the database which corresponds to this line
2026 varun.gupt 430
                line = Line.query.filter_by(cart = cart).filter_by(item_id = t_line.itemId).one()
1976 varun.gupt 431
            #Update its discounted price.
2026 varun.gupt 432
                line.discounted_price = t_line.discountedPrice
433
            cart.discounted_price = updated_cart.discountedPrice
434
            session.commit()
435
        except PromotionException as ex:
436
            remove_coupon(cart.id)
437
            retval = ex.message
563 chandransh 438
    return retval
576 chandransh 439
 
557 chandransh 440
def merge_cart(fromCartId, toCartId):
441
    fromCart = Cart.get_by(id=fromCartId)
442
    toCart = Cart.get_by(id=toCartId)
443
 
444
    old_lines = fromCart.lines
445
    new_lines = toCart.lines
446
 
447
    for line in old_lines:
448
        flag = True
449
        for new_line in new_lines:
450
            if line.item_id == new_line.item_id:
451
                flag = False
576 chandransh 452
        if flag:
3819 rajveer 453
            n_line = Line()
454
            n_line.item_id = line.item_id 
455
            n_line.quantity = line.quantity
456
            n_line.line_status = line.line_status
457
            n_line.estimate = line.estimate
458
            n_line.created_on = line.created_on
459
            n_line.updated_on = line.updated_on
460
            n_line.actual_price = line.actual_price
461
            toCart.lines.append(n_line)
557 chandransh 462
 
2019 varun.gupt 463
    if toCart.coupon_code is None:
464
        toCart.coupon_code = fromCart.coupon_code
465
 
466
    toCart.updated_on = datetime.datetime.now()
557 chandransh 467
    fromCart.expired_on = datetime.datetime.now()
468
    fromCart.cart_status = CartStatus.INACTIVE
643 chandransh 469
    session.commit()
691 chandransh 470
 
471
def check_out(cartId):
472
    if cartId is None:
473
        raise ShoppingCartException(101, "Cart id not specified")
716 rajveer 474
    cart = Cart.get_by(id = cartId)
691 chandransh 475
    if cart is None:
476
        raise ShoppingCartException(102, "The specified cart couldn't be found")
477
    cart.checked_out_on = datetime.datetime.now()
478
    session.commit()
479
    return True
480
 
481
def reset_cart(cartId, items):
482
    if cartId is None:
483
        raise ShoppingCartException(101, "Cart id not specified")
484
    for item_id, quantity in items.iteritems():
485
        line = Line.query.filter_by(cart_id=cartId, item_id=item_id).one()
486
        if line is not None:
3566 rajveer 487
            delete_discounts_for_line(line)
2261 varun.gupt 488
            line.discounted_price = None
691 chandransh 489
            line.quantity = line.quantity - quantity
490
            if line.quantity == 0:
491
                line.delete()
717 rajveer 492
    cart = Cart.get_by(id=cartId)
691 chandransh 493
    cart.updated_on = datetime.datetime.now()
1894 vikas 494
    cart.checked_out_on = None
1976 varun.gupt 495
 
496
    # Removing Coupon
497
    cart.total_price = None
498
    cart.discounted_price = None
499
    cart.coupon_code = None
500
 
691 chandransh 501
    session.commit()
766 rajveer 502
    return True
503
 
3386 varun.gupt 504
def get_carts_with_coupon_count(coupon_code):
505
    return Cart.query.filter_by(coupon_code = coupon_code).count()
4668 varun.gupt 506
 
507
def show_cod_option(cartId, sourceId, pincode):
508
    cart = Cart.get_by(id = cartId)
509
    cod_option = True
510
    logistics_client = LogisticsClient().get_client()
3386 varun.gupt 511
 
4668 varun.gupt 512
    if cart:
5129 varun.gupt 513
        if cart.coupon_code and cart.coupon_code.lower() == 'saccessory':
4668 varun.gupt 514
            cod_option = False 
515
 
516
        elif cart.lines:
517
            for line in cart.lines:
4866 rajveer 518
                logistics_info = logistics_client.getLogisticsEstimation(line.item_id, pincode, DeliveryType.PREPAID)
519
 
4871 rajveer 520
                if not logistics_info.codAllowed:
4668 varun.gupt 521
                    cod_option = False
522
                    break
523
 
524
    return cod_option
525
 
766 rajveer 526
def close_session():
527
    if session.is_active:
528
        print "session is active. closing it."
1621 rajveer 529
        session.close()