LINUX.ORG.RU

сервис для twitter. Выбор технологий.


0

2

Я решил вылезать из пеленок и попробовать написать нечто большее хеллоуворолда. Я пишу на python. Так вот есть у меня идея одного сервиса для работы с твиттером(взял tweepy). Мне придется частенько дергать апи твиттера, нужно будет выполнять задания по расписанию (отправить пачку твитов, обновить информацию по твиту, принять и обработать пачку твитов) и все это нужно делать по разным таймерам и для множества в данный момент активных задач. Ну и про запись в собственную бд забывать нельзя. Так же будет веб-морда которая собственно и позволяет ставить задачи на выполнение и смотреть за ходом событий (это будет джанга ибо это мой первый веб-проект вообще и я вот-вот уже дочитываю книжку по ней и ничего другого не знаю). И я так понимаю, что веб морда и сервер дергающий твиттер, это разные независимые приложения. Так вот, запрос к твиттеру занимает очень приличное время что как бы намекает мне на то что для реализации серверной части мне придется использовать какие-то многопоточные штуковины. Я в деле написания веб-серверов, многопоточности и прочем мягко говоря полный новичек В связи с чем хотел бы поинтересоваться технологиями которые мне можно будет применять в этом деле (пока я мельком глянул на gevent кажется то что надо), а так же литературу по этому всему счастью (например может есть какие статьи или даже книги по разработке серверных приложений ведь они отличаются от десктопных?!).

Резюмирую ничего не знаю, ничего не умею, но очень хочу научиться. Подскажите что смотреть куда копать.

Всем кто дочитал до конца уже спасибо, буду рад любому совету, кроме как бросить это дело/найти работу/девушку/сменить профессию.

>Так вот, запрос к твиттеру занимает очень приличное время что как бы намекает мне на то что для реализации серверной части мне придется использовать какие-то многопоточные штуковины.

Можно взять асинхронный tornado и запускать запрос в отдельном процессе через multiprocessing. Но это не везде подойдёт.

Можно джангой складывать задачи в БД, по крону скриптом проверять и выполнять, после чего результат обратно в БД. Это простой путь.

Ну и самое весёлое - написать сервер, который будет слушать то, что ему говорит джанга, и выполнять. Общаться они будут, например, через сокеты. А в сервере уже устраивать многопоточность и прочее.

anonymous
()

UPD:

(пока я мельком глянул на gevent кажется то что надо)

Если ты начинающий, и пишешь приложение, у которого не будет тысячи пользователей, то не стоит сильно заморачиваться с gevent-ами, всякими гринлетами и прочим. Лучше возьми всё стандартное питоновское, что попроще. Например twisted, либо вообще наследуйся от SocketServer.

anonymous
()
Ответ на: комментарий от anonymous

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

И, да я хочу именно позаморачиваться, чтобы выучить что-то новое, полезное... Планировал я именно вариант сервер отдельно - джанга отдельно. Сервер будет работать с твиттером и с БД, а джанга будет общаться с БД и с юзером.

Работать будет все так: пользователь через веб морду ставит на выполнение некое задание, которое завершится скажем через час, во время работы пользователь может смотреть на промежуточные результаты. Поэтому тут 2 варианта, либо обновлять статистику по запросу пользователя (тогда нужно организовывать взаимодействия морды и сервера) либо сервер самостоятельно будет обновлять статистику через какие-то промежутки времени, тогда взаимодействие не нужно. Либо какой-то промежуточный вариант с кешированием и со взаимодействием...

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

Zubchick
() автор топика
Ответ на: комментарий от Zubchick

Ну раз ты хочешь позаморачиваться, то пиши всё «с нуля». Вот например:

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

По сути это одно и то же. Ведь что морда напрямую говорит серверу что надо работать, что морда «через БД» говорит это серверу - мелочи:)

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

Например, основной поток раз в n секунд проверяет БД на наличие обновлений (которые кладёт туда джанга). Как только она видит новое задание, ты запускаешь второй процесс (через multiprocessing, например), или поток (через threading, там GIL влезть может, но у тебя не та сложность). Заодно ты создаёшь какой-нить Queue или Pipe для общения с первым потоком.

Второй поток/процесс работает как обычный скрипт - делает всё что надо с твиттером и в каком-то виде отдаёт ответ через пайп первому потоку (основному). Основной висит в цикле и, кроме проверки на новые задания, слушает ответ от второго, и, если надо, кладёт его в БД.

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

anonymous
()

Java+Jetty+JettyContinuations


ой, питон же. Ну тогда просто comet+continuations. Посоветовать особо ничего не могу, ибо не пробовал. Nagare должен уметь.

stevejobs ★★★★☆
()

Если у тебя джанга то сделай два джанга приложения:

1. Собственно фронтенд.

2. REST api для постановки задачи в очередь, выборки задания, статуса и т.д. В чем хранить не важно, база, файл, что душе милее.

И демон выполняющий непосредственную работу. Пункт один и демон общаются через пункт 2.

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

baverman ★★★
()
Ответ на: комментарий от baverman

что значит не надо заморачиваться с потоками? Демон будет работать в один поток и обрабатывать каждый запрос секунд по пять - десять?) А в очереди их будет сотня...

Zubchick
() автор топика
Ответ на: комментарий от anonymous

> Например, основной поток раз в n секунд проверяет БД на наличие обновлений (которые кладёт туда джанга). Как только она видит новое задание, ты запускаешь второй процесс (через multiprocessing, например), или поток (через threading, там GIL влезть может, но у тебя не та сложность). Заодно ты создаёшь какой-нить Queue или Pipe для общения с первым потоком.

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

Так же демон мониторит время окончания заданий и когда это время наступает актуализирует информацию в БД крайний раз для этого задания.

Zubchick
() автор топика
Ответ на: комментарий от Zubchick

А в очереди их будет сотня...

Запустить сразу несколько демонов, пусть параллельно разгребают, какие проблемы?

baverman ★★★
()
Ответ на: комментарий от Zubchick

какие-то блокировки чтобы они не принялись за одно задание.

чтобы они не принялись за одно задание.

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

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

baverman ★★★
()
Ответ на: комментарий от Zubchick

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

Что значит ждала? Ты ж не заставишь висеть пользователя без ответа от сервера, пока демон что-то там крутит?

Морда может проверять результаты работы демона при каждом запросе на неё, можно выделить это в сторонний демон, но всё равно - заставить висеть джангу долго - не очень хорошая идея. Тут, как я говорил, стоит посмотреть на tornado, хотя там не всё гладко.

anonymous
()
Ответ на: комментарий от anonymous

не то что бы долго - запрос в твиттер, запись в базу, отсылка сообщения джанге.

ЗЫ Торнадо разве не вебсервер?

Zubchick
() автор топика
Ответ на: комментарий от baverman

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

То что проект для собственного развития в моем случае значит то что я хочу научиться чему-то, а не то что я хочу собирать велосипеды и упрощать все до нельзя. Готовым компонентам - да-да-да. Я о них в первом посте в том числе и спрашивал :)

Zubchick
() автор топика
Ответ на: комментарий от Zubchick

>ЗЫ Торнадо разве не вебсервер?

Торнадо по-дефолту весь такой асинхронный.

anonymous
()

Главное определиться с тем как ты хочешь чтобы оно работало.
Самый очевидный вариант: очередь+вебморда к ней.
Да, крон+джанга. Вообще, это идёт к тому, чтобы сделать веб-морду к крону. Т.е. по нужному запросу добавляешь запись в крон. В записи - скрипт, который отчитывается о состоянии в твою бд.
Вообще, для длительных операций в вебе, самый лучший вариант это всегда очередь+крон, но торнадо даёт интересный функционал, который позволит всё сделать сразу.
На самом деле, это всё можно сделать на торнадо, ибо торнадо это ещё и веб-фреймворк. Но изучать и думать над тем, как использовать джанго-фишки в торнадо, я думаю, тебе не захочется(и правильно, джанго это ужас внутри). Поэтому придётся держать wsgi и tornado.
В общем, вот такие 2 варианта решения задачи. Один позволяет организовать и таймеры, другой - сделать всё на пайтоне, но подумать о реализации таймеров.

tia
()
Ответ на: комментарий от tia

Да мне честно говоря все-равно, могу и торнадо попробовать :)

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

Zubchick
() автор топика
Ответ на: комментарий от Zubchick

Вот в том и идея, ты будешь просить пользователя тыкать каждые 2 минуты F5? Да даже если через JS, то всё-равно ужас.

tia
()
Ответ на: комментарий от tia

да нет же, если никто не залезет на страничку с заданием за все время жизни этого задания, то оно просто завершится в назначенное ему время (как оно это сделает я написал выше). А если пользователь зайдет на эту страницу то ин-фа обновится и морда нарисует обновленную инфу. Как-то так.

Zubchick
() автор топика
Ответ на: комментарий от Zubchick

Я подумал что у тебя будет задача вроде:
Добавить задание с датой её начала.
Запуск задания по дате.

Чтобы запустить в торнадо процесс, который будет делать работу асинхронно, нужно использовать функцию, обёрнутую в нужный декоратор. Вызывать же эту функцию нужно из запроса(а откуда ещё?). Т.е. main loop один же, и он на веб-сервер, который обрабатывает запросы, а не задания.

tia
()
Ответ на: комментарий от tia

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

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

Zubchick
() автор топика

Если у тебя серверная часть будет по крону работать, то ты можешь просто делать асинхронные запросы к серверу на основе чего-то такого http://internet.newspoint.info/yazyk-programmirovaniya-python-asinkhronnyi-ht... А вообще если у тебя не так много задач, то можно и в один поток делать.
Для очередей самое удобное на мой взгляд - это memcacheq.

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

Tark ★★
()
Ответ на: комментарий от Tark

Я примерно так и решил делать, только с помощью celery+RabbitMQ

Zubchick
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.