Весы Gevent Socketio

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

Я попробовал https://github.com/abourget/gevent-socketio/tree/master/examples/django_chat/chat

Я использую Gunicorn и рабочий класс socketio.sgunicorn.GeventSocketIOWorker, поэтому сначала я подумал об увеличении количества рабочих. К сожалению, это время от времени выходит из строя. Я начал переписывать его, чтобы использовать Redis из нескольких источников, которые я нашел, и у меня есть 1 рабочий на каждом сервере, который теперь балансирует нагрузку. Однако, похоже, это та же проблема. Мне интересно, есть ли какая-то проблема в самом коде gevent socketio, которая не позволяет ему масштабироваться.

Вот как я начал, это просто код сообщения отправки.

def redis_client():
    """Get a redis client."""
    return Redis(settings.REDIS_HOST, settings.REDIS_PORT, settings.REDIS_DB)

class PubSub(object):
    """
    Very simple Pub/Sub pattern wrapper
    using simplified Redis Pub/Sub functionality.

    Usage (publisher)::

        import redis

        r = redis.Redis()

        q = PubSub(r, "channel")
        q.publish("test data")


    Usage (listener)::

        import redis

        r = redis.Redis()
        q = PubSub(r, "channel")

        def handler(data):
            print "Data received: %r" % data

        q.subscribe(handler)

    """
    def __init__(self, redis, channel="default"):
        self.redis = redis
        self.channel = channel

    def publish(self, data):
        self.redis.publish(self.channel, simplejson.dumps(data))

    def subscribe(self, handler):
        redis = self.redis.pubsub()
        redis.subscribe(self.channel)

        for data_raw in redis.listen():
            if data_raw['type'] != "message":
                continue

            data = simplejson.loads(data_raw["data"])
            handler(data)


from socketio.namespace import BaseNamespace
from socketio.sdjango import namespace
from supremo.utils import redis_client, PubSub
from gevent import Greenlet

@namespace('/chat')
class ChatNamespace(BaseNamespace):
    nicknames = []
    r = redis_client()
    q = PubSub(r, "channel")

    def initialize(self):
        # Setup redis listener
        def handler(data):
            self.emit('receive_message',data)

        greenlet = Greenlet.spawn(self.q.subscribe, handler)

    def on_submit_message(self,msg):
        self.q.publish(msg)

person Crazyconoli    schedule 27.03.2013    source источник


Ответы (1)


Я использовал части кода из https://github.com/fcurella/django-push-demo и gevent-socketio 0.3.5rc1 вместо rc2, и теперь он работает с несколькими рабочими процессами и балансировкой нагрузки.

person Crazyconoli    schedule 28.03.2013