1. Marcin Lulek
  2. gevent_cometd

Source

gevent_cometd / gevent_cometd / channel.py

import gevent_cometd
import datetime
import logging
from gevent_cometd import config, users_lock, channels_lock, stats

log = logging.getLogger(__name__)



class Channel(object):
    """ Represents one of our chat channels - has some config options """

    def __init__(self, name, long_name=None):
        self.name = name
        self.long_name = long_name
        self.last_active = datetime.datetime.utcnow()
        self.connections = {}
        self.presence = False
        self.salvagable = False
        self.store_history = False
        self.history_size = 10
        self.history = []

        # connections is global store of relationships between user and
        # connection correlated with channels in form of:
        # {user_id:list_of_connection_ids}

    def add_message(self, message, pm_users=None, exclude_user=None):
        if not pm_users:
            pm_users = []
        stats['total_unique_messages'] += 1
        self.last_active = datetime.datetime.utcnow()
        if self.store_history:
            self.history.append(message)
            self.history = self.history[(self.history_size) * -1:]
        message.update({'channel': self.name})
        # message everyone subscribed except excluded
        for u, conns in self.connections.iteritems():
            if u != exclude_user:
                for conn_id in conns:
                    connection = gevent_cometd.user.Connection.by_id(conn_id)
                    if connection and (not pm_users or connection.user in pm_users):
                        connection.add_message(message)

    def add_connection(self, user, connection):
        """ adds a connection to channel, avoids duplicates """
        try:
            if connection.id not in self.connections[user.user]:
                self.connections[user.user].append(connection.id)
            if not self.name in user.channels:
                user.channels.append(self.name)
            return True
        except KeyError, e:
            self.connections[user.user] = [connection.id]
            if not self.name in user.channels:
                user.channels.append(self.name)
            return True
        return False

    @classmethod
    def get_channel(cls, channel_name):
        """ "get or create new channel if it doesnt exist yet """
        channel_inst = gevent_cometd.channels.get(channel_name)
        if not channel_inst:
            with channels_lock:
                channel_inst = Channel(channel_name)
                gevent_cometd.channels[channel_name] = channel_inst
        return channel_inst

    def __repr__(self):
        return '<Channel: %s, connections:%s>' % (self.name, len(self.connections))