Публикации с меткой «django advent»

Блог django на хабрахабре

Django Framework / [Перевод] Сглаживая кривую

Практически для всех возможностей Django существуют способы модификации и расширения. Крайне редко может понадобиться переписывать существенную часть функционала Django только для того, чтобы изменить действие какого-то инструмента. Например, если вы хотите изменить внешний вид формы, вы можете отказаться от внешнего вида «по умолчанию» и создать собственное поле, или даже просто использовать собственный HTML. В обоих случаях вы выигрываете по спектру возможностей, сохраняя все остальные преимущества библиотеки форм.

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

До выхода в свет версии Django 1.2 для ORM такая кривая имела аналогичный вид, за одним исключением: существенный скачок в конце. Этот скачок появлялся в связи с тем, что при необходимости создания нестандартного SQL-запроса требовалось выйти за пределы ORM. Чтобы использовать определённый функционал ORM, пользователю пришлось бы создавать его заново самостоятельно, хоть это и не является само по себе катастрофой. В версии Django 1.2 добавлен метод Model.objects.raw (), который решает эту проблему и, таким образом, сглаживает эту кривую для ORM.

Изучаем Django

Smoothing The Curve

.article header { font-family:LeagueGothicRegular,Impact,sans-serif; font-weight:normal; height:100px; margin-bottom:20px; position:relative; text-transform:uppercase; display: block; } .article header h1 { color:#586C78; font-size:42px; font-weight:normal; height:60px; left:0; letter-spacing:1px; line-height:60px; position:absolute; top:10px; } .article header h2 { color:#CCCCCC; font-size:28px; font-weight:normal; height:40px; left:0; letter-spacing:1px; line-height:40px; position:absolute; top:0; } .article header h2 a { border:medium none; color:#ABB9C1; padding:0; text-decoration:none; } .article header h2 sup { font-size:0.7em; line-height:1em; text-decoration:underline; vertical-align:6px; } .article p, .article ul, .article ol, .article dl { font-size:18px; line-height:1.75em; margin-bottom:1em; font-family:Palatino,Georgia,"Times New Roman",Times,serif; } .article .content { width: 100% !important; } .article .editor { font-size: 80%; margin-top: 0; padding: 0 0 0 0; line-height: 100%; display: block; font-style: italic; } .article .footer p { font-size: 14px; line-height: 1.75em; } code { font-size: 13px; }

Smoothing The Curve

Sean O'Connor February 11th 2010

Практически для всех возможностей Django существуют способы модификации и расширения. Крайне редко может понадобиться переписывать существенную часть функционала Django только для того, чтобы изменить действие какого-то инструмента. Например, если вы хотите изменить внешний вид формы, вы можете отказаться от внешнего вида «по умолчанию» и создать собственное поле, или даже просто использовать собственный HTML. В обоих случаях вы выигрываете по спектру возможностей, сохраняя все остальные преимущества библиотеки форм.

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

До выхода в свет версии Django 1.2 для ORM такая кривая имела аналогичный вид, за одним исключением: существенный скачок в конце. Этот скачок появлялся в связи с тем, что при необходимости создания нестандартного SQL-запроса требовалось выйти за пределы ORM. Чтобы использовать определённый функционал ORM, пользователю пришлось бы создавать его заново самостоятельно, хоть это и не является само по себе катастрофой. В версии Django 1.2 добавлен метод Model.objects.raw (), который решает эту проблему и, таким образом, сглаживает эту кривую для ORM.

Старый способ

До выхода версии Django 1.2 при необходимости создать SQL запрос, нужно было написать нечто подобное:

from django.db import connection
from library.models import Author 

cursor = connection.cursor()
query = "SELECT * FROM library_author"
cursor.execute(query)
results = cursor.fetchall() 

authors = []
for result in results:
    author = Author(*result)
    authors.append(author)

Не то чтобы это было совсем ужасно, но здесь мы теряем доступ к функционалу ORM во всём, что не касается создания SQL запросов. В частности, недоступна автоматическая трансформация результатов запроса в экземпляр модели. В меру трудоёмкие способы восстановить утраченную функциональность, конечно, существуют, но фактически это будет изобретением велосипеда.

Новый способ

В версии Django 1.2 для создания прямого SQL запроса нужно написать следующее:

from library.models import Author 

query = "SELECT * FROM library_author"
authors = Author.objects.raw(query)

authors здесь будет экземпляром RawQuerySet. RawQuerySet во многом похож на QuerySet. В частности, сходство в том, что это — итерируемый объект, который возвращает экземпляр модели из результатов запроса с каждой итерацией. Отличие его от QuerySet состоит в том, что его нельзя встроить в цепочку. Но здесь это и не важно, поскольку запросы больше не формируются автоматически.

Как и при использовании БД курсора мы можем передать набор параметров запроса, Django заботливо их экранирует.

query = "SELECT * FROM library_author WHERE first_name = %s"
params = ('bob',)
authors = Author.objects.raw(query, params)

Так это же здорово! Код SQL защищён от атак, у нас экземпляр модели, который мы хотели, и никакого изобретения велосипеда.

«Но и это ещё не всё!»

Как и большинство инструментов Django, метод raw () оставляет пространство для использования дополнительных функций в неудобных ситуациях или для особо сложных запросов:

Независимый порядок полей

Для метода Model.objects.raw () неважно, в каком порядке возвращаются поля по запросу. Единственное, что важно — соответствуют ли имена полей запроса полям в модели.

# All of these queries will work the same
Author.objects.raw("SELECT * FROM library_author")
Author.objects.raw("SELECT id, first_name, last_name FROM library_author")
Author.objects.raw("SELECT last_name, id, first_name FROM library_author")

Аннотации

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

>>> authors = Author.objects.raw("SELECT *, age(birth_date) as age FROM library_authors")
>>> for author in authors:
...     print "%s is %s." % (author.first_name, author.age)
John is 37.
Jane is 42.
...

Определения соотношения между полями модели и запроса

Если по какой-либо причине не удаётся точно сопоставить имена поля запросов и имена поля модели, метод Model.objects.raw () возможность указать его вручную.

Чтобы сопоставить поля запроса с полями модели, нужно просто использовать словарь, содержащий требуемые соответствия, в качестве одного из параметров метода raw (). Соответствия необходимо определить только для тех полей, которые не удалось сопоставить с полями модели.

field_map = {'first': 'first_name', 'last': 'last_name'}
    query = 'SELECT id, first_name AS first, last_name as last FROM library_author'
    authors = Author.objects.raw(query, translations=field_map)

Отложенные поля

Те поля, которые предполагаются в модели, но не возвращаются запросом, отмечаются как отложенные. Они будут заполнены только при запросе к полю экземпляра модели. Это полезно в тех случая, когда данные запрашиваются не из «реальной» таблицы для модели, или когда сами таблицы достаточно большие. Здесь надо иметь в виду, что первичный ключ не может быть отложен и должен быть возвращён всеми запросами. Если запрос не возвращает первичный ключ, будет вызвано исключение InvalidQuery.

Ограничения

На действия метода raw () накладываются некоторые ограничения. Самое существенное из них заключается в том, что метод raw () позволяет работу только с SELECT. При попытке использовать любой другой тип запроса, будет вызвано исключение InvalidQuery. Первоначально это было сделано с целью защиты, но отчасти это сделано так и потому что нет смысла возвращать экземпляр модели для чего-либо ещё кроме запроса типа SELECT. Изменение данных с помощью прямого SQL — это последнее, что стоит делать с помощью Django. Чтобы не провоцировать эти действия, мы ни в коем случае не хотим делать их удобнее для пользователя. Если вам требуется использовать именно прямые запросы SQL кроме запроса типа SELECT, у вас всегда остаётся возможность создать курсор БД и работать оттуда.

Вот и всё

Ну вот и всё. В версии Django 1.2 существенно упрощена работа с SQL запросами там, где это необходимо. Кривая, о которой мы говорили выше, имеет гораздо более гладкий вид. Официальную документацию для этой функции можно найти в разделе, посвящённому SQL.

Шон О’Коннор — разработчик HUGE и один из партнёров организаторов сайта для группы пользователей Django NYC. В течение трёх предыдущих лет Шон работал над приложениями Django и последнее время внёс существенный вклад в базовые усовершенствования раздела прямых SQL запросов в Django 1.2. В свободное от разработки Django и HUGE время он пьёт пиво и играет в настольные игры. Найти в интернете его можно по адресу seanoc.com (http://seanoc.com/), его твиттер — @theSeanOC.

Изучаем Django

Messages for the rest of us

.article header { font-family:LeagueGothicRegular,Impact,sans-serif; font-weight:normal; height:100px; margin-bottom:20px; position:relative; text-transform:uppercase; display: block; } .article header h1 { color:#586C78; font-size:42px; font-weight:normal; height:60px; left:0; letter-spacing:1px; line-height:60px; position:absolute; top:10px; } .article header h2 { color:#CCCCCC; font-size:28px; font-weight:normal; height:40px; left:0; letter-spacing:1px; line-height:40px; position:absolute; top:0; } .article header h2 a { border:medium none; color:#ABB9C1; padding:0; text-decoration:none; } .article header h2 sup { font-size:0.7em; line-height:1em; text-decoration:underline; vertical-align:6px; } .article p, .article ul, .article ol, .article dl { font-size:18px; line-height:1.75em; margin-bottom:1em; font-family:Palatino,Georgia,"Times New Roman",Times,serif; } .article .content { width: 100% !important; } .article .editor { font-size: 80%; margin-top: 0; padding: 0 0 0 0; line-height: 100%; display: block; font-style: italic; } .article .footer p { font-size: 14px; line-height: 1.75em; } code { font-size: 13px; }

Messages for the rest of us

Jeff Croft February 10th 2010

Эта статья описывает изменения механизма сообщений в Django. В Django 1.2 можно посылать сообщения не только зарегистрированным пользователям, но и анонимным. Полностью переработан API.

Статья уже переведена мои другом Дмитрием Медвинским:

http://habrahabr.ru/blogs/django/87473/

Дмитрий мой бывший коллега и просто замечательный человек, follow @justadeveloper!

Изучаем Django

Multiple database support

.article header { font-family:LeagueGothicRegular,Impact,sans-serif; font-weight:normal; height:100px; margin-bottom:20px; position:relative; text-transform:uppercase; display: block; } .article header h1 { color:#586C78; font-size:42px; font-weight:normal; height:60px; left:0; letter-spacing:1px; line-height:60px; position:absolute; top:10px; } .article header h2 { color:#CCCCCC; font-size:28px; font-weight:normal; height:40px; left:0; letter-spacing:1px; line-height:40px; position:absolute; top:0; } .article header h2 a { border:medium none; color:#ABB9C1; padding:0; text-decoration:none; } .article header h2 sup { font-size:0.7em; line-height:1em; text-decoration:underline; vertical-align:6px; } .article p, .article ul, .article ol, .article dl { font-size:18px; line-height:1.75em; margin-bottom:1em; font-family:Palatino,Georgia,"Times New Roman",Times,serif; } .article .content { width: 100% !important; } .article .editor { font-size: 80%; margin-top: 0; padding: 0 0 0 0; line-height: 100%; display: block; font-style: italic; } .article .footer p { font-size: 14px; line-height: 1.75em; } code { font-size: 13px; }

Multiple database support

Alex Gaynor February 9th 2010

Изначально Django предполагал работу только с одной базой данных (системное ограничение включающее такие вещи как группа настроек DATABASE_*). В течение всего этого времени явно ощущалась необходимость поддержки возможности работы с несколькими БД. В рамках работы над версией 1.2 в течение Google Summer of Code поддержка нескольких БД была включена в trunk. С этими новшествами связаны как целый ряд внутренних изменений, так и несколько удачных расширений для существующих интерфейсов работы с БД.

Интерфейс работы с несколькими БД

Наиболее заметное изменение в Django состоит в том, что, вместо того, чтобы писать настройки базы данных таким образом:

DATABASE_ENGINE = "postgresql_psycopg2"
DATABASE_NAME = "my_big_project"
DATABASE_USER = "mario"
DATABASE_PASSWORD = "princess_peach"

Вы пишете следующее:

DATABASES = {
    "default": {
        "ENGINE": "django.db.backends.postgresql_psycopg2",
        "NAME": "my_big_project",
        "USER": "mario",
        "PASSWORD": "princess_peach",
    },

    "credentials": {
        "ENGINE": "django.db.backends.oracle",
        "NAME": "users",
    }
}

В конечном итоге все проекты должны будут быть переведены в такой вид, хотя старый формат будет поддерживаться в Django вплоть до версии 1.4. Единственный ключ в словаре DATABASES, имеющий критическое значение, это «default» — «по умолчанию». Если вы используете базу данных, вам необходимо определить базу данных «default».

Теперь, когда вы сообщили Django о всех своих базах данных, надо найти способ сообщить Django о том, как их использовать. Первым изменением интерфейса в этой области является метод using(). using() принимает единственный параметр имя БД (имена БД служат ключами словаря DATABASES), и привязывает QuerySet к этой базе данных. Как и любое другое средство класса QuerySet, он может быть при необходимости поставлен в цепочку (как, например, метод order_by(), обновляющий результаты первого запроса при повторном запросе). По сути, это даёт вам возможность полностью контролировать, откуда будут читаться данные (а при ловком использовании методов create(), delete() и update() даёт даже возможность контролировать запись):

>>>User.objects.filter(username__startswith="admin").using("credentials")

Новые методы работы с данными класса QuerySet delete() и save() принимают дополнительный аргумент using, в который передаётся, опять же, имя БД.

Кроме того, появляется новый метод класса Managers, db_manager(), который тоже принимает имя БД. Его функция по сути близка функции метода using(). Основное различие заключается в следующем: вместо того, чтобы возвращать QuerySet, он возвращает новый Manager. Сценарий его использования делает возможным связать его в цепочку с теми методами класса Managers, которые не возвращают QuerySet (например, такими как create_user() класса UserManager).

Маршрутизаторы БД

Используя все эти методы, вы получаете возможность реализовать любую систему, использующую несколько баз данных. В том числе master-slave replication, partitioning и sharding. Однако, это не обязательно будет удобно. Вам придётся часто использовать в коде запросы к методу using(), что не лучшим образом совместимо с принципом реиспользуемых приложений Django (именно по этой причине опция using была удалена из класса модели Meta). Кроме того, в некоторых случаях класс QuerySet не полностью определён. Так, например, для получения доступа к данным класса User метод my_obj.user неявно создаст QuerySet, но методу using() будет некуда отправить запрос. Этим и было обусловлено появление концепции «маршрутизатора БД». Маршрутизаторы БД получают всю информацию о запросе, который вы хотите выполнить, и определяют, какую базу необходимо обратиться. Маршрутизаторы задаются в файле настроек в виде списка DATABASE_ROUTERS:

DATABASE_ROUTERS = [
     "path.to.AuthRouter",
     "path.to.MasterSlaveRouter",
 ]

DATABASE_ROUTERS задаётся списком, поскольку маршрутизатор на любой стадии может вернуть значение None и тогда Django перейдет к следующему маршрутизатору из списка. Маршрутизаторы могу определять следующие методы:

  • db_for_read
  • db_for_write
  • allow_relation
  • allow_syncdb

Первые два метода очевидны, они возвращают имя БД, по отношению к которой выполняется запрос. Метод allow_relation призван контролировать разумность запросов. Django не позволит вам создать заведомо некорректные связи между БД. То есть, если вы попытаетесь создать взаимосвязь между двумя структурами данных из разных БД (для ForeignKey или для ManyToManyField), с помощью данного метода Django запросит необходимое подтверждение. И последний метод allow_syncdb позволяет определить, в какой из баз данных будет создана конкретная модель.

В документации Django по работе с несколькими БД, как всегда, приведена масса практических примеров. В том числе приведены примеры, описывающие, как начать применять распространённые паттерны с маршрутизаторами баз данных. Поддержка нескольких баз данных дает огромные преимущества и значительно расширяет области применения Django.

Алекс Гейнор — студент второго года обучения политехнического института Renesselear по специальности вычислительная техника, работает в качестве веб-разработчика в Eldarion. Работает с Django около двух лет, и примерно столько же активно участвует в его дальнейшей разработке. Кроме работы с Django, он вносит свой вклад в развитие таких проектов, как Pinax, django-debug-toolbar, а также запустил несколько собственных — как, например, django-filter, и django-taggit. Поклонник качественных программных интерфейсов, гибкого масштабирования и компиляторов.


Оригинал статьи | Все статьи

Не могу не упомянуть в теме о работе с базами данных в Django, замечательную утилиту миграции структуры БД South, которая уже поддерживает новый интерфейс.

Если вам понравился перевод подписывайтесь на RSS, я планирую перевести всю серию статей.

Хотите сообщить об ошибке в статье? Обсудить или задать вопрос по работе с несколькими БД? Добро пожаловать в комментарии.

Блог django на хабрахабре

Django Framework / [Перевод] Multiple database support

Изначально Django предполагал работу только с одной базой данных (системное ограничение включающее такие вещи как группа настроек DATABASE_*). В течение всего этого времени явно ощущалась необходимость поддержки возможности работы с несколькими БД. В рамках работы над версией 1.2 в течение Google Summer of Code поддержка нескольких БД была включена в trunk. С этими новшествами связаны как целый ряд внутренних изменений, так и несколько удачных расширений для существующих интерфейсов работы с БД.

Изучаем Django

Welcome to Django Advert

.article header { font-family:LeagueGothicRegular,Impact,sans-serif; font-weight:normal; height:100px; margin-bottom:20px; position:relative; text-transform:uppercase; display: block; } .article header h1 { color:#586C78; font-size:42px; font-weight:normal; height:60px; left:0; letter-spacing:1px; line-height:60px; position:absolute; top:10px; } .article header h2 { color:#CCCCCC; font-size:28px; font-weight:normal; height:40px; left:0; letter-spacing:1px; line-height:40px; position:absolute; top:0; } .article header h2 a { border:medium none; color:#ABB9C1; padding:0; text-decoration:none; } .article header h2 sup { font-size:0.7em; line-height:1em; text-decoration:underline; vertical-align:6px; } .article p, .article ul, .article ol, .article dl { font-size:18px; line-height:1.75em; margin-bottom:1em; font-family:Palatino,Georgia,"Times New Roman",Times,serif; } .article .content { width: 100% !important; } .article .editor { font-size: 80%; margin-top: 0; padding: 0 0 0 0; line-height: 100%; display: block; font-style: italic; }

Welcome to Django-Advent

Jacob Kaplan-Moss February 8th 2010

Релиз Django 1.2 невероятно меня воодушевил. Оглядываясь назад, я могу сказать, что было несколько моментов, которые оказались ключевыми как для самого проекта Django, так и для общества в целом. Слияние ветки «magic-removal» и последующий релиз 0.96 был первым таким моментом: мы выпустили улучшенный Django и наше сообщество начало развиваться огромными скачками. Релиз Django 1.0 стал следующим ключевым моментом. Метка 1.0 гордо символизировала наш профессионализм и зрелость проекта.

И я абсолютно уверен, что версия 1.2 станет очередной ключевой точкой проекта.

Новые особенности — поддержка множественных соединений с базами данных, валидация моделей, усовершенствованная защита от CSRF, улучшение административного интерфейса — являются одними из самых ожидаемых в истории Django. Эти особенности позволят нашим пользователям покорять новые горизонты с Django, и я с нетерпением жду, когда смогу увидеть, какие новые задачи вы сможете решить.

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

Поддержка множественных соединений с базами данных это «киллер фича» Django 1.2. Добавление функции такого рода — интересная задача: существуют разногласие между нуждами начинающих и  разработчиков ненагруженных приложений — которые более всего ценят простоту и удобство в использовании — и возрастающего числа разработчиков высоконагруженных приложений, которым необходимо больше  контроля и  гибкости, то есть большей сложности фремворка.

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

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

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

Многие из новичков попали к нам через Google’s Summer of Code 2009. В том году мы приняли 6 проектов:

  • поддержка множественных соединений с базами данных (Alex Gaynor)
  • улучшения HTTP и WSGI (Chris Cahoon)
  • улучшенние локализации (Marc Garcia)
  • валидация моделей (Honza Král)
  • дополнения к тестовому фреймворку (Kevin Kubasic)
  • улучшения администрировного интерфейса (Zain Memon).

Программа имела потрясающий успех: все проекты произвели хороший, работающий код. Часть его вошла в версию 1.2 часть продолжит свой путь в выпуске 1.3. Многие из этих проектов были воодушевлены долгим ожиданием новых функций, а работа, сделанная в течение Summer of Code оказалась как раз тем, что было нам нужно для их реализации.

Мы также добавили пару новых разработчиков — Дженнис Лейдел и Джеймса Таубера — и я готов спорить, что мы увидим еще ребят, которые будут задействованы в проекте до финального релиза.

Кстати, когда же он? (Django 1.2 вышел 17 мая 2010) прим. переводчика

Запланированная дата релиза — 9 марта 2010 года. И мы стоим на пути к тому, что выпуск осуществится вовремя… но мы никогда не сделали бы этого без Вашей помощи!

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

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

Онлайн документация Django включает описание того, как вы можете помочь проекту.

Мы также проводим спринт для разработчиков по Django 1.2 на PyCon US 2010. В течении четырех дней спринта (22—25 февраля) мы будем рады, если вы присоединитесь к нам лично или виртуально по IRC (#django-dev на irc.freenode.net) или на http://groups.google.com/group/django-developers

Я надеюсь, что вам понравятся остальные статьи и что в конце концов вы будете столь же впечатлены выходом Django 1.2, как и я!


Статья на Английском

В честь выхода Django 1.2 решил перевести статьи с замечательного сайта Django Advent

Сейчас на сайте опубликовано 20 статей, и каждая из них рассказывает нам о новой возможности Django. Поверьте, там есть на что посмотреть.

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

Метки

.net .NET C# .sort 1.2 2009 2010 404 error admin ajax amazon analytics and apache api archlinux asp.net async asynchronous autocomplete bash blender blog blogengine blogs book bootstrap bot bpython buildout byteflow bzr C c plus plus C++ cache cbv Chaco checkio chrome ci ckeditor class based views clojure closure cms cms с удобной админкой code coding style collectd COM comet competition conference ConfigParser contest Context continuous integration CouchDB coverage CppCMS cpyext cpython crud csrf CSS ctypes curl custom model fields cx_freeze cython database db dbm dbqueries debian debug debugging decorator decorators deploy deployment descriptor design dev devconf developers development diveintopython Django django 1.2 django 1.3 django advent django framework django template django trunk django weblog django-admin-tools django-cms django-compressor django-hosts django-piston django-registration django-sphinx django.admin djangoadvent djangocms djangodash doc documentation drupal e-legion eclipse EGit emacs encoding Enthought epoll erlang event exception ExtJS fabric facebook fastcgi finaloption fixtures fonts forms formset fp framework freebsd freeswitch fs2web ftp fun funcparserlib functional gae gamin gandi generic views gettext gevent gil git github gitosis Google Google App Engine google picasa Google Translate google wave Google Web Toolkit grab grablab greenlet gtd gui haskell hg hgshelve highlighter host hosting how-to howto html html5lib Hudson humor i18n icfpc ide idiomatic image-scripting improvements Internet interpreter ipython ironpython izmenimsya.ru jabber java javascript jenkins jetbrains JIT job jquery json jstree jython kde kiev kiyv kyivpy l10n ldap library libs Life Links linux Linux & Unix LLVM logging logs lxml Mac OS X magic mail markdown Matplotlib Mayavi maybe mediavirus meetup memcache Memcached memory messages metaclass middleware migration mikrotik mkd model models mod_python mod_wsgi mongodb monitoring mptt musicmans.ru musicx mvc my-projects mysql netCDF networkx newforms newforms-admin news nginx Nhibernate nix nose NoSQL numpy oop open source OpenID openoffice opster optimization oracle orm os pagination parsing path patterns pdf PDF-принтер PEP PEP8 performance performance optimization perl personality photo php picture-driven computing PIL pinax pingback pip plasma plone plugin plugins postgresql programming progress bar psycopg2 py2exe pybb pybbm pycamp pycharm pycon pycow pycurl pydev pygtk pylons PyNGL pypy pyqt PyQt4 pyrad pyramid PySide Python Python 2.5 python 2.7 python 3 python c api python speed python-mssql python3 pywinauto Qt Qt4 queue rabbitmq radius raw sql re redis redsolution redsolution cms regexp regular expressions release repoze.bfg RequestContext reusable apps robokassa rss ru ruby ruby-on-rails sample satchmo scalability SciPy scraping screencast search selenium self.error seo server setattr settings setuptools shell sikuli sms snippet socket.io software sorting south sphinx spider sql sqlalchemy sqlite ssh startup step-by-step subdomain subversion svn SyntaxHighlighter system tags tdd tddspry teh drama template templates templatetags test testing thinkpad threading threads tips tips and tricks tools tornadio tornado tornado server tricks tutorial tweepy twisted twitter typography uapycon Ubuntu ucsvlog uml Uncategorized unicode unit test unit testing UnitTest Unladen Swallow upload urllib urls utf-8 uwsgi validation vcs versioning video vim virtualenv Visual Studio vkontakte voip wave web web-devel web-services web-разработка webdev webfaction webkit webpy websockets webtest widget widgets Win API windows Wirbel work wrapper wsgi wxPython wxWidgets wysiwyg xapian xml xmonad xmpp xpath yandex youtube zip zomg zope [cdata[cbv]] [cdata[ci]] [cdata[class based views]] [cdata[continuous integration]] [cdata[django framework]] [cdata[django-sphinx]] [cdata[django]] [cdata[nginx]] [cdata[python]] [cdata[virtualenv]] [cdata[программирование]] автоматизация администрирование администрирование django админка алгоритмы архитектура атрибуты базы данных Без рубрики безопасность библиотеки блоге бот веб-разработка видео Визуализация данных вконтакте Все записи гвидо ван россум граббер графика графы декоратор декораторы дескриптор дескрипторы документация заметки игра жизнь идея интересное киев Клиентам книги конференция личное математика метаклассы модели модули монады морфология мысли невозможное новости о облачные вычисления обо мне Обработка данных оптимизация оптимизация кода Основная лента основы парсинг парсинг сайтов перевод песочница Питон поебень поиск правила кодирования программирование Проектирование производительность работа рабочее размышлизмы Разное разработка разработка приложений разработки регулярные выражения сайт событие события ссылки статьи тестирование тесты Тюмень убунтариум фигня философия формы форум Хабрахабр хакинг хостинг шаблоны шаблоны проектирования эксперимент Эксперименты юмор я пиарюсь Яндекс