def parse_price_from_cart(self, response): loader = ProductLoader(item=response.meta['product'], response=response) loader.replace_xpath( 'price', '//td[@class="right"]/div[@class="prodetail-price"][1]/text()') shipping_cost = 9.9 if loader.get_output_value('price') < 200 else 0 loader.replace_value('shipping_cost', shipping_cost) yield loader.load_item()
def parse_product(self, response): loader = ProductLoader(item=Product(), response=response) css = '.nosto_product .%s ::text' loader.add_css('identifier', css % 'product_id') loader.add_css('sku', css % 'product_id') for field in ('url', 'name', 'image_url', 'brand'): loader.add_css(field, css % field) list_price = response.css(css % 'list_price').extract_first() sales_price = response.css(css % 'price').extract_first() loader.add_value('price', list_price) if 'InStock' not in response.css(css % 'availability').extract_first(): loader.add_value('stock', 0) category = response.css(css % 'category').extract_first() loader.add_value('category', category.split('/')[-1]) options_data = response.xpath('//script/text()').re( 'Product.Config.({.+})') if not options_data: item = loader.load_item() if sales_price != list_price: item['metadata'] = {'SalesPrice': Decimal(sales_price)} yield item return options_data = json.loads(options_data[0]) if len(options_data['attributes']) > 1: self.log('More than one options attributes found on %s' % response.url) return price = loader.get_output_value('price') name = loader.get_output_value('name') sales_price = Decimal(sales_price) for option in options_data['attributes'].values()[0]['options']: new_price = sales_price + Decimal(option['price']) loader.replace_value('price', price + Decimal(option['oldPrice'])) loader.replace_value('name', name + ' ' + option['label']) loader.replace_value('identifier', option['products'][0]) loader.replace_value('sku', option['products'][0]) loader.replace_xpath( 'image_url', '//li[@id="simple-product-image-%s"]/a/@href' % option['products'][0]) item = loader.load_item() if price + Decimal(option['oldPrice']) != new_price: item['metadata'] = {'SalesPrice': new_price} yield item
def parse_product(self, response): categories = response.xpath( '//li[@class="blockBreadcrumb__item"]/a/text()').extract()[-3:] loader = ProductLoader(item=Product(), response=response) loader.add_xpath('identifier', '//input[@name="simpleSku"]/@value') loader.add_xpath('sku', '//input[@id="configSku"]/@value') loader.add_value('url', response.url) loader.add_xpath('name', '//h1[contains(@class, "__heading")]/text()') loader.add_xpath('name', '//input[@name="simpleSku"]/../span/text()') loader.add_xpath('image_url', '//div[@class="layoutImage"]//img/@src') loader.add_xpath('price', '//input[@id="price"]/@value') loader.add_xpath('brand', '//input[@id="brand"]/@value') loader.add_value('category', categories) loader.add_xpath('stock', '//@data-instock') item = loader.load_item() options = response.xpath('//select[@id="js-simple-selector"]/option') if not options: if loader.get_output_value('identifier'): yield item return for option in options: loader = ProductLoader(item=Product(item), selector=option) loader.replace_xpath('identifier', './@value') loader.add_xpath('name', './text()') identifier = loader.get_output_value('identifier') price = response.xpath( '//div[@data-simple-sku="%s"]//span[contains(@class, "actualPrice")]/text()' % identifier).extract() loader.replace_value('price', price) image_url = response.xpath( '//div[@data-simple-sku="%s"]/a[contains(@class, "link_selected")]/@data-product-image' % identifier).extract() loader.replace_value('image_url', image_url) loader.replace_xpath('stock', './@data-instock') yield loader.load_item()
def parse_product(self, response): loader = ProductLoader(response=response, item=Product()) loader.add_value('url', response.url) sku = response.xpath('//input[@id="productSku"]/@value').extract_first() loader.add_value('identifier', sku) loader.add_value('sku', sku) loader.add_xpath('brand', '//span[@itemprop="brand"]/text()') category = response.xpath('//div[@class="breadcrumbs"]//li/a/text()').extract()[-3:] loader.add_value('category', category) loader.add_xpath('name', '//h1[@itemprop="name"]/text()') loader.add_xpath('price', '//span[@id="price-displayed"]/text()') image_url = response.xpath('//a[@id="productImage"]/img/@src').extract() if image_url: loader.add_value('image_url', response.urljoin(image_url[0])) item = loader.load_item() attributes = response.xpath('//br/preceding-sibling::label[@for!="input-quantity"]/text()').extract() options = response.xpath('//tr[@itemprop="offers"]') headers = map(lambda x:x.lower(), response.xpath('//table[@id="variant-table"]//th/text()').extract()) attr_indexes = {headers.index(attr.lower()): attr for attr in attributes} if not options: yield item return for option in options: metadata = dict() option_name = [] for idx in sorted(attr_indexes): value = option.xpath('.//td')[idx].xpath('.//text()').re_first(' *\S+.+') if value: option_name.append(value.strip()) metadata[attr_indexes[idx]] = value.strip() loader = ProductLoader(Product(), selector=option) loader.add_value(None, item) loader.add_value('name', option_name) loader.replace_xpath('price', './/span[@itemprop="price"]/text()') loader.add_value('price', 0) loader.replace_xpath('identifier', './/input[contains(@name, "VariantSku")]/@value') loader.replace_xpath('sku', './/input[contains(@name, "VariantSku")]/@value') option_item = loader.load_item() option_item['metadata'] = metadata yield option_item
def parse_product(self, response): hxs = HtmlXPathSelector(response) if not hxs.select('//div[@class="productDetail"]'): return product_loader = ProductLoader( item=Product(), selector=hxs.select('//div[@class="productDetail"]')) product_loader.add_value('url', response.url) product_loader.add_xpath( 'brand', './div[@class="productDescription"]/h2/text()') product_loader.add_xpath('image_url', './/img[@class="productImage"]/@src') product_loader.add_xpath( 'category', './/p[@id="breadCrumbs"]/a[position()>1]/text()') p = product_loader.load_item() found = False for product in hxs.select( '//div[@class="rangeTable"]/div[@class="rangeProduct"]'): found = True product_loader = ProductLoader(item=p, selector=product) product_loader.replace_xpath( 'identifier', './/input[@name="UC_recordId"]/@value') product_loader.replace_xpath( 'sku', './/input[@name="UC_recordId"]/@value') product_loader.add_xpath('name', './/div[@class="productName"]/*/text()') if product.select('.//input[@value="Buy"]'): product_loader.add_value('stock', '1') product_loader.add_xpath('price', './/span[@class="ourPrice"]/text()') item = product_loader.load_item() if item['price'] <= 19.99: item['shipping_cost'] = Decimal('1.95') item['price'] = item['price'] + item['shipping_cost'] metadata = FragranceDirectMeta() metadata['promotion'] = ''.join( product.select('.//span[@class="productDiscount"]/text()'). extract()).strip() if item.get('price'): metadata['price_exc_vat'] = Decimal( item['price']) / Decimal('1.2') item['metadata'] = metadata yield item if found: return product_loader.replace_xpath( 'sku', './div[@class="productDescription"]//input[@name="UC_recordId"]/@value' ) product_loader.replace_xpath( 'identifier', './div[@class="productDescription"]//input[@name="UC_recordId"]/@value' ) product_loader.add_xpath( 'name', './div[@class="productDescription"]/*[self::h3 or self::h4]/text()' ) if hxs.select( '//div[@class="productDescription"]//input[@value="Buy"]'): product_loader.add_value('stock', '1') product_loader.add_xpath('price', './/span[@class="ourPrice"]/text()') item = product_loader.load_item() if item['price'] <= 19.99: item['shipping_cost'] = Decimal('1.95') item['price'] = item['price'] + item['shipping_cost'] metadata = FragranceDirectMeta() metadata['promotion'] = ''.join( hxs.select( './/span[@class="productDiscount"]/text()').extract()).strip() if item.get('price'): metadata['price_exc_vat'] = Decimal(item['price']) / Decimal('1.2') item['metadata'] = metadata yield item