Бот Jabber - как получить доступность контактов? - PullRequest
4 голосов
/ 08 октября 2010

Мне нужно настроить jabber-бот, использующий python, который будет отправлять сообщения в зависимости от доступности нескольких контактов в режиме онлайн / офлайн.

Я изучал pyxmpp и xmpppy, но не смог найти никакого способа (по крайней мере, ничего простого) проверить состояние данного контакта.

Есть ли какие-нибудь указатели о том, как этого добиться?

В идеале я хотел бы что-то вроде, например. bot.status_of("contact1@gmail.com") возвращение "online"

Ответы [ 3 ]

2 голосов
/ 08 октября 2010

Я не думаю, что это возможно так, как вы этого хотите, потому что присутствие контактов (которые содержат информацию об их доступности) принимается ботом асинхронно.

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

Используя xmpppy, вы делаете это примерно так:

def connect(jid, password, res, server, proxy, use_srv):
    conn = xmpp.Client(jid.getDomain())

    if not conn.connect(server=server, proxy=proxy, use_srv=use_srv):
        log( 'unable to connect to server.')
        return None

    if not conn.auth(jid.getNode(), password, res):
        log( 'unable to authorize with server.')
        return None

    conn.RegisterHandler( 'presence', callback_presence)
    return conn

conn = connect(...)

def callback_presence(sess, pres):
    if pres.getStatus() == "online":
        msg = xmpp.Message(pres.getFrom(), "Hi!")
        conn.send(msg)

PS: Я не проверял код, но он долженчто-то очень похожее на это.

0 голосов
/ 22 декабря 2010

Что вам нужно сделать, это:

  1. Connect.
  2. Объявить обработчик присутствия. Этот обработчик поддерживает кэш-память о присутствии каждого контакта (подробности см. Ниже)
  3. Отправка начального присутствия на сервер, который будет вызывать получение статусов присутствия от всех ваших онлайн-контактов, что, в свою очередь, вызовет обработчик.
  4. Метод status_of () считывает кеш и немедленно определяет состояние присутствия контакта.

Теперь все зависит от того, какая информация о присутствии вам нужна. Для простоты давайте представим, что вам просто нужно значение "онлайн" / "оффлайн". Кеш будет представлять собой словарь, ключами которого являются чистые (без ресурсов) JID, а значения - это набор связанных ресурсов для этого JID. Например:

{'foo@bar.com': set(['work', 'notebook']), 'bob@example.net': set(['gtalk'])}

Теперь, когда вы получаете «доступное» присутствие от определенного JID / ресурса:

if jid not in cache:
    cache[jid] = set()
cache[jid].add(resource)

Взаимно, когда вы получаете "недоступное" присутствие:

if jid in cache: # bad people send "unavailable" just to make your app crash
    cache[jid].discard(resource)
    if 0 == len(cache[jid]):
        del cache[jid]

А теперь:

def is_online(jid):
    return jid in cache

Конечно, если вам нужна более подробная информация, вы можете сохранить не только список доступных ресурсов для контакта, но также статус, сообщение о состоянии, приоритет и т. Д. Каждого ресурса.

0 голосов
/ 09 октября 2010

То, что вы хотите сделать через <presence type="probe"/>. Это делается от имени клиента и НЕ ДОЛЖНО ими выполняться (в соответствии с RFC для XMPP IM). Поскольку это бот, вы можете реализовать датчик присутствия и получить текущее присутствие данного объекта. Не забудьте отправить зонд на пустой JID (sans-ресурс), потому что сервер отвечает от имени клиентов за зонды присутствия. Это означает, что ваш рабочий процесс будет выглядеть так:

<presence/> // I'm online!                                        BOT
  <presence from="juliet@capulet.org/balcony"/>                   RESPONSE
  <presence from="romeo@montague.net/hallway"/> // and so on...   RESPONSE
<presence type="probe" to="benvolio@montague.net"/>               BOT
  <presence from="benvoio@montague.net/hallway">                  RESPONSE
     <status>Huzzah!</status>
     <priority>3</priority>
  </presence>

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

...