Python кодировка UTF8 и MySQL
Многочасовые пляски с бубном наконец то привели к желаемому результату и в базу все пишется в нормальной кодировке. Проблема оказалась в том что в самой MySQL была по умолчанию кодировка latin1 а не utf-8
вот так вот все это проявлялось:
$ python yelp.py
восточного ао управа района богородское
yelp.py:148: Warning: Incorrect string value: '\xD0\xB2\xD0\xBE\xD1\x81...' for column 'name' at row 1
cursor.execute("""INSERT INTO grab_moscow (name) VALUES(%s)""",(title))посмотреть какая сейчас кодировка в MySQL можно этим запросом:
SHOW VARIABLES LIKE 'char%';
я создавал базу с помощью MySQL Query Browser, а правильнее было бы создавать запросом типа этого
CREATE DATABASE db CHARACTER SET utf8 COLLATE utf8_general_ci;
При использовании модуля MySQLdb в python необходимо указать следующее:
conn = MySQLdb.connect(host = "localhost", user = "root", passwd = "secretpassword", db = "yp", use_unicode = 1, charset = 'utf8' ) conn.set_character_set('utf8') cursor = conn.cursor() cursor.execute('SET NAMES utf8') cursor.execute('SET CHARACTER SET utf8') cursor.execute('SET character_set_connection=utf8')
Куски из кода - грабер сайта "Желтые страницы", в ходе написания в очередной раз на практике убедился в том что чем проще решение тем оно лучше. По сути это и является принципом большинства Unix систем, множество маленьких программ, которые хорошо и безглючно работают. Год или 1.5 года назад, когда я только начал более менее серьезно заниматься веб-программированием я делал сайт под партнерку mp3sugar.com. Нужно было сделать какой то сайт, чтобы было чего показывать на собеседованиях, а для этого все работодатели требовали рабочие интернет-проекты и свой код.
Тогда я начал с нуля писать движок для сайта под эту партнерку, написание самого движка много времени не заняло. Потом я решил сграбить сайт с текстами песен, выдернуть из него все тексты и объеденить все это с сахарной базой. Сначала для скачивания сайта я натравил Teleport Pro (полную версию), он работал всю ночь, а на утро я обнаружил что он скачал что-то типа 64000 страниц и больше он не может. Ограничение такое в программе хотя она и платная. Потом скачал бесплатный Httrack, он таки все нормально выкачал.
Сейчас нарыл на винте те регулярные выражения которыми все парсилось, тогда я только учился их писать и вообще не знал, так что вот пример как их писать НЕ надо :)
result_urls = re.findall(r'/search/\?s=.*(?=")', text) result_artists = re.findall(r'(?!/search/\?s=.*".*class=st>.*)(?< =class=st>).*(?< =[^])(?< =[^\[\?\] <a HREF="/browse/A/P2.html"><strong>»</strong></a>\s\s\s)', text) result_songs = re.findall(r'(?!/search/\?s=.*".*class=st>.*)(?< =class=st>).*(?< =[^])(?< =[^\[\?\]Текст.*песни)(?< =Текст.песни).*(?< =[^])
Скачанный сайт на жестком диске занимал что-то около 8 гигов, и все это парсилось и запихивалось в базу наверно часа 2-3. Чуть ниже пример эволюции в написании граберов :) 15000 данных о фирмах скачались минут за 20, это при том что я специально выставил задержку в 5 секунд после каждой страницы чтобы меня не забанили на файрволе как злобного dos-атакера.
regexp = { 'items' : r"""<a CLASS="comp_header" HREF="(.*)">(.*)</a>""",
'pages' : r"""
<td><a HREF="(.*)"><img TITLE="на 1 страницу вперед" ALT="на 1 страницу вперед" BORDER="0" HEIGHT="9" WIDTH="5" SRC="http:\/\/img.ypages.ru\/pager\/forward_1_on.gif" />< \/a></a></td>
""",
#'pages' : r""" <a CLASS="apage" HREF="(.+)">""",
'item_d_title' : r"""
</a>
Почтовый адрес (.+):
""",
'item_d_address' : r"""
<a TARGET="_blank" HREF="http://www.postindex.ru/(.+)">(.+)</a>, (.+?)(<span CLASS="noprint|</div">
)""",
'item_d_telephone' : r"""
</span>т (.+)
""",
'item_d_website' : r"""
<a TARGET="_blank" HREF="(.+)">""",
'item_d_metro' : r"""
<p CLASS="c-info"><img VSPACE="1" HSPACE="1" STYLE="background-color: #0077ce" ALT="(.+)" SRC="http:\/\/img.ypages.ru\/metro\/metrologo.gif" /> (.+),""",
'item_d_postcode' : r"""
</p><p CLASS="c-info"><a TARGET="_blank" HREF="(.+)">(.+)</a>,""",
}
regexp_group = { 'items' : 1,
'pages' : 1,
'item_d_title' : 1,
'item_d_address' : 3,
'item_d_telephone' : 1,
'item_d_website' : 1,
'item_d_metro' : 2,
'item_d_postcode' : 2
}Я пишу все это не к тому чтобы показать какой я типа умный, а к тому что упрощение намного ускоряет решение задач, и зачастую все то что проще сделано работает надежнее и быстрее. Сначала я хотел дергать страницу, загружать ее как XML документ, находить нужную ветку и оттуда брать то что надо. К счастью для меня наверно, html-код страницы был настолько криво написан что tidy его даже не смог сделать нормальным, и dom парсер не смог его загрузить, тогла я плюнул и за несколько минут написал эти регулярные выражения, в чем очень помогает бесплатная утилитка kodos (под виндой тоже работает).