Записки программиста, обо всем и ни о чем. Но, наверное, больше профессионального.

2013-06-28

Iceweasel

У меня на десктопе (Debian Linux) уж сто-лет-в-обед основным браузером трудится Firefox. На подхвате у него Chrome. Про системный Iceweasel я и забыл уже — так давно его не видел. Это как-бы предистория. А, чуть не забыл, при щелчке на линках в документах или чатах или еще где открывается Firefox, как и положено основному браузеру.

А вот вчера произошло странное: щелкаю я правой кнопкой по иконке дропбокса, выбираю «Launch Dropbox Website» и, внезапно, запускается тот самый Iceweasel! Я не понял, с каких таких ватрушек? Полез разбираться.


Сразу скажу — двух часов мне не хватило на отыскание способа починки. Сдаюсь.

Удалять пакет iceweasel стремно — слишком много зависимостей на нем.
Заклинания типа
update-alternatives --install /usr/bin/x-www-browser x-www-browser /opt/firefox/firefox 100
update-alternatives --config x-www-browser
xdg-mime, xdg-open
не помогают. Да оно, в общем, и понятно — система в норме, кроме дропбокса никто Вию веки не поднимает айсвизел не запускает.

Склоняюсь к мнению, что это дефект/эффект/бага/фича дропбокса и мне проще не пользоваться этим пунктом меню. Тем более, что нужен он мне раз в год.

Зато попался чудный материал: руководство/обзор masthave софта для десктопа под Debian - http://debianhelp.wordpress.com/2012/10/02/crunchbang-11-waldorf-debian-wheezy-os/


original post http://vasnake.blogspot.com/2013/06/iceweasel.html

2013-06-27

CopyQ

Очень интересная утилита для работы с буфером обмена (clipboard):

CopyQ - это менеджер буфера обмена, написанный с использованием Qt, имеющий продвинутые возможности, поддержку изображений, редактируемую историю, поддержку командной строки, горячих клавиш, и многое другое. Приложение работает под Linux и Windows


  • Supports Linux (X11) and Windows.
  • Store text, HTML, images and any other custom format.
  • Customize tray menu.
  • Save items in new tabs.
  • Quickly browse through items (fast navigation, filtering with matched text highlighting).
  • Sort items, create new, remove, copy/paste to different tab.
  • Variety of system-wide shortcuts (e.g. show main window or tray, edit clipboard, copy next/previous item, paste as plain text).
  • Immediately paste to focused window from tray or main window.
  • Fully customizable appearance (colors, fonts, transparency).
  • Advanced command-line interface and scripting.
  • Ignore clipboard copied from some windows or containing some text.
  • Apply custom commands on selected items or automatically when new matching clipboard content is available.


Готовые сборки здесь:

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


Надо будет потестировать.

original post http://vasnake.blogspot.com/2013/06/copyq.html

2013-06-26

input background-image

Поговорим про веб верстку: html, css.

Вчера обнаружил пренеприятное поведение браузера Chrome. Эта падла на ходу подметки рвет подменяет мой background-image на свой, в элементе input text, в момент получения элементом фокуса.

Отладка показывает стили — до клика в элемент:
element.style {
background-image: url(/static/search.png);
background-position: 0% 0%;
background-repeat: repeat repeat;
}

После клика:

Что характерно, пришлось делать скриншот, ибо любой клик мышкой снимает состояние «focus» с элемента.

На скриншоте хорошо видно, что background-image поменялся на «data:image/png;base64, iVBORw0KG...», который представляет собой прозрачную png-шку размерами 16х16 пикселей.

Это поведение можно видеть на примере поля «поиск» на странице plone.org. Просто откройте http://plone.org/ в Chrome и кликните в поле поиска. Картинка, образующая скругленные углы и иконку поиска — пропадает незамедлительно. Беда небольшая, когда это происходит на белом фоне. А мне что делать?

И это я еще в MSIE верстку сайта не проверял.




original post http://vasnake.blogspot.com/2013/06/input-background-image.html

2013-06-25

Pyramid

Осваивать что-либо удобнее на примерах. Вот пример создания веб-приложения на Pyramid/Pylons:

веб-приложение «Бар желаний», созданное за один день с помощью Python и Pyramid.
Может быть, после прочтения статьи кто-то решит повторно использовать «Бар желаний» для поздравлений. Возможно, кто-то откроет для себя Pyramid — веб-фреймворк, прекрасно подходящий для быстрого создания небольших веб-проектов. Наконец, можно просто забрать исходный код приложения с GitHub для использования в своих целях.
В статье показан процесс разработки небольшого веб-приложения, начиная с постановки задачи и проектирования и заканчивая развертыванием приложения на сервере. По ходу статьи приведены комментарии к реализации, которые объясняют на примерах некоторые принципы работы веб-приложений в общем и Pyramid в частности. Таким образом, статью можно рассматривать также как руководство по Pyramid для начинающих на примере реальной задачи.
После того, как веб-приложение было готово, встал вопрос о способе его развертывания на сервере в локальной сети под управлением Ubuntu. Я вбил в поиск запрос «Pyramid setup.py» и обнаружил документ, с которым мне следовало ознакомиться в самом начале. Документ описывает стандартный способ создания Pyramid-проектов.
Утилита pcreate автоматически генерирует типовую структуру проекта и создает файл setup.py для нового веб-приложения, в котором уже прописаны все зависимости. Необходимо перейти на уровень выше нашего проекта и запустить в консоли pcreate -s starter wishbar


Материал вполне годится для «быстрого старта».

original post http://vasnake.blogspot.com/2013/06/pyramid.html

2013-06-24

Поломки и починки

Как-то накопилось материала про поломки. Это всё луна.

Виндсерфинг.
В пятницу ветер задувал с севера до 10 м/с на порывах. Конечно же мы не могли пропустить такое редкое событие и поехали катацца в Строгино. Сходу выяснилось, что трамвая (№30 или №15) не будет, ибо ветер сронял дерево а дерево перебило провод. Ой. Ладно, поехали на такси, ехали по пробкам пять километров более получаса. Так или иначе — добрались до места, хоть и с отставанием от графика на полчаса. По словам катальщиков — «час назад дуло лучше». Ой.
Но нам и так хвтило, накатались, заодно и парус порвали. По словам Наташки, она убралась коленом в парус, после чего он треснул по шву в нижнем окне.

Повесили парус сушиться до субботы, в субботу стали латать. Ильич выдал нам два куска липкой пленки, SEKISUI #5760, и мы с двух сторон налепили их поверх разрыва. Адгезия жуткая, но разрыв неудачный, на стыке ткани и пленки — теоретически, латка отвалится. Такие повреждения надо зашивать (ripstop, dacron с клейкой стороной). Будем посмотреть. Еще люди пременяют армированный скотч и пленку ORACAL для починки парусов.

Кстати, в субботу трамвай опять не ходил — столб упал. Два дня подряд нам такая удача.


Virtualbox.
В понедельник я обновлял станцию и заметил, что Virtualbox.обновился до верси 4.2.14. Под это дело я решил побороть проблему отсутствия
/usr/share/virtualbox/VBoxCreateUSBNode.sh
во время загрузки, когда раздел /usr сделан отдельно от корневого.

Рецепт очень простой:
locate VBoxCreateUSBNode.sh
cp /usr/share/virtualbox/VBoxCreateUSBNode.sh /lib/udev/
nano /etc/udev/rules.d/10-vboxdrv.rules
в 10-vboxdrv.rules заменить /usr/share/virtualbox/ на /lib/udev/.
Вообще замену можно сделать одной командой типа «sed», но я не настолько врос в консоль. Мне проще ручками перебить.

Забавно то, что после исправления этой ошибки, доступа к USB по прежнему не было «Could not load the Host USB Proxy Service (VERR_FILE_NOT_FOUND)».
Пришлось сделать еще одну починку:
grep vbox /etc/group
    vboxusers:x:119:
nano /etc/fstab
# 119 is vboxusers
none     /proc/bus/usb     usbfs      devgid=119,devmode=666    0    0
И после перезапуска хоста, наконец, USB стал доступен в гостевых машинах Virtualbox. Ура.

Сцылки:


original post http://vasnake.blogspot.com/2013/06/blog-post_24.html

2013-06-20

YAML Ain’t Markup Language (YAML™)

Так назывемый «рекурсивный акроним» - YAML.
Оказывается, YAML это, формально, надмножество JSON:

YAML can therefore be viewed as a natural superset of JSON, offering improved human readability and a more complete information model. This is also the case in practice; every JSON file is also a valid YAML file. This makes it easy to migrate from JSON to YAML if/when the additional features are required.

JSON's RFC4627 requires that mappings keys merely “SHOULD” be unique, while YAML insists they “MUST” be. Technically, YAML therefore complies with the JSON spec, choosing to treat duplicates as an error. In practice, since JSON is silent on the semantics of such duplicates, the only portable JSON files are those with unique keys, which are therefore valid YAML files.


Так чем же отличается YAML от JSON?
Разница в целеполагании: JSON упирает на простоту и универсальность, что приводит к легкости генерирования и парсинга но ухудшает читаемость глазом. YAML делает акцент на читаемости глазом и поддержке сериализации произвольных структур данных, что приводит к относительно более медленной работе парсера и сериализатора.



original post http://vasnake.blogspot.com/2013/06/yaml-aint-markup-language-yaml.html

2013-06-18

И опять CDATA

Намедни я тут зафиксировал одну проблему, проявляющуюся как результат неудачного совмещения визуального редактора TinyMCE и библиотеки фильтрации кода HTML. Используя TinyMCE, в Plone невозможно добавить на страницу Javascript. Редактор оборачивает его в «CDATA» а Плоновская библиотека фильтрации вырезает это содержимое при рендеринге страницы.

Я тут покопался в деталях, из любопытства, нашел корень проблемы:
    def parse_declaration(self, i):
        """Fix handling of CDATA sections. Code borrowed from BeautifulSoup.
        """
        j = None
        if self.rawdata[i:i+9] == '<![CDATA[':
            k = self.rawdata.find(']]>', i)
            if k == -1:
                k = len(self.rawdata)
            j = k+3
        else:
            try:
                j = SGMLParser.parse_declaration(self, i)
            except SGMLParseError:
                j = len(self.rawdata)
        return j

Хотя, по чесноку, корень проблемы в том, что не следует внедрять код Javascript в страницу. Надо подключать внешние файлы.

Что интересно:

sgmllib — Simple SGML parser
Deprecated since version 2.6: The sgmllib module has been removed in Python 3



То есть следующая версия Plone не должна использовать SGMLParser, а это большая работа по замене кода.

original post http://vasnake.blogspot.com/2013/06/cdata.html

Plone site home page

Всем хороша Plone CMS, но в семье не без урода.

Как и любая порядочная CMS, Plone позволяет создавать и удалять папки (разделы сайта) и страницы. Именовать их и переименовывать. За одним исключением — самая первая страница сайта, «Home» или, по русски, «Главная». Переименовать ее невозможно. Можно только спрятать, что многие и делают. Только это не решает проблему а лишь чуть маскирует. Типа мусор под ковром.

Слушайте сюда, истину говорю вам — я знаю как переименовать эту «главную» страницу. Кстати, этим же способом можно переименовать любой текст или сообщение Plone

Так вот, переименовать папку/страницу «Главная»/«Home» можно. Только делается это слегка перректально, а именно - через Buildout.
Вкратце, нужно создать свой Python package, добавить в него файлы локализации/интернационализации, и включить этот пакет в сборку Plone.
Как это сделал я - читайте далее


Можете насладиться пельмешком.


original post http://vasnake.blogspot.com/2013/06/plone-site-home-page.html

2013-06-14

Flask-Foundation

Я гляжу, многим нравится Flask:

Стал использовать Flask для небольших проектов. Django неимоверно разрослась, да и просто замылила глаз
В целом Flask мне нравится. Код чище, его меньше, работает быстрее. SQLAlchemy на голову уделывает на текущий момент Django ORM.
Но порог вхождения гораздо выше, как ни странно, множество задач уже решенных сообществом Django тут приходится решать заново.


Все верно, по сравнению с Django, Flask это весьма минималистичный фреймворк. Это его преимущество и это его недостаток, дуализъм, понимашь.
Тем же, кому хочется «все-в-одном» как в Django, только без Django, посвящена такая сборка:

Я собрал свою сборку: http://github.com/klen/Flask-Foundation базового проекта на Flask, содержащую следующие вещи:
Проект содержит богатый функционал и может послужить хорошим примером для быстрого старта.



Хорошая Фляжка, годная.

original post http://vasnake.blogspot.com/2013/06/flask-foundation.html

2013-06-13

TinyMCE, Plone & Javascript

Столкнулся вчера с занятными (г|т)раблями — никак не получалось у меня добавить на страничку в Plone код Javascript. Ну, типа такого:
<img src="http://www.onsite.ru/ftp/vivwater/webcam.jpg" name="webcam">
<script language="JavaScript">
function go()
{
  var now = new Date();
  var stamp= parseInt(now.getTime() / 1000);  document.images.webcam.src="http://www.onsite.ru/ftp/vivwater/webcam.jpg?"+stamp;
  setTimeout("go()", 2000);
}
setTimeout("go()", 1000);
</script>

Понятное дело, сначала я проверил, не отфильтровываются ли напрочь «вредные» теги. Толковую инструкцию я нашел только одну
зато она годится для любых случаев. Хотя, как оказалось, не любых.

После серии бесплодных попыток, я выяснил, что используемый редактор (TinyMCE) оборачивает код Javascript. в тег CDATA. Получается у него вот так:
<script language="JavaScript">
// <![CDATA[
function go()
{
  var now = new Date();
  var stamp= parseInt(now.getTime() / 1000);  document.images.webcam.src="http://www.onsite.ru/ftp/vivwater/webcam.jpg?"+stamp;
  setTimeout("go()", 2000);
}
setTimeout("go()", 1000);
// ]]>
</script>
Такая обертка приводит к тому, что шаблонизатор Plone вырезает из выдачи код скрипта.
В коде отрендеренной страницы видно такое:
<script language="JavaScript">
//
</script>
Здорово, правда?

И что с этим делать — неясно. Если бы CDATA был нормальным тегом, можно было бы добавить его в список исключений. Я пробовал — не выходит.

В итоге пришлось идти в обход. В настройках своей учетной записи в Plone я выбрал в качестве редактора «нет редактора», то есть страницу сайта редактировать придется в HTML, никакого WYSIWYG, зато и «интеллекта» вредного тоже нет. Убрал я тег CDATA из кода страницы ручками и всё у меня получилось.

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


original post http://vasnake.blogspot.com/2013/06/tinymce-plone-javascript.html

2013-06-12

Big fin

Как только я понял, что шверт мне уже не нужен, сразу задумался — а какой тогда нужен плавник (fin)?

Всем известно, что изготовители ставят на доски стоковые плавники по принципу «чтоб был», хорошим стоковый плавник еще никто не называл. Это раз.
Маленький или неудачный плавник может мешать выходу на глиссирование, вызывать спинаут, не давать резаться на ветер. Это два.
Для больших парусов, для широких досок, для сильного ветра, для тяжелого серфера надо плавник побольше. Это три.

С другой стороны, слишком большой плавник мешает делать beach start, за все цепляется и создает повышенное сопротивление движению.

Вот сижу и думаю, какой же мне предпочесть плавник для доски Starboard Start 2006-2007 с парусом 6-7.5 метров?

Стоковый плавник там Drake Shallow 410 с креплением Deep Tuttle, уже изрядно побитый. Судя по некоторым источникам, такого плавника должно хватать вплоть до 8-ми метровых парусов.

А по другим источникам, серъезные пацаны, которые любят гонять по плоской воде в слабый ветер, ставят плавник не менее 62 сантиметров для парусов 8.5 и говорят, что 54 см. плавник — очевидно недостаточно.

I've used a 54cm NSM in the Start. You WILL be disappointed with spinout
and total lack of upwind ability on a 54cm fin. This not the fault of the
fin as that same fin works great in my friend's F2 Course Large (65cm wide).
The problem is that the 100cm wide Start just give you so much leverage over
the fin you will need to go bigger. I find a 62cm fin was the minimum for
reasonable performance. I use a 70cm every time with this board for
comfortable reaching you can lean on with good upwind results. I sold my 62
to a friend to use in his Start and it works well for him at 165 lbs and 8.5
sail. I am 195lb and on 8.5 sail.

Что любопытно, при грамотном использовании доски Starboard Start, на ней можно обгонять любителей формулы.

I have seen big guys with big sails on a Start blow past many other
boards -- never underestimate a Freight Train once it is up to speed...The
Start is a big guy's dream for more planing time as long as they will go for
a truly big and powerful sail combined with the biggest fins. Put a 70 cm
on one and board comes alive. Ray hostinghostinghostinghostingz even rides an 80 cm fin with his Start, and I've seen Ray mow down a handful of formula boards in a drag
race.

Вывод наверное такой — до тех пор, пока спинауты не проявляются и ходить upwind получается без проблем, новый плавник не нужен. Тем более, что цена вопроса — более $100.

The 41 cm fin is for beginners. It's a "trainer" fin.
If you are using sails > 7.0 m2, the 41 cm fin really is not very good.
> 7.0 you need the regular fin that normally comes with the GO 171.
What size rigs do you plan to use.
A 32-38 cm weed fin will normally replace a 40-48 cm vertical fin, but
sail size is the most important parameter here.

If you have weeds, weed fin is the answer. Regarding need for fin for better performance, the fin is not the problem.
You will need a bigger fin when you are planing on this board without the dagger board and you want to plane earlier with a 7.5 and larger sail. Then you want a 60 cm or bigger fin. Until then, except for the weeds, the fin is not the answer to your performance issues.


original post http://vasnake.blogspot.com/2013/06/big-fin.html

2013-06-11

Исследуем безопасность

Мощная штука, этот Kali Linux, просто чемоданчик взломщика. А в нашем законодательстве вроде как статья есть за хранение и распространение подобного софта.

дистрибутив для исследования безопасности систем - Kali Linux, пришедший на смену ранее развиваемому проекту BackTrack Linux
...
Kali, как и BackTrack, содержит одну из самых богатых подборок программ, связанных с безопасностью: от средств для тестирования web-приложений и проникновения в беспроводные сети, до программ для считывания данных с идентификационных RFID чипов. В комплект входит коллекция эксплоитов и более 300 специализированных утилит для проверки безопасности, таких как Aircrack, Maltego, Metasploit, SAINT, Kismet, Bluebugger, Btcrack, Btscanner, Nmap, p0f. Помимо этого, в дистрибутив включены средства для акселерации подбора паролей (Multihash CUDA Brute Forcer) и WPA ключей (Pyrit) через задействование технологий CUDA и ATI Stream, позволяющих использовать GPU видеокарт NVidia и ATI для выполнения вычислительных операций.
...
Дистрибутив позиционируется как профессиональная версия BackTrack Linux, готовая для использования в корпоративной среде и учитывающая возможные потребности отвечающего за безопасность IT-персонала по адаптации дистрибутива для инфраструктуры предприятия.
...
Ключевым отличием от предшественника является переход на пакетную базу Debian GNU/Linux
...
Для упрощения работы новичков введена новая категория - "Top 10 Security Tools", в которой представлено 10 наиболее востребованных инструментов для проверки безопасности, таких как Aircrack-ng, Hydra, John the Ripper, Metasploit, Nmap, SQLMap, Wireshark и Zaproxy
...
Следствием использования технологий Debian стало существенное расширение средств для кастомизации дистрибутива и увеличение числа доступных для загрузки образов. Кроме LiveDVD-образа (2 Гб) для архитектур i386 и amd64 началось формирование минималистичных консольных сборок, размером 400 Мб. Также отныне доступны сборки для устройств на базе архитектуры ARM, в том числе armel (Raspberry Pi) и armhf (ChromeBook, Odroid U2, RK3306 / SS808). Упрощён процесс формирования собственных сборок - достаточно загрузить базовый файл конфигурации, изменить его на своё усмотрение (например, вместо GNOME выбрать KDE, LXDE, MATE или XFCE), при необходимости пересобрать интересующие пакеты или добавить пакеты из репозиториев Debian, и запустить команду сборки iso-образа или окружения для виртуальной машины




original post http://vasnake.blogspot.com/2013/06/blog-post_8313.html

Шверт не нужен

Ура! Мне не нужен шверт с сегодняшнего дня. Нынче я научился резаться на ветер на бесшвертовой доске. Раньше у меня не получалось, хотя вроде все делал правильно, но выходил либо галфвинд либо снос по ветру. Поэтому без шверта выходить было стремно. Но теперь я знаю тайну.

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

Прощай, шверт.

original post http://vasnake.blogspot.com/2013/06/blog-post_11.html


2013-06-07

Пропала иконка

Как я уже упоминал, после очередного обновления Firefox пропала иконка этого замечательного браузера. Недолгое расследование показало, что добрые разработчики, наводя порядок, переместили картинку в подпапку «browser»:
/opt/firefox/browser/icons/mozicon128.png
Очевидно, что Gnome ищет иконку в другом месте.

Довольно долго у меня руки не доходили до решения проблемы, хотя пустота в ровных рядах иконок напрягала реально, как разглядывание выбитого зуба, примерно.

И вот, пришло время хоббитам зарамсить проблему, иконка восстановлена и без каких либо переустановок софта. Всего-то пришлось вспомнить — как правильно регистрировать аппликуху в Gnome 3.

/home/valik/.local/share/applications/firefox.desktop

в котором указал местоположение иконки. Которую намедни разработчики ФФ снесли в другую папку. Поправить firefox.desktop — дело 5-ти секунд и порядок восстановлен.

original post http://vasnake.blogspot.com/2013/06/blog-post_7.html

2013-06-06

Такая проблемная асинхронность

Как правильно обрабатывать события, которые происходят чаще, чем вы успеваете их обрабатывать?

One solution is to use a sequence number (also known as a change counter) that gets incremented each time the thing changes. If there is only one thread which updates the thing, you can try to update it atomically
...
Another solution would be to detect the re-entrancy and just remember that there is more work to be done after the previous update finishes.


Следует уточнить, что в статье рассматривается достаточно частный случай с Reg­Notify­Change­Key­Value

Как бывает непросто работать с асинхронными событиями, однако.

original post http://vasnake.blogspot.com/2013/06/blog-post_6.html

Имя розы

Посмотрел фильму «Имя розы», в оригинале «The name of the Rose (1986)».

Книгу, помню, читать было занимательнее. Зато нынче, при просмотре, родилось послание к защитникам «чувств верующих»: вы, недостойные, сперва посмотрите этот фильм а потом почитайте исторические труды про крестовые походы, святую инквизицию и прочие достойные деяния, свершенные во имя бога и веры. А потом мы, если захотите, поговорим про «чувства верующих».

original post http://vasnake.blogspot.com/2013/06/blog-post.html

2013-06-04

Crossposting

Люди пишут в дневники с тех пор, как изобрели письменность, много тысяч лет уже. Совсем недавно, с появлением Интернет, появилась новая разновидность дневников — публичная. То, что раньше было «только для себя, на память», стало публичным — средством пиара, коммуникации и утешения тщеславия.

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


Почему? Неужели это никому не нужно?
Вероятнее, это не нужно и даже вредно владельцам сетей.


Попробовать, что-ли самому написать аппликуху для кросспостинга в всякие G+, Facebook, Twitter и прочие Vkонтакте?

original post http://vasnake.blogspot.com/2013/06/crossposting.html

2013-06-03

Psycopg2 cursor description

В Mapfeatureserver у меня есть код, который решает, что делать с текущей колонкой выборки (из БД), на основании типа данных в этой колонке. А работа с БД построена на использовании пакета Psycopg2.
Выглядит это примерно так:
    import psycopg2
    import psycopg2.extensions
    psycopg2.extensions.register_type(psycopg2.extensions.UNICODE)
    psycopg2.extensions.register_type(psycopg2.extensions.UNICODEARRAY)

    conn = psycopg2.connect("host=vags101 port=5432 dbname=postgisdb user=mfs password=12345678 connect_timeout=10 client_encoding=utf8")
    conn.autocommit = True
    cur = conn.cursor()

    cur.execute("""
        select * from mfsdata.patching limit 1;
    """)
    for descr in cur.description:
        if descr.type_code in GEOMETRY_TYPES:
            print 'geometry data'

Это, конечно, очень удобно, когда выборка содержит не только кортежи с данными, но и метаданные. Всё, как в спецификации Python Database API Specification v2.0.
Но есть, как выяснилось, проблема. Фишка в том, что от системы к системе эти коды (cursor.description.type_code) могут меняться, поэтому полагаться на заранее составленный список кодов нельзя.

Документация на Psycopg2 говорит следующее:

type_code: the PostgreSQL OID of the column. You can use the pg_type system table to get more informations about the type. This is the value used by Psycopg to decide what Python type use to represent the value. See also Type casting of SQL types into Python objects.


То есть, код типа это, фактически, идентификатор записи в реестре pg_type, причем повторяемости этих идентификаторов для разных систем можно ожидать только для стандартных типов данных.

Небольшая демонстрация реального положения вещей для таблицы «mfsdata.patching»:
    import psycopg2
    import psycopg2.extensions
    psycopg2.extensions.register_type(psycopg2.extensions.UNICODE)
    psycopg2.extensions.register_type(psycopg2.extensions.UNICODEARRAY)

    conn = psycopg2.connect("host=vags101 port=5432 dbname=postgisdb user=mfs password=12345678 connect_timeout=10 client_encoding=utf8")
    conn.autocommit = True
    cur = conn.cursor()

    cur.execute("""
        select * from mfsdata.patching limit 1;
    """)
    for rec in cur.description:
        print "Field name: '%s', field type_code: '%s'" % (rec.name, rec.type_code)

    cur.execute("""
        SELECT attname, atttypid FROM pg_attribute WHERE attrelid = 'mfsdata.patching'::regclass;
    """)
    for rec in cur:
        print "(Field name, field type_code): '%s'" % (rec,)

    cur.execute("""
        select pg_type.oid as type_code, pg_type.typname as type_name, pg_attribute.attname as field_name
            from pg_type, pg_attribute
            where pg_type.oid = pg_attribute.atttypid and pg_attribute.attrelid = 'mfsdata.patching'::regclass;
    """)
    for rec in cur:
        print "(type_code, type name, field name): '%s'" % (rec,)

В связи с ненадежностью решения на списках type_code возникает вопрос — как определять тип поля в выборке?

Одно из решений описано тут http://initd.org/psycopg/docs/advanced.html#type-casting-from-sql-to-python - при загрузке модуля зарегистрировать интересующие типы данных вручную.

Но в моем случае, проще будет воспользоваться заранее созданным файлом метаданных слоя. Там, по спецификации, есть описания полей с указанием их типов.

original post http://vasnake.blogspot.com/2013/06/psycopg2-cursor-description.html

Архив блога

Ярлыки

linux (241) python (191) citation (186) web-develop (170) gov.ru (159) video (124) бытовуха (115) sysadm (100) GIS (97) Zope(Plone) (88) бурчалки (84) Book (83) programming (82) грабли (77) Fun (76) development (73) windsurfing (72) Microsoft (64) hiload (62) internet provider (57) opensource (57) security (57) опыт (55) movie (52) Wisdom (51) ML (47) driving (45) hardware (45) language (45) money (42) JS (41) curse (40) bigdata (39) DBMS (38) ArcGIS (34) history (31) PDA (30) howto (30) holyday (29) Google (27) Oracle (27) tourism (27) virtbox (27) health (26) vacation (24) AI (23) Autodesk (23) SQL (23) humor (23) Java (22) knowledge (22) translate (20) CSS (19) cheatsheet (19) hack (19) Apache (16) Klaipeda (15) Manager (15) web-browser (15) Никонов (15) functional programming (14) happiness (14) music (14) todo (14) PHP (13) course (13) scala (13) weapon (13) HTTP. Apache (12) SSH (12) frameworks (12) hero (12) im (12) settings (12) HTML (11) SciTE (11) USA (11) crypto (11) game (11) map (11) HTTPD (9) ODF (9) Photo (9) купи/продай (9) benchmark (8) documentation (8) 3D (7) CS (7) DNS (7) NoSQL (7) cloud (7) django (7) gun (7) matroska (7) telephony (7) Microsoft Office (6) VCS (6) bluetooth (6) pidgin (6) proxy (6) Donald Knuth (5) ETL (5) NVIDIA (5) Palanga (5) REST (5) bash (5) flash (5) keyboard (5) price (5) samba (5) CGI (4) LISP (4) RoR (4) cache (4) car (4) display (4) holywar (4) nginx (4) pistol (4) spark (4) xml (4) Лебедев (4) IDE (3) IE8 (3) J2EE (3) NTFS (3) RDP (3) holiday (3) mount (3) Гоблин (3) кухня (3) урюк (3) AMQP (2) ERP (2) IE7 (2) NAS (2) Naudoc (2) PDF (2) address (2) air (2) british (2) coffee (2) fitness (2) font (2) ftp (2) fuckup (2) messaging (2) notify (2) sharepoint (2) ssl/tls (2) stardict (2) tests (2) tunnel (2) udev (2) APT (1) Baltic (1) CRUD (1) Canyonlands (1) Cyprus (1) DVDShrink (1) Jabber (1) K9Copy (1) Matlab (1) Portugal (1) VBA (1) WD My Book (1) autoit (1) bike (1) cannabis (1) chat (1) concurrent (1) dbf (1) ext4 (1) idioten (1) join (1) krusader (1) license (1) life (1) migration (1) mindmap (1) navitel (1) pneumatic weapon (1) quiz (1) regexp (1) robot (1) science (1) seaside (1) serialization (1) shore (1) spatial (1) tie (1) vim (1) Науру (1) крысы (1) налоги (1) пианино (1)