Subversion Repositories SmartDukaan

Rev

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

Rev Author Line No. Line
626 chandransh 1
#!/usr/bin/python
5440 phani.kuma 2
# coding: ascii
4090 chandransh 3
'''
4
This script is used to load item details in the catalog database.
5
It's now mostly used for Accessories since they come in huge numbers.
1080 chandransh 6
 
4090 chandransh 7
@author: Chandranshu
8
'''
626 chandransh 9
import optparse
1080 chandransh 10
import csv
626 chandransh 11
import xlrd
12
import datetime
13
 
14
if __name__ == '__main__' and __package__ is None:
15
    import sys
16
    import os
17
    sys.path.insert(0, os.getcwd())
18
 
5440 phani.kuma 19
from shop2020.thriftpy.model.v1.catalog.ttypes import status, ItemType
626 chandransh 20
from shop2020.model.v1.catalog.impl import DataService
724 chandransh 21
from shop2020.model.v1.catalog.impl.DataService import Item, EntityIDGenerator,\
1356 chandransh 22
    ItemChangeLog, Vendor, VendorItemPricing, VendorItemMapping
626 chandransh 23
from elixir import *
24
 
5440 phani.kuma 25
def load_item_data(filename, vendorId, full_update, dry_run):
1250 chandransh 26
    DataService.initialize('catalog')
1356 chandransh 27
 
28
    vendor = Vendor.get_by(id=vendorId)
29
    if vendor is None:
30
        raise Exception("No vendor found for the id: " + str(vendorId))
5440 phani.kuma 31
 
626 chandransh 32
    workbook = xlrd.open_workbook(filename)
33
    sheet = workbook.sheet_by_index(0)
34
    num_rows = sheet.nrows
35
    updatedOn = datetime.datetime.now()
1080 chandransh 36
    new_items = []
1264 chandransh 37
    updated_items = []
4717 phani.kuma 38
    not_created_items = []
1356 chandransh 39
 
626 chandransh 40
    for rownum in range(1, num_rows):
1833 chandransh 41
        print sheet.row_values(rownum)
1264 chandransh 42
 
5440 phani.kuma 43
        our_brand, our_model_number, our_model_name, our_color,\
44
        product_group, brand, model_number, model_name, color,\
45
        dp, mrp, mop, sp, xfer_price,\
46
        comments, weight, start_date, deal_text, deal_value,\
47
        warranty_period, serialized, hasItemNo, preferredVendor = sheet.row_values(rownum)[0:23]
48
 
1833 chandransh 49
        print product_group
5440 phani.kuma 50
 
626 chandransh 51
        if isinstance(model_number, float):
52
            model_number = str(int(model_number))
1810 chandransh 53
 
5065 phani.kuma 54
        if isinstance(our_model_number, float):
55
            our_model_number = str(int(our_model_number))
56
 
1810 chandransh 57
        if our_brand == '':
58
            our_brand = brand
59
        if our_model_number == '':
60
            our_model_number = model_number
4739 phani.kuma 61
        if our_model_name == '':
62
            our_model_name = model_name
1810 chandransh 63
        if our_color == '':
64
            our_color = color
65
 
1633 chandransh 66
        if sp == '':
67
            sp = mop 
1356 chandransh 68
        item = None
4725 phani.kuma 69
        similar_item = None
1356 chandransh 70
        vendor_item_pricing = None
1080 chandransh 71
 
1356 chandransh 72
        key = product_group.strip().lower() + '|' + brand.strip().lower() + '|' + model_number.strip().lower() + '|' + color.strip().lower()
73
 
4717 phani.kuma 74
        # Check if a similar items already exists in our database
4739 phani.kuma 75
        similar_items = Item.query.filter_by(brand=our_brand.strip(), model_number=our_model_number.strip(), model_name=our_model_name.strip()).all()
4717 phani.kuma 76
 
4725 phani.kuma 77
        # Check if a similar item already exists in our database
4717 phani.kuma 78
        for old_item in similar_items:
4725 phani.kuma 79
            if old_item.color != None and old_item.color.strip().lower() == our_color.strip().lower():
4717 phani.kuma 80
                item = old_item
81
                break
82
 
4725 phani.kuma 83
        # Check if a similar item already exists in our database with out valid color if similar item with same color is not found
626 chandransh 84
        if item is None:
4717 phani.kuma 85
            for old_item in similar_items:
4725 phani.kuma 86
                if not check_color_valid(old_item.color):
4717 phani.kuma 87
                    item = old_item
88
                    break
89
 
90
        i = 0
91
        color_of_similar_item = None
4725 phani.kuma 92
        # Check if a similar item already exists in our database to be used to get catalog_item_id
4717 phani.kuma 93
        for old_item in similar_items:
4725 phani.kuma 94
            # get a similar item already existing in our database with valid color
95
            if check_color_valid(old_item.color):
4717 phani.kuma 96
                similar_item = old_item
97
                color_of_similar_item = similar_item.color
98
                break
99
            i = i + 1
4725 phani.kuma 100
            # get a similar item already existing in our database if similar item with valid color is not found
4717 phani.kuma 101
            if i == len(similar_items):
102
                similar_item = old_item
103
                color_of_similar_item = similar_item.color
4725 phani.kuma 104
 
105
        # Check if a similar item that is obtained above is having a valid color
106
        if check_color_valid(color_of_similar_item):
107
            # if a similar item that is obtained above is having a valid color and new item is about to be created with out valid color it is not done.
108
            # since for example if their is a item with red color in our database and we are creating a new item with no color for the same product which is wrong.
109
            if item is None and not check_color_valid(our_color):
4717 phani.kuma 110
                not_created_items.append(rownum)
111
                continue
112
 
113
        if item is None:
114
            #print "[ADDING:]{0} {1} {2} {3} to our catalogue.".format(brand, model_number, model_name, color)
1080 chandransh 115
            new_items.append(rownum)
626 chandransh 116
            item = Item()
4762 phani.kuma 117
            item.brand = our_brand.strip()
4717 phani.kuma 118
            item.product_group = product_group.strip()
119
            item.model_number = our_model_number.strip()
4739 phani.kuma 120
            item.model_name = our_model_name.strip()
4717 phani.kuma 121
            item.color = our_color.strip()
626 chandransh 122
            item.status = status.IN_PROCESS
2035 rajveer 123
            item.status_description = "This item is in process"
626 chandransh 124
            item.addedOn = updatedOn
1356 chandransh 125
 
4762 phani.kuma 126
            vendor_item_mapping = VendorItemMapping(vendor=vendor, item=item, item_key=key)
1359 chandransh 127
            vendor_item_pricing = VendorItemPricing(vendor=vendor, item=item)
5440 phani.kuma 128
 
626 chandransh 129
            session.add(item)
1356 chandransh 130
            session.add(vendor_item_mapping)
1359 chandransh 131
            session.add(vendor_item_pricing)
1080 chandransh 132
 
4717 phani.kuma 133
            if similar_item is None or similar_item.catalog_item_id is None:
134
                # If there is no similar item in the database from before,
135
                # use the entity_id_generator
136
                entity_id = EntityIDGenerator.query.first()
137
                item.catalog_item_id = entity_id.id + 1
138
                entity_id.id = entity_id.id  + 1
139
                if similar_item is not None and similar_item.catalog_item_id is None:
140
                    similar_item.catalog_item_id = entity_id.id
1080 chandransh 141
            else:
4717 phani.kuma 142
                #If a similar item already exists for a product group, brand and model_number, set it as same.
143
                item.catalog_item_id = similar_item.catalog_item_id
144
                item.category = similar_item.category
4762 phani.kuma 145
                item.product_group = similar_item.product_group
4717 phani.kuma 146
                item.status = similar_item.status
147
                item.status_description = similar_item.status_description
148
                #Use the same brand, model name and model number as in similar item in database
149
                item.brand = similar_item.brand
150
                item.model_name = similar_item.model_name
151
                item.model_number = similar_item.model_number
626 chandransh 152
        else:
1356 chandransh 153
            # If this item already existed and one of its price parameters has changed
1278 chandransh 154
            # in which case we add it to the list of updated items for reporting.
1965 chandransh 155
            if item.status == status.PHASED_OUT:
156
                item.status = status.IN_PROCESS #Not the ideal choice but we don't know whether content has been generated for it beforehand.
2035 rajveer 157
                item.status_description = "This item is in process"
4717 phani.kuma 158
 
4725 phani.kuma 159
            if check_color_valid(our_color) and (item.color == None or item.color.strip().lower() != our_color.strip().lower()):
4717 phani.kuma 160
                item.color = our_color.strip()
161
 
162
            vendor_item_mapping = VendorItemMapping.get_by(vendor=vendor, item=item)
163
            if vendor_item_mapping is None:
4762 phani.kuma 164
                vendor_item_mapping = VendorItemMapping(vendor=vendor, item=item, item_key=key)
4717 phani.kuma 165
                session.add(vendor_item_mapping)
4725 phani.kuma 166
            else:
167
                vendor_item_mapping.item_key = key
168
 
1356 chandransh 169
            vendor_item_pricing = VendorItemPricing.get_by(vendor=vendor, item=item)
170
            if vendor_item_pricing is None:
171
                vendor_item_pricing = VendorItemPricing(vendor=vendor, item=item)
172
                session.add(vendor_item_pricing)
173
 
1633 chandransh 174
            if item.mrp != mrp or vendor_item_pricing.dealerPrice != dp or vendor_item_pricing.transfer_price != xfer_price or item.sellingPrice != sp:
5440 phani.kuma 175
                updated_items.append(sheet.row_values(rownum)[0:23] + [item.mrp, vendor_item_pricing.dealerPrice, vendor_item_pricing.transfer_price, item.sellingPrice])
2330 rajveer 176
 
1080 chandransh 177
        if dp != "":
178
            item.sellingPrice = dp
1356 chandransh 179
            vendor_item_pricing.dealerPrice = dp
629 rajveer 180
 
1080 chandransh 181
        if mrp != "" and mop != "" and mrp <  mop:
4717 phani.kuma 182
            raise Exception("[BAD MRP and MOP:] for {0} {1} {2} {3}. MRP={4}. MOP={5}".format(brand, model_number, model_name, color, mrp, mop))
5440 phani.kuma 183
 
1633 chandransh 184
        if mrp != "" and sp != "" and mrp < sp:
4717 phani.kuma 185
            raise Exception("[BAD MRP and SP:] for {0} {1} {2} {3}. MRP={4}. SP={5}".format(brand, model_number, model_name, color, mrp, sp))
5440 phani.kuma 186
 
1080 chandransh 187
        if mop != "" and xfer_price != "" and xfer_price > mop:
4717 phani.kuma 188
            raise Exception("[BAD MOP and TP:] for {0} {1} {2} {3}. TP={4}. MOP={5}".format(brand, model_number, model_name, color, xfer_price, mop))
873 rajveer 189
 
4717 phani.kuma 190
        if preferredVendor == None or preferredVendor == "":
191
            raise Exception("[Preferred Vendor required:] for {0} {1} {2} {3}".format(brand, model_number, model_name, color))
192
        else:
193
            try:
194
                item.preferredVendor = int(preferredVendor)
195
            except:
196
                raise Exception("[Preferred Vendor should be number:] for {0} {1} {2} {3}. preferredVendor={4}".format(brand, model_number, model_name, color, preferredVendor))
197
 
5440 phani.kuma 198
        if serialized == None or serialized == "":
199
            raise Exception("[Serialized required:] for {0} {1} {2} {3}".format(brand, model_number, model_name, color))
200
        else:
4717 phani.kuma 201
            try:
5440 phani.kuma 202
                if serialized:
203
                    item.type = ItemType.SERIALIZED
204
                else:
205
                    item.type = ItemType.NON_SERIALIZED
4717 phani.kuma 206
            except:
5440 phani.kuma 207
                raise Exception("[Serialized should be either TRUE(SERIALIZED) or FALSE(NON_SERIALIZED):] for {0} {1} {2} {3}. serialized={4}".format(brand, model_number, model_name, color, serialized))
4717 phani.kuma 208
 
5440 phani.kuma 209
        if hasItemNo == None or hasItemNo == "":
210
            raise Exception("[hasItemNo required:] for {0} {1} {2} {3}".format(brand, model_number, model_name, color))
211
        else:
4762 phani.kuma 212
            try:
5440 phani.kuma 213
                if hasItemNo:
214
                    item.hasItemNo = 1
215
                else:
216
                    item.hasItemNo = 0
4762 phani.kuma 217
            except:
5440 phani.kuma 218
                raise Exception("[hasItemNo should be either TRUE or FALSE:] for {0} {1} {2} {3}. hasItemNo={4}".format(brand, model_number, model_name, color, hasItemNo))
219
 
220
        if warranty_period != "":
221
            try:
222
                item.warranty_period = int(warranty_period)
223
            except:
4762 phani.kuma 224
                pass
225
 
1431 chandransh 226
        if mrp != "":
227
            item.mrp = mrp
228
 
629 rajveer 229
        if mop != "":
1356 chandransh 230
            vendor_item_pricing.mop = mop
5440 phani.kuma 231
 
724 chandransh 232
        if xfer_price !="":
1356 chandransh 233
            vendor_item_pricing.transfer_price = xfer_price
1080 chandransh 234
 
2088 chandransh 235
        if start_date is not None and start_date != '':
236
            #If a start date has been specified, it takes precedence.
237
            item.startDate = datetime.datetime(*xlrd.xldate_as_tuple(start_date, workbook.datemode))
238
        elif item.startDate == None or item.startDate == '': 
239
            #If start date is not specified and item's start date is not set, set it to current time
1431 chandransh 240
            item.startDate = datetime.datetime.now()
5440 phani.kuma 241
 
1633 chandransh 242
        item.sellingPrice = sp
5440 phani.kuma 243
 
629 rajveer 244
        if weight != "":    
245
            item.weight = weight
1080 chandransh 246
 
626 chandransh 247
        item.updatedOn = updatedOn
724 chandransh 248
 
249
        item_change_log = ItemChangeLog()
250
        item_change_log.new_status = item.status
251
        item_change_log.timestamp = updatedOn
252
        item_change_log.item = item
1080 chandransh 253
 
254
        if not dry_run:
255
            session.commit()
256
 
5440 phani.kuma 257
    write_report("/tmp/items_not_created_dueto_color.csv", not_created_items, sheet, False)
258
    write_report("/tmp/new_items.csv", new_items, sheet, False)
259
    write_report("/tmp/updated_items.csv", updated_items, sheet, True)
1080 chandransh 260
 
261
    if (not dry_run) and full_update:
2035 rajveer 262
        query_string =  "UPDATE " + str(Item.table) + " SET status=" + str(status.PHASED_OUT) + ", status_description='This item has been phased out'" + ", updatedOn='"+ str(updatedOn) +"'"+\
4762 phani.kuma 263
                        " WHERE updatedOn <> '" + str(updatedOn) + "'";
1080 chandransh 264
        session.execute(query_string, mapper=Item)
626 chandransh 265
        session.commit()
266
 
267
    print "Successfully updated the item list information."
268
 
4725 phani.kuma 269
def check_color_valid(color):
270
    if color is not None:
271
        color = color.strip().lower()
272
        if color != '' and color != 'na' and color != 'blank' and color != '(blank)':
273
            return True
274
    return False
275
 
1264 chandransh 276
def write_report(filename, items, sheet, is_item):
4023 chandransh 277
    '''
278
    Iterates through the items list and writes all the values to the specified
279
    filename in the CSV format. 'is_item' indicates whether the list consists
280
    of row numbers or complete row data.
281
    '''
1080 chandransh 282
    items_writer = csv.writer(open(filename, "wb"), delimiter=',', quoting=csv.QUOTE_ALL)
5440 phani.kuma 283
    items_writer.writerow(sheet.row_values(0)[0:23] + ['Old MRP', 'Old DP', 'Old TP', 'Old SP'])
1264 chandransh 284
    if is_item:
4023 chandransh 285
        #The list contains the complete rows.
1264 chandransh 286
        for item in items:
1833 chandransh 287
            print item
1264 chandransh 288
            items_writer.writerow([str(value) for value in item])
289
    else:
4023 chandransh 290
        #The list only has row numbers. We've to fetch the data ourselves.
1264 chandransh 291
        for i in items:
1833 chandransh 292
            print sheet.row_values(i)
5440 phani.kuma 293
            items_writer.writerow([str(value) for value in sheet.row_values(i)[0:23]])
1080 chandransh 294
 
626 chandransh 295
def main():
296
    parser = optparse.OptionParser()
297
    parser.add_option("-f", "--file", dest="filename",
298
                   default="ItemList.xls", type="string",
299
                   help="Read the item list from FILE",
300
                   metavar="FILE")
1356 chandransh 301
    parser.add_option("-v", "--vendor", dest="vendor",
302
                      type="int",
303
                      help="Update the pricing information for VENDOR",
304
                      metavar="VENDOR")
1080 chandransh 305
    parser.add_option("-d", "--dry-run", dest="dry_run",
306
                      action="store_true",
307
                      help="Dry run only reporting on pending changes.Please note that some of the items can be reported twice.")
308
    parser.add_option("-a", "--full", dest="full_update",
309
                      action="store_true",
310
                      help="In a full update, all older items are marked as PHASED_OUT. Also see -pm.")
311
    parser.add_option("-p", "--partial", dest="full_update",
312
                      action="store_false",
313
                      help="In a partial update, older items are left as is. Also see -fm.")
5620 mandeep.dh 314
    parser.set_defaults(full_update=False, dry_run=False, vendor=1)
626 chandransh 315
    (options, args) = parser.parse_args()
316
    if len(args) != 0:
317
        parser.error("You've supplied extra arguments. Are you sure you want to run this program?")
318
    filename = options.filename
5440 phani.kuma 319
    load_item_data(filename, options.vendor, options.full_update, options.dry_run)
626 chandransh 320
 
321
if __name__ == '__main__':
322
    main()