Учебники

Scrapy – Загрузчики предметов

Загрузчики элементов предоставляют удобный способ заполнять элементы, которые соскребаются с веб-сайтов.

Объявление загрузчиков предметов

Объявление Загрузчиков Предметов подобно Предметам.

Например –

from scrapy.loader import ItemLoader 
from scrapy.loader.processors import TakeFirst, MapCompose, Join  

class DemoLoader(ItemLoader):  
   default_output_processor = TakeFirst()  
   title_in = MapCompose(unicode.title) 
   title_out = Join()  
   size_in = MapCompose(unicode.strip)  
   # you can continue scraping here

В приведенном выше коде вы можете видеть, что входные процессоры объявлены с использованием суффикса _in, а выходные процессоры объявлены с использованием суффикса _out .

Атрибуты ItemLoader.default_input_processor и ItemLoader.default_output_processor используются для объявления процессоров ввода / вывода по умолчанию.

Использование загрузчиков элементов для заполнения элементов

Чтобы использовать Item Loader, сначала создайте экземпляр с помощью dict-like объекта или без него, где элемент использует класс Item, указанный в атрибуте ItemLoader.default_item_class .

  • Вы можете использовать селекторы для сбора значений в Загрузчик элементов.

  • Вы можете добавить больше значений в том же поле элемента, где загрузчик элементов будет использовать соответствующий обработчик для добавления этих значений.

Вы можете использовать селекторы для сбора значений в Загрузчик элементов.

Вы можете добавить больше значений в том же поле элемента, где загрузчик элементов будет использовать соответствующий обработчик для добавления этих значений.

Следующий код демонстрирует, как элементы заполняются с помощью загрузчиков элементов.

from scrapy.loader import ItemLoader 
from demoproject.items import Demo  

def parse(self, response): 
   l = ItemLoader(item = Product(), response = response)
   l.add_xpath("title", "//div[@class = 'product_title']")
   l.add_xpath("title", "//div[@class = 'product_name']")
   l.add_xpath("desc", "//div[@class = 'desc']")
   l.add_css("size", "div#size]")
   l.add_value("last_updated", "yesterday")
   return l.load_item()

Как показано выше, есть два разных XPath, из которых поле заголовка извлекается с помощью метода add_xpath ()

1. //div[@class = "product_title"] 
2. //div[@class = "product_name"]

После этого аналогичный запрос используется для поля desc . Данные о размере извлекаются с использованием метода add_css (), а last_updated заполняется значением «вчера» с использованием метода add_value () .

Как только все данные собраны, вызовите метод ItemLoader.load_item (), который возвращает элементы, заполненные данными, извлеченными с использованием методов add_xpath () , add_css () и add_value () .

Процессоры ввода и вывода

Каждое поле загрузчика элементов содержит один входной процессор и один выходной процессор.

  • Когда данные извлекаются, процессор ввода обрабатывает их и их результат сохраняется в ItemLoader.

  • Затем, после сбора данных, вызовите метод ItemLoader.load_item (), чтобы получить заполненный объект Item.

  • Наконец, вы можете присвоить результат обработчику вывода элементу.

Когда данные извлекаются, процессор ввода обрабатывает их и их результат сохраняется в ItemLoader.

Затем, после сбора данных, вызовите метод ItemLoader.load_item (), чтобы получить заполненный объект Item.

Наконец, вы можете присвоить результат обработчику вывода элементу.

Следующий код демонстрирует, как вызывать процессоры ввода и вывода для определенного поля:

l = ItemLoader(Product(), some_selector)
l.add_xpath("title", xpath1) # [1]
l.add_xpath("title", xpath2) # [2]
l.add_css("title", css)      # [3]
l.add_value("title", "demo") # [4]
return l.load_item()         # [5]

Строка 1 – данные заголовка извлекаются из xpath1 и передаются через процессор ввода, а их результат собирается и сохраняется в ItemLoader.

Строка 2 – аналогично, заголовок извлекается из xpath2 и проходит через тот же процессор ввода, а его результат добавляется к данным, собранным для [1].

Строка 3 – заголовок извлекается из селектора css и передается через тот же процессор ввода, а результат добавляется к данным, собранным для [1] и [2].

Строка 4 – Далее значение «demo» назначается и передается через процессоры ввода.

Строка 5 – Наконец, данные собираются внутри всех полей и передаются в выходной процессор, и окончательное значение присваивается Элементу.

Объявление процессоров ввода и вывода

Процессоры ввода и вывода объявлены в определении ItemLoader. Кроме того, они также могут быть указаны в метаданных поля элемента .

Например –

import scrapy 
from scrapy.loader.processors import Join, MapCompose, TakeFirst 
from w3lib.html import remove_tags  

def filter_size(value): 
   if value.isdigit(): 
      return value  

class Item(scrapy.Item): 
   name = scrapy.Field( 
      input_processor = MapCompose(remove_tags), 
      output_processor = Join(), 
   )
   size = scrapy.Field( 
      input_processor = MapCompose(remove_tags, filter_price), 
      output_processor = TakeFirst(), 
   ) 

>>> from scrapy.loader import ItemLoader 
>>> il = ItemLoader(item = Product()) 
>>> il.add_value('title', [u'Hello', u'<strong>world</strong>']) 
>>> il.add_value('size', [u'<span>100 kg</span>']) 
>>> il.load_item()

Он отображает вывод как –

{'title': u'Hello world', 'size': u'100 kg'}

Контекст загрузчика элементов

Контекст загрузчика элементов – это набор произвольных значений ключей, общих для процессоров ввода и вывода.

Например, предположим, что у вас есть функция parse_length

def parse_length(text, loader_context): 
   unit = loader_context.get('unit', 'cm') 
   
   # You can write parsing code of length here  
   return parsed_length

Получая аргументы loader_context, он сообщает загрузчику элементов, что он может получить контекст загрузчика элементов. Есть несколько способов изменить значение контекста Item Loader –

  • Изменить текущий активный контекст загрузчика элементов –

Изменить текущий активный контекст загрузчика элементов –

loader = ItemLoader (product)
loader.context ["unit"] = "mm"
  • На экземпляре Item Loader –

На экземпляре Item Loader –

loader = ItemLoader(product, unit = "mm")
  • В объявлении Item Loader для процессоров ввода / вывода, которые создаются с контекстом Item Loader –

В объявлении Item Loader для процессоров ввода / вывода, которые создаются с контекстом Item Loader –

class ProductLoader(ItemLoader):
   length_out = MapCompose(parse_length, unit = "mm")

ItemLoader Objects

Это объект, который возвращает загрузчик нового элемента, чтобы заполнить данный элемент. У него есть следующий класс –

class scrapy.loader.ItemLoader([item, selector, response, ]**kwargs)

В следующей таблице приведены параметры объектов ItemLoader –

Sr.No Параметр и описание
1

вещь

Это элемент для заполнения с помощью вызова add_xpath (), add_css () или add_value ().

2

селектор

Он используется для извлечения данных с веб-сайтов.

3

ответ

Он используется для создания селектора с использованием default_selector_class.

вещь

Это элемент для заполнения с помощью вызова add_xpath (), add_css () или add_value ().

селектор

Он используется для извлечения данных с веб-сайтов.

ответ

Он используется для создания селектора с использованием default_selector_class.

В следующей таблице показаны методы объектов ItemLoader –

Sr.No Метод и описание пример
1

get_value (значение, * процессоры, ** kwargs)

При заданном аргументе процессора и ключевого слова значение обрабатывается методом get_value ().

>>> from scrapy.loader.processors import TakeFirst
>>> loader.get_value(u'title: demoweb', TakeFirst(), unicode.upper, re = 'title: (.+)')
'DEMOWEB`
2

add_value (field_name, value, * processors, ** kwargs)

Он обрабатывает значение и добавляет его в поле, где оно сначала передается через get_value, передавая процессоры и аргументы ключевых слов перед передачей через поле ввода процессора.

loader.add_value('title', u'DVD')
loader.add_value('colors', [u'black', u'white'])
loader.add_value('length', u'80')
loader.add_value('price', u'2500')
3

replace_value (имя_поля, значение, * процессоры, ** kwargs)

Он заменяет собранные данные новым значением.

loader.replace_value('title', u'DVD')
loader.replace_value('colors', [u'black', u'white'])
loader.replace_value('length', u'80')
loader.replace_value('price', u'2500')
4

get_xpath (xpath, * процессоры, ** kwargs)

Он используется для извлечения строк Юникода, давая процессоры и аргументы ключевых слов, получая XPath .

# HTML code: <div class = "item-name">DVD</div>
loader.get_xpath("//div[@class = 'item-name']")

# HTML code: <div id = "length">the length is 45cm</div>
loader.get_xpath("//div[@id = 'length']", TakeFirst(), re = "the length is (.*)")
5

add_xpath (имя_поля, xpath, * процессоры, ** kwargs)

Он получает XPath в поле, которое извлекает строки Unicode.

# HTML code: <div class = "item-name">DVD</div>
loader.add_xpath('name', '//div[@class = "item-name"]')

# HTML code: <div id = "length">the length is 45cm</div>
loader.add_xpath('length', '//div[@id = "length"]', re = 'the length is (.*)')
6

replace_xpath (field_name, xpath, * процессоры, ** kwargs)

Он заменяет собранные данные с помощью XPath с сайтов.

# HTML code: <div class = "item-name">DVD</div>
loader.replace_xpath('name', '//div[@class = "item-name"]')

# HTML code: <div id = "length">the length is 45cm</div>
loader.replace_xpath('length', '//div[@id = "length"]', re = 'the length is (.*)')
7

get_css (css, * процессоры, ** kwargs)

Он получает селектор CSS, используемый для извлечения Unicode-строк.

loader.get_css("div.item-name")
loader.get_css("div#length", TakeFirst(), re = "the length is (.*)")
8

add_css (имя_поля, css, * процессоры, ** kwargs)

Он похож на метод add_value () с одним отличием в том, что он добавляет селектор CSS в поле.

loader.add_css('name', 'div.item-name')
loader.add_css('length', 'div#length', re = 'the length is (.*)')
9

replace_css (имя_поля, css, * процессоры, ** kwargs)

Он заменяет извлеченные данные с помощью селектора CSS.

loader.replace_css('name', 'div.item-name')
loader.replace_css('length', 'div#length', re = 'the length is (.*)')
10

load_item ()

Когда данные собраны, этот метод заполняет элемент собранными данными и возвращает их.

def parse(self, response):
l = ItemLoader(item = Product(), response = response)
l.add_xpath('title', '//div[@class = "product_title"]')
loader.load_item()
11

nested_xpath (XPath)

Он используется для создания вложенных загрузчиков с помощью селектора XPath.

loader = ItemLoader(item = Item())
loader.add_xpath('social', 'a[@class = "social"]/@href')
loader.add_xpath('email', 'a[@class = "email"]/@href')
12

nested_css (CSS)

Он используется для создания вложенных загрузчиков с помощью селектора CSS.

loader = ItemLoader(item = Item())
loader.add_css('social', 'a[@class = "social"]/@href')
loader.add_css('email', 'a[@class = "email"]/@href')	

get_value (значение, * процессоры, ** kwargs)

При заданном аргументе процессора и ключевого слова значение обрабатывается методом get_value ().

add_value (field_name, value, * processors, ** kwargs)

Он обрабатывает значение и добавляет его в поле, где оно сначала передается через get_value, передавая процессоры и аргументы ключевых слов перед передачей через поле ввода процессора.

replace_value (имя_поля, значение, * процессоры, ** kwargs)

Он заменяет собранные данные новым значением.

get_xpath (xpath, * процессоры, ** kwargs)

Он используется для извлечения строк Юникода, давая процессоры и аргументы ключевых слов, получая XPath .

add_xpath (имя_поля, xpath, * процессоры, ** kwargs)

Он получает XPath в поле, которое извлекает строки Unicode.

replace_xpath (field_name, xpath, * процессоры, ** kwargs)

Он заменяет собранные данные с помощью XPath с сайтов.

get_css (css, * процессоры, ** kwargs)

Он получает селектор CSS, используемый для извлечения Unicode-строк.

add_css (имя_поля, css, * процессоры, ** kwargs)

Он похож на метод add_value () с одним отличием в том, что он добавляет селектор CSS в поле.

replace_css (имя_поля, css, * процессоры, ** kwargs)

Он заменяет извлеченные данные с помощью селектора CSS.

load_item ()

Когда данные собраны, этот метод заполняет элемент собранными данными и возвращает их.

nested_xpath (XPath)

Он используется для создания вложенных загрузчиков с помощью селектора XPath.

nested_css (CSS)

Он используется для создания вложенных загрузчиков с помощью селектора CSS.

В следующей таблице показаны атрибуты объектов ItemLoader –

Sr.No Атрибут и описание
1

вещь

Это объект, на котором Item Loader выполняет разбор.

2

контекст

Это текущий контекст загрузчика элементов, который активен.

3

default_item_class

Он используется для представления элементов, если он не указан в конструкторе.

4

default_input_processor

Поля, в которых не указан процессор ввода, являются единственными, для которых используются default_input_processors.

5

default_output_processor

Поля, в которых не указан выходной процессор, являются единственными, для которых используются default_output_processors.

6

default_selector_class

Это класс, используемый для создания селектора, если он не задан в конструкторе.

7

селектор

Это объект, который можно использовать для извлечения данных с сайтов.

вещь

Это объект, на котором Item Loader выполняет разбор.

контекст

Это текущий контекст загрузчика элементов, который активен.

default_item_class

Он используется для представления элементов, если он не указан в конструкторе.

default_input_processor

Поля, в которых не указан процессор ввода, являются единственными, для которых используются default_input_processors.

default_output_processor

Поля, в которых не указан выходной процессор, являются единственными, для которых используются default_output_processors.

default_selector_class

Это класс, используемый для создания селектора, если он не задан в конструкторе.

селектор

Это объект, который можно использовать для извлечения данных с сайтов.

Вложенные Погрузчики

Он используется для создания вложенных загрузчиков при разборе значений из подраздела документа. Если вы не создаете вложенные загрузчики, вам нужно указать полный XPath или CSS для каждого значения, которое вы хотите извлечь.

Например, предположим, что данные извлекаются из страницы заголовка –

<header>
   <a class = "social" href = "http://facebook.com/whatever">facebook</a>
   <a class = "social" href = "http://twitter.com/whatever">twitter</a>
   <a class = "email" href = "mailto:someone@example.com">send mail</a>
</header>

Затем вы можете создать вложенный загрузчик с селектором заголовка, добавив связанные значения в заголовок –

loader = ItemLoader(item = Item())
header_loader = loader.nested_xpath('//header')
header_loader.add_xpath('social', 'a[@class = "social"]/@href')
header_loader.add_xpath('email', 'a[@class = "email"]/@href')
loader.load_item()

Повторное использование и расширение загрузчиков предметов

Загрузчики предметов предназначены для облегчения обслуживания, которое становится фундаментальной проблемой, когда ваш проект приобретает больше пауков.

Например, предположим, что на сайте название продукта заключено в три черты (например, –DVD —). Вы можете удалить эти черточки, повторно используя загрузчик элементов товара по умолчанию, если вы не хотите, чтобы он был в окончательных названиях продуктов, как показано в следующем коде –

from scrapy.loader.processors import MapCompose 
from demoproject.ItemLoaders import DemoLoader  

def strip_dashes(x): 
   return x.strip('-')  

class SiteSpecificLoader(DemoLoader): 
   title_in = MapCompose(strip_dashes, DemoLoader.title_in)

Доступные встроенные процессоры

Ниже приведены некоторые из наиболее часто используемых встроенных процессоров:

класс scrapy.loader.processors.Identity

Возвращает исходное значение без изменения. Например –

>>> from scrapy.loader.processors import Identity
>>> proc = Identity()
>>> proc(['a', 'b', 'c'])
['a', 'b', 'c']

класс scrapy.loader.processors.TakeFirst

Возвращает первое значение, которое не является нулевым / непустым из списка полученных значений. Например –

>>> from scrapy.loader.processors import TakeFirst
>>> proc = TakeFirst()
>>> proc(['', 'a', 'b', 'c'])
'a'

класс scrapy.loader.processors.Join (разделитель = u ”)

Возвращает значение, прикрепленное к разделителю. Разделителем по умолчанию является u ”, и он эквивалентен функции u ” .join . Например –

>>> from scrapy.loader.processors import Join
>>> proc = Join()
>>> proc(['a', 'b', 'c'])
u'a b c'
>>> proc = Join('<br>')
>>> proc(['a', 'b', 'c'])
u'a<br>b<br>c'

класс scrapy.loader.processors.Compose (* функции, ** default_loader_context)

Он определяется процессором, в котором каждое его входное значение передается первой функции, а результат этой функции передается второй функции и т. Д., Пока функция ast не вернет конечное значение в качестве вывода.

Например –

>>> from scrapy.loader.processors import Compose
>>> proc = Compose(lambda v: v[0], str.upper)
>>> proc(['python', 'scrapy'])
'PYTHON'

класс scrapy.loader.processors.MapCompose (* функции, ** default_loader_context)

Это процессор, в котором входное значение повторяется, и первая функция применяется к каждому элементу. Затем результат этих вызовов функций объединяется для создания новой итерации, которая затем применяется ко второй функции и т. Д. До последней функции.

Например –

>>> def filter_scrapy(x): 
   return None if x == 'scrapy' else x  

>>> from scrapy.loader.processors import MapCompose 
>>> proc = MapCompose(filter_scrapy, unicode.upper) 
>>> proc([u'hi', u'everyone', u'im', u'pythonscrapy']) 
[u'HI, u'IM', u'PYTHONSCRAPY'] 

класс scrapy.loader.processors.SelectJmes (json_path)

Этот класс запрашивает значение, используя предоставленный путь json, и возвращает выходные данные.

Например –

>>> from scrapy.loader.processors import SelectJmes, Compose, MapCompose
>>> proc = SelectJmes("hello")
>>> proc({'hello': 'scrapy'})
'scrapy'
>>> proc({'hello': {'scrapy': 'world'}})
{'scrapy': 'world'}

Ниже приведен код, который запрашивает значение путем импорта json –