Subversion Repositories SmartDukaan

Rev

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

Rev Author Line No. Line
104 ashish 1
'''
2
Created on 29-Mar-2010
3
 
4
@author: ashish
5
'''
1262 varun.gupt 6
from string import Template
7
from shop2020.thriftpy.utils.ttypes import HelperServiceException, Mail
8
 
104 ashish 9
from shop2020.model.v1.order.impl.DataService import Transaction, LineItem,\
1225 chandransh 10
    Alerts, Order, BatchNoGenerator
104 ashish 11
from shop2020.thriftpy.model.v1.order.ttypes import Transaction as T_Transaction,\
690 chandransh 12
    TransactionServiceException, TransactionStatus, OrderStatus
104 ashish 13
import datetime
122 ashish 14
from elixir import *
855 rajveer 15
from shop2020.utils.Utils import to_py_date, to_java_date
1382 varun.gupt 16
from sqlalchemy.sql.expression import and_, or_
483 rajveer 17
from shop2020.model.v1 import order
743 rajveer 18
from shop2020.clients.LogisticsClient import LogisticsClient
871 chandransh 19
from shop2020.clients.InventoryClient import InventoryClient
1262 varun.gupt 20
from shop2020.clients.UserClient import UserClient
1351 varun.gupt 21
from shop2020.clients.HelperClient import HelperClient
104 ashish 22
 
23
def get_new_transaction():
24
    transaction = Transaction()
25
    transaction.createdOn = datetime.datetime.now()
738 chandransh 26
    transaction.status = TransactionStatus.INIT
104 ashish 27
    transaction.status_message = "New transaction"
483 rajveer 28
    return transaction
29
 
30
def create_order(t_order):
31
    order = Order()
32
    if t_order.warehouse_id:
33
        order.warehouse_id = t_order.warehouse_id
509 rajveer 34
    if t_order.logistics_provider_id:    
483 rajveer 35
        order.logistics_provider_id = t_order.logistics_provider_id
36
        order.airwaybill_no = t_order.airwaybill_no
37
        order.tracking_id = t_order.tracking_id
38
    if t_order.expected_delivery_time:    
39
        order.expected_delivery_time = to_py_date(t_order.expected_delivery_time)
40
    if t_order.customer_id:    
41
        order.customer_id = t_order.customer_id
42
        order.customer_name = t_order.customer_name
860 rajveer 43
        order.customer_city = t_order.customer_city
44
        order.customer_state = t_order.customer_state
483 rajveer 45
        order.customer_mobilenumber = t_order.customer_mobilenumber
46
        order.customer_pincode = t_order.customer_pincode
738 chandransh 47
        order.customer_address1 = t_order.customer_address1
48
        order.customer_address2 = t_order.customer_address2
483 rajveer 49
        order.customer_email = t_order.customer_email
50
    #new status and status description to be added    
716 rajveer 51
    order.status = t_order.status  
483 rajveer 52
    order.statusDescription = t_order.statusDescription
53
    order.total_amount = t_order.total_amount
54
    order.total_weight = t_order.total_weight
55
    if t_order.created_timestamp:
56
        order.created_timestamp = to_py_date(t_order.created_timestamp)
57
    else:
685 chandransh 58
        order.created_timestamp = datetime.datetime.now()
483 rajveer 59
    return order
60
 
61
def create_transaction(t_transaction):
62
    t_orders = t_transaction.orders
63
    if not t_orders:
64
        raise TransactionServiceException(101, "Orders missing from the transaction")
65
    transaction = get_new_transaction()
66
    transaction.customer_id = t_transaction.customer_id 
67
    transaction.shopping_cart_id = t_transaction.shoppingCartid
68
 
69
    for t_order in t_orders:
70
        order = create_order(t_order)
71
        order.transaction = transaction 
72
        for line_item in t_order.lineitems:
73
            litem = LineItem()
716 rajveer 74
            litem.item_id = line_item.item_id
963 chandransh 75
            litem.productGroup = line_item.productGroup
483 rajveer 76
            litem.brand = line_item.brand
77
            if line_item.model_number:
78
                litem.model_number = line_item.model_number
79
            if line_item.model_name:    
80
                litem.model_name = line_item.model_name
908 chandransh 81
            if line_item.color:
82
                litem.color = line_item.color
483 rajveer 83
            if line_item.extra_info:
84
                litem.extra_info = line_item.extra_info
85
            litem.quantity = line_item.quantity
86
            litem.unit_price = line_item.unit_price
87
            litem.unit_weight = line_item.unit_weight
88
            litem.total_price = line_item.total_price
89
            litem.total_weight = line_item.total_weight
1262 varun.gupt 90
            litem.transfer_price = line_item.transfer_price
483 rajveer 91
            """
92
            if line_item.addedOn:
93
                litem.added_on = to_py_date(line_item.addedOn)
94
            else:
95
                litem.added_on = datetime.datetime.now()
96
            """
97
            litem.order = order
98
    session.commit()
99
    return transaction.id
100
 
101
def get_transaction(transaction_id):
102
    transaction = Transaction.get_by(id=transaction_id)
103
    if not transaction:
104
        raise TransactionServiceException(108, "no such transaction")
105
 
106
    return transaction
107
 
108
def get_transactions_for_customer(customer_id, from_date, to_date, status):
109
    if not customer_id:
110
        raise TransactionServiceException(101, "bad customer id")
111
    query = Transaction.query.filter(Transaction.customer_id == customer_id)
112
    if status:
113
        query = query.filter(Transaction.status == status)
114
    if from_date:
115
        query = query.filter(Transaction.createdOn >from_date)
116
    if to_date:
117
        query = query.filter(Transaction.createdOn < to_date)
118
    return query.all()
119
 
120
def get_transactions_for_shopping_cart_id(shopping_cart_id):
121
    transactions = Transaction.query.filter_by(shopping_cart_id=shopping_cart_id).all()
122
    if not transactions:
123
        raise TransactionServiceException(108, "transactions for this shopping cart")
124
    return transactions
125
 
126
def get_transaction_status(transaction_id):
127
    if not transaction_id:
128
        raise TransactionServiceException(101, "bad transaction id")
129
 
130
    transaction = get_transaction(transaction_id)
131
 
132
    return transaction.status
133
 
134
def change_transaction_status(transaction_id, new_status, description):
135
    transaction = get_transaction(transaction_id)
136
    transaction.status = new_status
137
    transaction.status_message = description
690 chandransh 138
    if new_status == TransactionStatus.FAILED:
139
        for order in transaction.orders:
140
            order.status = OrderStatus.PAYMENT_FAILED
141
    elif new_status == TransactionStatus.IN_PROCESS:
142
        for order in transaction.orders:
143
            order.status = OrderStatus.SUBMITTED_FOR_PROCESSING
1219 chandransh 144
            order.statusDescription = "Submitted to warehouse"
743 rajveer 145
            #After we got payment success, we will set logistics info also 
146
            logistics_client = LogisticsClient().get_client()
147
            #FIXME line item is only one now. If multiple will come, need to fix.
871 chandransh 148
            item_id = order.lineitems[0].item_id
149
            logistics_info = logistics_client.getLogisticsInfo(order.customer_pincode, item_id)
743 rajveer 150
 
151
            order.warehouse_id = logistics_info.warehouseId
152
            order.logistics_provider_id = logistics_info.providerId
153
            order.airwaybill_no = logistics_info.airway_billno
154
            order.tracking_id = order.airwaybill_no
855 rajveer 155
            order.expected_delivery_time = datetime.datetime.now() + datetime.timedelta(days=logistics_info.deliveryTime)
871 chandransh 156
 
157
            catalog_client = InventoryClient().get_client()
158
            catalog_client.reserveItemInWarehouse(item_id, logistics_info.warehouseId, order.lineitems[0].quantity)
1351 varun.gupt 159
 
1341 chandransh 160
            item_pricing = catalog_client.getItemPricing(item_id, order.warehouse_id)
161
            order.lineitems[0].transfer_price = item_pricing.transferPrice
1262 varun.gupt 162
 
483 rajveer 163
    session.commit()
164
    return True
165
 
1398 varun.gupt 166
def enqueue_transaction_info_email(transaction_id):
1262 varun.gupt 167
    transaction = get_transaction(transaction_id)
168
 
169
    html_header = """
170
<html>
171
<body>
172
<div>
173
    <p>
174
        Hello,<br /><br />
175
        Thanks for your placing your order with us. Following are the details of your order:
176
    </p>
177
    <div>
178
        Order Date: $order_date
179
    </div><hr />
180
    <div>
181
        <b>Order Details</b>
182
        <hr />
183
        <table>
184
        <tr>
185
            <th>Order No.</th>
186
            <th>Product</th>
187
            <th>Quantity</th>
188
            <th>Unit Price</th>
189
            <th>Amount</th>
190
        </tr>
191
    """
1398 varun.gupt 192
    user_email = ""
1262 varun.gupt 193
    total_amount = 0.0
194
    html_table = ""
195
 
196
    for order in transaction.orders:
197
        order_date = order.created_timestamp
1398 varun.gupt 198
        user_email = order.customer_email
1262 varun.gupt 199
        html_tr = "<tr><td>" + str(order.id) + "</td>"
200
 
201
        for lineitem in order.lineitems:
1276 chandransh 202
            html_tr += "<td>" + str(lineitem) + "</td>"
1262 varun.gupt 203
            html_tr += "<td>" + str(lineitem.quantity) + "</td>"
204
            html_tr += "<td>" + str(lineitem.unit_price) + "</td>"
205
            html_tr += "<td>" + str(lineitem.total_price) + "</td></tr>"
206
            total_amount += lineitem.total_price
207
            html_table += html_tr
208
    html_footer = """
209
        <tr><td colspan=5>&nbsp;</td></tr>
210
        <tr>
211
            <td colspan=4>Total Amount</td>
212
            <td>$total_amount</td>
213
        </tr>
214
        </table>
215
    </div><hr />
216
    <p>
217
        Best Wishes,<br />
218
        Saholic Team
219
    </p>
220
</div>
221
</body>
222
</html>
223
    """
1398 varun.gupt 224
 
1262 varun.gupt 225
    formated_order_date = order_date
226
    email_header = Template(html_header).substitute(dict(order_date = formated_order_date))
227
    email_footer = Template(html_footer).substitute(dict(total_amount = total_amount))
228
 
1351 varun.gupt 229
    try:
230
        helper_client = HelperClient().get_client()
1398 varun.gupt 231
        helper_client.saveUserEmailForSending(user_email, "", "Saholic - Order Details", email_header + html_table + email_footer, str(transaction_id), "TransactionInfo")
1351 varun.gupt 232
        return True
233
    except Exception as e:
234
        print e
235
        return False
1262 varun.gupt 236
 
483 rajveer 237
def get_order(order_id):
238
    order = Order.get_by(id=order_id)
239
    if not order:
240
        raise TransactionServiceException(108, "no such order")
241
 
242
    return order
243
 
244
def get_orders_for_customer(customer_id, from_date, to_date, status):
245
    if not customer_id:
246
        raise TransactionServiceException(101, "bad customer id")
247
    query = Order.query.filter(Order.customer_id == customer_id)
248
    if status:
249
        query = query.filter(Order.status == status)
250
    if from_date:
251
        query = query.filter(Order.created_timestamp >from_date)
252
    if to_date:
253
        query = query.filter(Order.created_timestamp < to_date)
254
    return query.all()
255
 
256
def get_all_orders(status, from_date, to_date, warehouse_id):
257
    if not warehouse_id:
258
        raise TransactionServiceException(101, "bad warehouse id")
259
    query = Order.query.filter(Order.warehouse_id == warehouse_id)
260
    if status:
261
        query = query.filter(Order.status == status)
262
    if from_date:
263
        query = query.filter(Order.created_timestamp >from_date)
264
    if to_date:
265
        query = query.filter(Order.created_timestamp < to_date)
266
    return query.all()
267
 
1382 varun.gupt 268
def get_returnable_orders_for_customer(customer_id, limit = None):
269
    if not customer_id:
270
        raise TransactionServiceException(101, "bad customer id")
271
 
272
    query = Order.query.filter(Order.customer_id == customer_id)
273
    query = query.filter(Order.status != OrderStatus.PAYMENT_FAILED)
274
    query = query.filter(Order.status != OrderStatus.REJECTED)
275
    query = query.filter(Order.status > OrderStatus.SHIPPED_FROM_WH)
276
    query = query.filter(or_(Order.status < OrderStatus.DELIVERY_SUCCESS, Order.delivery_timestamp < datetime.datetime.now() + datetime.timedelta(hours = 48)))
277
    orders = query.all()
278
    order_ids = [order.id for order in orders]
279
    return order_ids
280
 
281
def get_cancellable_orders_for_customer(customer_id, limit = None):
282
    if not customer_id:
283
        raise TransactionServiceException(101, "bad customer id")
284
 
285
    query = Order.query.filter(Order.customer_id == customer_id)
286
    query = query.filter(Order.status != OrderStatus.PAYMENT_FAILED)
287
    query = query.filter(Order.status != OrderStatus.REJECTED)
288
    query = query.filter(Order.status < OrderStatus.BILLED)
289
    orders = query.all()
290
    return [order.id for order in orders]
291
 
995 varun.gupt 292
def get_orders_by_billing_date(status, start_billing_date, end_billing_date, warehouse_id):
293
    if not warehouse_id:
294
        raise TransactionServiceException(101, "bad warehouse id")
295
 
296
    query = Order.query.filter(Order.warehouse_id == warehouse_id)
297
 
298
    if status:
299
        query = query.filter(Order.status == status)
300
 
301
    if start_billing_date:
302
        query = query.filter(Order.billing_timestamp >= start_billing_date)
303
 
304
    if end_billing_date:
305
        query = query.filter(Order.billing_timestamp <= end_billing_date)
306
 
307
    return query.all()
308
 
1208 chandransh 309
def get_orders_for_transaction(transaction_id):
310
    orders = Order.query.filter_by(transaction_id=transaction_id).all()
311
    if not orders:
312
        raise TransactionServiceException(101, "No order for the transaction")
313
    return orders
314
 
1405 ankur.sing 315
def get_undelivered_orders(provider_id, warehouse_id):
316
    query = Order.query
317
    if provider_id != -1:
318
        query = query.filter_by(Order.logistics_provider_id == provider_id)
319
    if warehouse_id != -1:
320
        query = query.filter(Order.warehouse_id == warehouse_id)
321
    query = query.filter(and_(Order.status != OrderStatus.DELIVERY_SUCCESS, Order.status != OrderStatus.FAILED, \
322
                              Order.status > OrderStatus.SHIPPED_FROM_WH))
323
    query = query.filter(Order.expected_delivery_time < datetime.datetime.now())
324
    orders = query.all()
325
    return orders
326
 
1208 chandransh 327
def get_line_items_for_order(order_id):
328
    query = LineItem.query.filter(LineItem.order_id == order_id)
329
    return query.all()
330
 
483 rajveer 331
def change_order_status(self, orderId, status, description):
332
    order = get_order(orderId)
333
    order.status = status
334
    order.statusDescription = description
335
    session.commit()
336
    return True
337
 
921 rajveer 338
def accept_order(self, orderId):
339
    order = get_order(orderId)
340
    order.status = OrderStatus.ACCEPTED
341
    order.statusDescription = "Order Accepted"
342
    order.accepted_timestamp = datetime.datetime.now()
343
    session.commit()
344
    return True
345
 
346
def bill_order(self, orderId):
347
    order = get_order(orderId)
348
    order.status = OrderStatus.BILLED
349
    order.statusDescription = "Order Billed"
350
    order.billing_timestamp = datetime.datetime.now()
351
    session.commit()
1208 chandransh 352
    return True
921 rajveer 353
 
1149 chandransh 354
def add_billing_details(orderId, invoice_number, billed_by):
494 rajveer 355
    order = Order.get_by(id=orderId)
356
    if not order:
357
        raise TransactionServiceException(101, "No order found for the givem orderid")
358
    order.invoice_number = invoice_number
359
    order.billed_by = billed_by
360
    session.commit()
361
    return True
759 chandransh 362
 
1149 chandransh 363
def add_jacket_number(orderId, jacket_number):
364
    order = Order.get_by(id=orderId)
365
    if not order:
366
        raise TransactionServiceException(101, "No order found for the givem orderid")
367
    order.jacket_number = jacket_number 
368
    session.commit()
369
    return True
370
 
1220 chandransh 371
def batch_orders(warehouseId):
372
    if not warehouseId:
373
        raise TransactionServiceException(101, "bad warehouse id")
1225 chandransh 374
 
375
    batchno_generator = BatchNoGenerator()
376
    session.commit()
1220 chandransh 377
    query = Order.query.filter_by(warehouse_id=warehouseId)
378
    query = query.filter_by(status=OrderStatus.SUBMITTED_FOR_PROCESSING)
379
    query = query.order_by(Order.created_timestamp)
380
    pending_orders = query.all()
1225 chandransh 381
 
1220 chandransh 382
    serial_no = 1
383
    for order in pending_orders:
1276 chandransh 384
        order.batchNo = batchno_generator.id
1220 chandransh 385
        order.serialNo = serial_no
386
        serial_no += 1
387
    session.commit() 
388
    pending_orders = query.all()
389
    return pending_orders
390
 
391
def order_outofstock(orderId):
392
    order = get_order(orderId)
393
    order.status = OrderStatus.INVENTORY_LOW
394
    order.statusDescription = "Low Inventory"
395
    order.outofstock_timestamp = datetime.datetime.now()
396
    session.commit()
397
    return True
398
 
759 chandransh 399
def mark_orders_as_manifested(warehouse_id, provider_id):
400
    try:
986 chandransh 401
        current_timestamp = datetime.datetime.now()
852 chandransh 402
        orders = Order.query.filter_by(warehouse_id = warehouse_id, logistics_provider_id = provider_id, status = OrderStatus.BILLED).all()
759 chandransh 403
        for order in orders:
404
            order.status = OrderStatus.SHIPPED_FROM_WH
987 chandransh 405
            order.statusDescription = "Order shipped from warehouse"
986 chandransh 406
            order.shipping_timestamp = current_timestamp
759 chandransh 407
        session.commit()
408
        return True
409
    except:
410
        return False
1113 chandransh 411
 
412
def mark_orders_as_picked_up(provider_id, pickup_details):
413
    for awb, pickup_timestamp in pickup_details.iteritems():
1135 chandransh 414
        order = Order.query.filter_by(airwaybill_no=awb, logistics_provider_id = provider_id).first()
1113 chandransh 415
        if order == None:
416
            raise TransactionServiceException(102, "No order found for the awb: " + awb)
417
        order.status = OrderStatus.SHIPPED_TO_LOGST
418
        order.statusDescription = "Order picked up by Courier Company"
1246 chandransh 419
        order.pickup_timestamp = pickup_timestamp
1113 chandransh 420
    session.commit()
1217 chandransh 421
 
1132 chandransh 422
    current_time = datetime.datetime.now()
423
    to_datetime = datetime.datetime(current_time.year, current_time.month, current_time.day)
1246 chandransh 424
    from_datetime = to_datetime - datetime.timedelta(2)
1132 chandransh 425
    orders_not_picked_up = Order.query.filter_by(logistics_provider_id = provider_id).filter_by(status=OrderStatus.SHIPPED_FROM_WH).filter(Order.shipping_timestamp >= from_datetime).filter(Order.shipping_timestamp <= to_datetime).all()
1113 chandransh 426
    return orders_not_picked_up
427
 
1132 chandransh 428
def mark_orders_as_delivered(provider_id, delivered_orders):
429
    for awb, detail in delivered_orders.iteritems():
1135 chandransh 430
        order = Order.query.filter_by(airwaybill_no=awb, logistics_provider_id = provider_id).first()
1132 chandransh 431
        if order == None:
432
            raise TransactionServiceException(103, "No order found for the awb:" + awb)
433
        order.status = OrderStatus.DELIVERY_SUCCESS
434
        order.statusDescription = "Order delivered"
435
        order.delivery_timestamp, order.receiver = detail.split('|')
436
    session.commit()
437
 
1135 chandransh 438
def mark_orders_as_failed(provider_id, returned_orders):
439
    for awb, detail in returned_orders.iteritems():
440
        order = Order.query.filter_by(airwaybill_no=awb, logistics_provider_id = provider_id).first()
441
        if order == None:
442
            raise TransactionServiceException(103, "No order found for the awb:" + awb)
443
        order.status = OrderStatus.FAILED
444
        order.delivery_timestamp, reason = detail.split('|')
445
        order.statusDescription = "Order Returned to Origin:" + reason
446
    session.commit()    
447
 
1246 chandransh 448
def update_non_delivery_reason(provider_id, undelivered_orders):
449
    for awb, reason in undelivered_orders.iteritems():
450
        order = Order.query.filter_by(airwaybill_no=awb, logistics_provider_id = provider_id).first()
451
        if order == None:
452
            raise TransactionServiceException(103, "No order found for the awb:" + awb)
453
        order.statusDescription = reason
454
    session.commit()
455
 
483 rajveer 456
def get_alerts(order_id, all):
457
    query = Alerts.query.filter_by(order_id=order_id)
458
    if not all:
459
        query = query.filter_by(valid=True)
460
    return query.all()
461
 
462
def set_alert(order_id, unset, type, comment):
463
    #get existing alert
464
    if unset:
465
        query = Alerts.query.filter_by(order_id=order_id)
466
        query = query.filter_by(type=type)
467
        alerts = query.all()
468
        for alert in alerts:
469
            if alert.valid:
470
                alert.valid = False
471
                alert.comment = comment
472
                alert.time_unset = datetime.datetime.now()
473
    else:
474
        alert = Alerts()
475
        alert.order_id = order_id
476
        alert.valid = True
477
        alert.type = type
478
        alert.comment = comment
479
        alert.time_set = datetime.datetime.now()
766 rajveer 480
    session.commit()    
481
 
482
def close_session():
483
    if session.is_active:
484
        print "session is active. closing it."
485
        session.close()