Заполнение сайта на Drupal 7 с помощью python

Автор: Igor Kirsanov

При заполении сайта на базе Drupal 7 столкнулся с небольшой проблемой в виде скрытых полей для защиты от межсайтовых запросов (CSRF атаки).

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

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

Материал для заполнения лежит в папке content относительно скрипта, внутри этой папки вложенных папок нет, одни файлы, так что обработку опускаем. Ошибки тоже не обрабатываем.

Материал представляет собой файл в котором первая строка является заголовком, все последующие - содержимое статьи. Кодировка файлов windows 1251, заполнение ведется с компьютера на ubuntu (linux) с консолью в формате utf-8.

Структура файлов следующая

.
├── content
│   ├── article_11.htm
│   ├── article_12.htm
│   ├── article_7.htm
│   └── article_9.htm
└── drupal-post.py

Исходный код с комментариями:


# -*- coding: UTF-8 -*-
# библиотеки для обработки контента
from os import listdir
from os.path import join as joinpath
# библиотеки для эмулирования браузера
from twill.commands import go
from twill.commands import fv
from twill.commands import submit
from twill.commands import showforms


# авторизуемся в drupal, авторизация не прерывается, поэтому в функцию выносить не нужно
go("http://www.seo-xxx.ru/") # переходим на сайт, пишем СВОЙ
fv("1", "name", "ЛОГИН") # в первой форме (1) вводим имя
fv("1", "pass", "ПАРОЛЬ")  # пароль, поля стандартные, названия можно посмотреть в исходном коде страницы
submit('5') # c помощью showforms() смотрим форму, 5 это номер кнопки отправить 


# функция отправки информации заполняем сайт информацией
def zapolnit(zagolovok, body):
    go("http://www.seo-xxx.ru/node/add/anekdoty") # переходим на страницу, у Вас будет СВОЙ путь добавления материала.
    fv("1", "title", zagolovok) # заполняем поле заголовок (title)
    fv("1", "body[und][0][value]", body) # содержимое, имя body[und][0][value] странное  на первый взгляд, но так генерирует drupal
    submit('18') # отправляем данные
    #showforms()  # если что-то не идет, комментируем отправку и смотрим что заполняется, содержимое и названия полей формы


# подготавливаем контент для заполнения
mypath = "content" # путь к папке
counter = 0 # счетчик для удобства
for i in listdir(mypath):  # получаем список файлов и идем в цикле по каждому
    counter = counter + 1  # увеличиваем счетчик на один
    f = open(joinpath(mypath,i)).read() # открываем файлик, т.к. содержимое в папке, то складываем чтобы получить путь
    stroki = f.split('\n') # разбиваем построчно, до этого файл прочитали целиком
    zagolovok = stroki[0].decode('cp1251').encode('utf-8') # получаем первую строку, потом цепочка перекодировок
    text = '' # чтобы удобнее делать сложение других строк
    body = text.join(stroki[1:]).decode('cp1251').encode('utf-8') # складываем все остальные обратно в цельный текст, за исключением первой строки, она 0.
    print counter # не нужно, но всегда интересно где программа сейчас, выводим счетчик
    zapolnit(zagolovok, body) # сам постинг с помощью функции выше

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