def announce_contact(self, name=CONTACT_NAME):
        basic_txt = { "txtvers": "1", "status": "avail" }

        self.contact_name = '%s@%s' % (name, get_host_name())
        self.listener, port = setup_stream_listener(self.q, self.contact_name,
                protocol=IncomingXmppiChatStream)

        AvahiAnnouncer(self.contact_name, "_presence._tcp", port, basic_txt)
コード例 #2
0
    def announce_contact(self, name=CONTACT_NAME):
        basic_txt = { "txtvers": "1", "status": "avail" }

        self.contact_name = '%s@%s' % (name, get_host_name())
        self.listener, port = setup_stream_listener(self.q, self.contact_name,
                protocol=IncomingXmppiChatStream)

        AvahiAnnouncer(self.contact_name, "_presence._tcp", port, basic_txt)
コード例 #3
0
    def my_request_ft_channel(self):
        self.contact_name = '%s@%s' % (self.CONTACT_NAME, get_host_name())
        self.handle = self.conn.Contacts.GetContactByID(self.contact_name,
                                                        [])[0]

        try:
            self.request_ft_channel()
        except dbus.DBusException, e:
            if e.get_dbus_name() != cs.NOT_AVAILABLE:
                raise
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = { "txtvers": "1", "status": "avail" }

    contact_name = "test-text-channel@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name =  conn.Properties.Get(cs.CONN, "SelfID")

    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
        protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()


    e = q.expect('service-resolved', service = service)

    xmpp_connection = connect_to_stream(q, contact_name,
        self_handle_name, str(e.pt), e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason

    e = q.expect('stream-opened', connection = xmpp_connection)

    # connected to salut, now send a messages as composing part 
    # here be sillyness
    parts = OUTGOING_MESSAGE.split(" ")

    for x in xrange(1,len(parts)):
        message = domish.Element(('', 'message'))
        message.addElement('body', content=' '.join(parts[:x]))
        event = message.addElement('x', 'jabber:x:event')
        event.addElement('composing')
        event.addElement('id')
        xmpp_connection.send(message)

    message = domish.Element(('', 'message'))
    message.addElement('body', content=OUTGOING_MESSAGE)
    event = message.addElement('x', 'jabber:x:event')
    event.addElement('composing')
    xmpp_connection.send(message)

    e = q.expect('dbus-signal', signal='Received')
    assert e.args[2] == handle
    assert e.args[5] == OUTGOING_MESSAGE
コード例 #5
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = {"txtvers": "1", "status": "avail"}

    contact_name = "test-text-channel@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name = conn.Properties.Get(cs.CONN, "SelfID")

    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added',
                 name=self_handle_name,
                 protocol=avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service=service)

    xmpp_connection = connect_to_stream(q, contact_name, self_handle_name,
                                        str(e.pt), e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason

    e = q.expect('stream-opened', connection=xmpp_connection)

    # connected to salut, now send a messages as composing part
    # here be sillyness
    parts = OUTGOING_MESSAGE.split(" ")

    for x in xrange(1, len(parts)):
        message = domish.Element(('', 'message'))
        message.addElement('body', content=' '.join(parts[:x]))
        event = message.addElement('x', 'jabber:x:event')
        event.addElement('composing')
        event.addElement('id')
        xmpp_connection.send(message)

    message = domish.Element(('', 'message'))
    message.addElement('body', content=OUTGOING_MESSAGE)
    event = message.addElement('x', 'jabber:x:event')
    event.addElement('composing')
    xmpp_connection.send(message)

    e = q.expect('dbus-signal', signal='Received')
    assert e.args[2] == handle
    assert e.args[5] == OUTGOING_MESSAGE
コード例 #6
0
    def announce_contact(self, name=CONTACT_NAME, metadata=True):
        client = 'http://telepathy.freedesktop.org/fake-client'
        features = [ns.IQ_OOB]

        if metadata:
            features += [ns.TP_FT_METADATA]

        ver = compute_caps_hash([], features, {})
        txt_record = {
            "txtvers": "1",
            "status": "avail",
            "node": client,
            "ver": ver,
            "hash": "sha-1"
        }

        suffix = '@%s' % get_host_name()
        name += ('-' + os.path.splitext(os.path.basename(sys.argv[0]))[0])

        self.contact_name = name + suffix
        if len(self.contact_name) > 63:
            allowed = 63 - len(suffix)
            self.contact_name = name[:allowed] + suffix

        self.listener, port = setup_stream_listener(self.q, self.contact_name)

        self.contact_service = AvahiAnnouncer(self.contact_name,
                                              "_presence._tcp", port,
                                              txt_record)

        self.handle = wait_for_contact_in_publish(self.q, self.bus, self.conn,
                                                  self.contact_name)

        # expect salut to disco our caps
        e = self.q.expect('incoming-connection', listener=self.listener)
        stream = e.connection

        e = self.q.expect('stream-iq',
                          to=self.contact_name,
                          query_ns=ns.DISCO_INFO,
                          connection=stream)
        assertEquals(client + '#' + ver, e.query['node'])
        send_disco_reply(stream, e.stanza, [], features)

        # lose the connection here to ensure connections are created
        # where necessary; I just wanted salut to know my caps.
        stream.send('</stream:stream>')
        # spend a bit of time in the main loop to ensure the last two
        # stanzas are actually received by salut before closing the
        # connection.
        sync_dbus(self.bus, self.q, self.conn)
        stream.transport.loseConnection()
def setup_tests(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = { "txtvers": "1", "status": "avail" }

    contact_name = "test-yst-message@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    return handle, contact_name, listener
コード例 #8
0
def setup_tests(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = {"txtvers": "1", "status": "avail"}

    contact_name = "test-yst-message@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    return handle, contact_name, listener
    def announce_contact(self, name=CONTACT_NAME, metadata=True):
        client = 'http://telepathy.freedesktop.org/fake-client'
        features = [ns.IQ_OOB]

        if metadata:
            features += [ns.TP_FT_METADATA]

        ver = compute_caps_hash([], features, {})
        txt_record = { "txtvers": "1", "status": "avail",
                       "node": client, "ver": ver, "hash": "sha-1"}

        suffix = '@%s' % get_host_name()
        name += ('-' + os.path.splitext(os.path.basename(sys.argv[0]))[0])

        self.contact_name = name + suffix
        if len(self.contact_name) > 63:
            allowed = 63 - len(suffix)
            self.contact_name = name[:allowed] + suffix

        self.listener, port = setup_stream_listener(self.q, self.contact_name)

        self.contact_service = AvahiAnnouncer(self.contact_name, "_presence._tcp",
                port, txt_record)

        self.handle = wait_for_contact_in_publish(self.q, self.bus, self.conn,
                self.contact_name)

        # expect salut to disco our caps
        e = self.q.expect('incoming-connection', listener=self.listener)
        stream = e.connection

        e = self.q.expect('stream-iq', to=self.contact_name, query_ns=ns.DISCO_INFO,
                     connection=stream)
        assertEquals(client + '#' + ver, e.query['node'])
        send_disco_reply(stream, e.stanza, [], features)

        # lose the connection here to ensure connections are created
        # where necessary; I just wanted salut to know my caps.
        stream.send('</stream:stream>')
        # spend a bit of time in the main loop to ensure the last two
        # stanzas are actually received by salut before closing the
        # connection.
        sync_dbus(self.bus, self.q, self.conn)
        stream.transport.loseConnection()
def test(q, bus, conn):
    AvahiListener(q).listen_for_service("_presence._tcp")

    conn.Connect()

    e = q.expect('service-added',
      name=PUBLISHED_NAME + "@" + avahitest.get_host_name())

    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service = service)

    for (key, val) in { "1st": FIRST_NAME,
                        "last": LAST_NAME,
                        "status": "avail",
                        "txtvers": "1" }.iteritems():
        v =  txt_get_key(e.txt, key)
        assert v == val, (key, val, v)
コード例 #11
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = {"txtvers": "1", "status": "avail"}

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name = conn.Properties.Get(cs.CONN, "SelfID")

    contact_name = "test-ichat-incoming-msg@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # Create a connection to send msg stanza
    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added',
                 name=self_handle_name,
                 protocol=avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service=service)

    outbound = connect_to_stream(q, contact_name, self_handle_name, str(e.pt),
                                 e.port, OutgoingXmppiChatStream)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason
    e = q.expect('stream-opened', connection=outbound)

    msg = domish.Element((None, 'message'))
    msg['to'] = self_handle_name
    msg['type'] = 'chat'
    boddy = msg.addElement('body', content='hi')
    outbound.send(msg)

    e = q.expect('dbus-signal', signal='Received')
    assert e.args[2] == handle
    assert e.args[3] == cs.MT_NORMAL
    assert e.args[5] == "hi"
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = { "txtvers": "1", "status": "avail" }

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name =  conn.Properties.Get(cs.CONN, "SelfID")

    contact_name = "test-ichat-incoming-msg@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # Create a connection to send msg stanza
    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
        protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service = service)

    outbound = connect_to_stream(q, contact_name,
        self_handle_name, str(e.pt), e.port, OutgoingXmppiChatStream)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason
    e = q.expect('stream-opened', connection = outbound)

    msg = domish.Element((None, 'message'))
    msg['to'] = self_handle_name
    msg['type'] = 'chat'
    boddy = msg.addElement('body', content='hi')
    outbound.send(msg)

    e = q.expect('dbus-signal', signal='Received')
    assert e.args[2] == handle
    assert e.args[3] == cs.MT_NORMAL
    assert e.args[5] == "hi"
コード例 #13
0
def test(q, bus, conn):
    AvahiListener(q).listen_for_service("_presence._tcp")

    conn.Connect()

    e = q.expect('service-added',
                 name=PUBLISHED_NAME + "@" + avahitest.get_host_name())

    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service=service)

    for (key, val) in {
            "1st": FIRST_NAME,
            "last": LAST_NAME,
            "status": "avail",
            "txtvers": "1"
    }.iteritems():
        v = txt_get_key(e.txt, key)
        assert v == val, (key, val, v)
コード例 #14
0
def test_ft_caps_from_contact(q, bus, conn, client):

    conn_caps_iface = dbus.Interface(conn, cs.CONN_IFACE_CONTACT_CAPS)
    conn_contacts_iface = dbus.Interface(conn, cs.CONN_IFACE_CONTACTS)

    # send presence with FT capa
    ver = compute_caps_hash([], [ns.IQ_OOB], {})
    txt_record = {
        "txtvers": "1",
        "status": "avail",
        "node": client,
        "ver": ver,
        "hash": "sha-1"
    }
    contact_name = "test-caps-ft@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
                               txt_record)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener=listener)
    incoming = e.connection

    # Salut looks up our capabilities
    event = q.expect('stream-iq',
                     connection=incoming,
                     query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        client + '#' + ver, (query_node.attributes['node'], client, ver)

    contact_handle = conn_contacts_iface.GetContactByID(contact_name, [])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = client + '#' + ver

    feature = query.addElement('feature')
    feature['var'] = ns.IQ_OOB
    incoming.send(result)

    # FT capa is announced
    e = q.expect('dbus-signal',
                 signal='ContactCapabilitiesChanged',
                 predicate=lambda e: contact_handle in e.args[0])
    caps = e.args[0][contact_handle]
    assertContains(ft_caps, caps)

    # check the Contacts interface give the same caps
    caps_via_contacts_iface = conn_contacts_iface.GetContactAttributes(
            [contact_handle], [cs.CONN_IFACE_CONTACT_CAPS], False) \
            [contact_handle][cs.CONN_IFACE_CONTACT_CAPS + '/capabilities']
    assert caps_via_contacts_iface == caps, caps_via_contacts_iface

    # check if Salut announces the OOB capa
    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name = conn.Properties.Get(cs.CONN, "SelfID")

    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added',
                 name=self_handle_name,
                 protocol=avahi.PROTO_INET)
    service = e.service
    service.resolve()

    receive_presence_and_ask_caps(q, incoming, service, contact_name)

    # capa announced without FT
    ver = compute_caps_hash([], ["http://telepathy.freedesktop.org/xmpp/pony"],
                            {})
    txt_record = {
        "txtvers": "1",
        "status": "avail",
        "node": client,
        "ver": ver,
        "hash": "sha-1"
    }
    contact_name = "test-caps-ft2@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
                               txt_record)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener=listener)
    incoming = e.connection

    # Salut looks up our capabilities
    event = q.expect('stream-iq',
                     connection=incoming,
                     query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        client + '#' + ver, (query_node.attributes['node'], client, ver)

    contact_handle = conn_contacts_iface.GetContactByID(contact_name, [])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = client + '#' + ver

    feature = query.addElement('feature')
    feature['var'] = "http://telepathy.freedesktop.org/xmpp/pony"
    incoming.send(result)

    # the FT capability is not announced
    e = q.expect('dbus-signal', signal='ContactCapabilitiesChanged')
    caps = e.args[0][contact_handle]
    assertDoesNotContain(ft_caps, caps)

    # check the Contacts interface give the same caps
    caps_via_contacts_iface = conn_contacts_iface.GetContactAttributes(
            [contact_handle], [cs.CONN_IFACE_CONTACT_CAPS], False) \
            [contact_handle][cs.CONN_IFACE_CONTACT_CAPS + '/capabilities']
    assert caps_via_contacts_iface == caps, caps_via_contacts_iface

    # no capabilites announced (assume FT is supported to insure interop)
    txt_record = {"txtvers": "1", "status": "avail"}
    contact_name = "test-caps-ft-no-capa2@" + get_host_name()
    contact_handle = conn_contacts_iface.GetContactByID(contact_name, [])[0]
    listener, port = setup_stream_listener(q, contact_name)
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
                               txt_record)

    # FT capa is announced
    e = q.expect('dbus-signal',
                 signal='ContactCapabilitiesChanged',
                 predicate=lambda e: contact_handle in e.args[0].keys())

    caps = e.args[0][contact_handle]
    assertContains(ft_caps, caps)

    # check the Contacts interface give the same caps
    caps_via_contacts_iface = conn_contacts_iface.GetContactAttributes(
            [contact_handle], [cs.CONN_IFACE_CONTACT_CAPS], False) \
            [contact_handle][cs.CONN_IFACE_CONTACT_CAPS + '/capabilities']
    assert caps_via_contacts_iface == caps, caps_via_contacts_iface
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = { "txtvers": "1", "status": "avail" }

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name =  conn.Properties.Get(cs.CONN, "SelfID")

    contact_name = "test-text-channel@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # create a clique room
    basic_txt = { "txtvers": "0"}
    AvahiAnnouncer("myroom", "_clique._udp", 41377, basic_txt)

    # connect a stream
    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
        protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service = service)

    xmpp_connection = connect_to_stream(q, contact_name,
        self_handle_name, str(e.pt), e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason

    e = q.expect('stream-opened', connection = xmpp_connection)

    # send an invitation
    message = domish.Element(('', 'message'))
    message['type'] = 'normal'
    message.addElement('body', content='You got a Clique chatroom invitation')
    invite = message.addElement((NS_CLIQUE, 'invite'))
    invite.addElement('roomname', content='myroom')
    invite.addElement('reason', content='Inviting to this room')
    invite.addElement('address', content='127.0.0.1')
    invite.addElement('port', content='41377')
    xmpp_connection.send(message)

    # group channel is created
    e = q.expect('dbus-signal', signal='NewChannel',
            predicate=lambda e:
                e.args[1] == cs.CHANNEL_TYPE_TEXT and
                e.args[2] == cs.HT_ROOM)
    path = e.args[0]
    channel = make_channel_proxy(conn, path, 'Channel')
    props_iface = dbus.Interface(bus.get_object(conn.object.bus_name, path),
        dbus.PROPERTIES_IFACE)

    q.expect('dbus-signal', signal='MembersChanged', path=path)

    lp_members = props_iface.Get('org.freedesktop.Telepathy.Channel.Interface.Group',
        'LocalPendingMembers')

    assert len(lp_members) == 1
    added, actor, reason, msg = lp_members[0]

    assert added == self_handle
    assert actor == handle
    assert reason == 4                       #invited
    assert msg == 'Inviting to this room'

    # decline invitation
    channel.Close()
    q.expect('dbus-signal', signal='Closed')
def test(q, bus, conn):
    self_name = 'testsuite' + '@' + avahitest.get_host_name()

    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with the roomlist ones announces.
    wait_for_contact_list(q, conn)

    # check if we can request roomlist channels
    properties = conn.GetAll(
            tp_name_prefix + '.Connection.Interface.Requests',
            dbus_interface='org.freedesktop.DBus.Properties')
    assert ({tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_ROOM_LIST,
             tp_name_prefix + '.Channel.TargetHandleType': 0,
             },
             [],
             ) in properties.get('RequestableChannelClasses'),\
                     properties['RequestableChannelClasses']

    requestotron = dbus.Interface(conn,
            tp_name_prefix + '.Connection.Interface.Requests')

    # create roomlist channel using new API
    call_async(q, requestotron, 'CreateChannel',
            { tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_ROOM_LIST,
              tp_name_prefix + '.Channel.TargetHandleType': 0,
              })

    ret, new_sig = q.expect_many(
        EventPattern('dbus-return', method='CreateChannel'),
        EventPattern('dbus-signal', signal='NewChannels'),
        )
    path2 = ret.value[0]
    chan2 = wrap_channel(bus.get_object(conn.bus_name, path2), "RoomList")

    props = ret.value[1]
    assert props[tp_name_prefix + '.Channel.ChannelType'] ==\
            cs.CHANNEL_TYPE_ROOM_LIST
    assert props[tp_name_prefix + '.Channel.TargetHandleType'] == 0
    assert props[tp_name_prefix + '.Channel.TargetHandle'] == 0
    assert props[tp_name_prefix + '.Channel.TargetID'] == ''
    assert props[tp_name_prefix + '.Channel.Requested'] == True
    assert props[tp_name_prefix + '.Channel.InitiatorHandle'] \
            == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert props[tp_name_prefix + '.Channel.InitiatorID'] \
            == self_name
    assert props[tp_name_prefix + '.Channel.Type.RoomList.Server'] == ''

    assert new_sig.args[0][0][0] == path2
    assert new_sig.args[0][0][1] == props

    assert chan2.Properties.Get(cs.CHANNEL_TYPE_ROOM_LIST, 'Server') == ''

    # ensure roomlist channel
    yours, ensured_path, ensured_props = requestotron.EnsureChannel(
            { tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_ROOM_LIST,
              tp_name_prefix + '.Channel.TargetHandleType': 0,
              })

    assert not yours
    assert ensured_path == path2, (ensured_path, path2)

    # Closing roomlist channels crashed Salut for a while.
    chan2.Close()
    q.expect_many(
            EventPattern('dbus-signal', signal='Closed',
                path=path2),
            EventPattern('dbus-signal', signal='ChannelClosed', args=[path2]),
            )

    conn.Disconnect()

    q.expect_many(
            EventPattern('dbus-signal', signal='StatusChanged', args=[2, 1]),
            )
コード例 #17
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal',
             signal='StatusChanged',
             args=[cs.CONN_STATUS_CONNECTED, cs.CSR_NONE_SPECIFIED])

    assertContains(cs.CONN_IFACE_CONTACT_INFO,
                   conn.Properties.Get(cs.CONN, "Interfaces"))
    ci_props = conn.Properties.GetAll(cs.CONN_IFACE_CONTACT_INFO)
    assertEquals(cs.CONTACT_INFO_FLAG_PUSH, ci_props['ContactInfoFlags'])
    assertEquals([
        ('n', [], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
        ('fn', [], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
        ('email', ['type=internet'
                   ], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
        ('x-jabber', [], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
    ], ci_props['SupportedFields'])

    # Just to verify that RCI does approximately nothing and doesn't crash.
    conn.ContactInfo.RefreshContactInfo([21, 42, 88])

    basic_txt = {"txtvers": "1", "status": "avail"}

    contact_name = "aliastest@" + get_host_name()
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", 1234, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)
    alias = wait_for_aliases_changed(q, handle)
    assertEquals(contact_name, alias)

    for (alias, dict, expect_contact_info_changed) in [
            # Contact publishes just one of 1st and last
        ("last", {
            "last": "last"
        }, True),
        ("1st", {
            "1st": "1st"
        }, True),
            # Contact publishes a meaningful value for one of 1st and last, and an
            # empty value for the other one and for "nick". Empty values should be
            # treated as if missing.
        ("last", {
            "last": "last",
            "1st": "",
            "nick": ""
        }, True),
        ("1st", {
            "1st": "1st",
            "last": "",
            "nick": ""
        }, True),
            # When a contact publishes both 1st and last, we have to join them
            # together in a stupid anglo-centric way, like iChat does.
        ("1st last", {
            "1st": "1st",
            "last": "last"
        }, True),
            # Nickname should be preferred as the alias to 1st or last. Since we
            # don't report nicknames in ContactInfo, and nothing else has changed
            # from the last update, no ContactInfo changes should be announced.
        ("nickname", {
            "1st": "1st",
            "last": "last",
            "nick": "nickname"
        }, False),
            # If the contact stops publishing any of this stuff, we should fall back
            # to their JID as their alias.
        (contact_name, {}, True)
    ]:
        txt = basic_txt.copy()
        txt.update(dict)

        announcer.set(txt)

        a = wait_for_aliases_changed(q, handle)
        assert a == alias, (a, alias, txt)

        if expect_contact_info_changed:
            info = wait_for_contact_info_changed(q, handle)
            check_contact_info(info, dict)

        attrs = conn.Contacts.GetContactAttributes([handle],
                                                   [cs.CONN_IFACE_ALIASING],
                                                   True)[handle]
        assertEquals(alias, attrs[cs.CONN_IFACE_ALIASING + "/alias"])

        check_all_contact_info_methods(conn, handle, dict)

    for keys in [  # Check a few neat transitions, with no empty fields
        {
            "email": "*****@*****.**"
        },
        {
            "jid": "*****@*****.**",
            "email": "*****@*****.**"
        },
        {
            "jid": "*****@*****.**"
        },
            # Check that empty fields are treated as if omitted
        {
            "email": "*****@*****.**",
            "jid": ""
        },
        {
            "jid": "*****@*****.**",
            "email": ""
        },
    ]:
        txt = basic_txt.copy()
        txt.update(keys)

        announcer.set(txt)
        info = wait_for_contact_info_changed(q, handle)
        check_contact_info(info, keys)

        check_all_contact_info_methods(conn, handle, keys)

    # Try an invalid handle. Request should return InvalidHandle.
    # (Technically so should RefreshContactInfo but I am lazy.)
    call_async(q, conn.ContactInfo, 'RequestContactInfo', 42)
    q.expect('dbus-error', method='RequestContactInfo', name=cs.INVALID_HANDLE)

    # Try a valid handle for whom we have no data from the network.
    # Request should fail.
    h = conn.Contacts.GetContactByID('rthrtha@octopus', [])[0]
    call_async(q, conn.ContactInfo, 'RequestContactInfo', h)
    q.expect('dbus-error', method='RequestContactInfo', name=cs.NOT_AVAILABLE)
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged',
        args=[cs.CONN_STATUS_CONNECTED, cs.CSR_NONE_SPECIFIED])

    assertContains(cs.CONN_IFACE_CONTACT_INFO,
        conn.Properties.Get(cs.CONN, "Interfaces"))
    ci_props = conn.Properties.GetAll(cs.CONN_IFACE_CONTACT_INFO)
    assertEquals(cs.CONTACT_INFO_FLAG_PUSH, ci_props['ContactInfoFlags'])
    assertEquals(
        [ ('n', [], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
          ('fn', [], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
          ('email', ['type=internet'],
           cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),
          ('x-jabber', [], cs.CONTACT_INFO_FIELD_FLAG_PARAMETERS_EXACT, 1),

        ],
        ci_props['SupportedFields'])

    # Just to verify that RCI does approximately nothing and doesn't crash.
    conn.ContactInfo.RefreshContactInfo([21,42,88])

    basic_txt = { "txtvers": "1", "status": "avail" }

    contact_name = "aliastest@" + get_host_name()
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", 1234, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)
    alias = wait_for_aliases_changed(q, handle)
    assertEquals(contact_name, alias)

    for (alias, dict, expect_contact_info_changed) in [
      # Contact publishes just one of 1st and last
      ("last", { "last": "last" }, True),
      ("1st", { "1st": "1st"}, True),
      # Contact publishes a meaningful value for one of 1st and last, and an
      # empty value for the other one and for "nick". Empty values should be
      # treated as if missing.
      ("last", { "last": "last", "1st": "", "nick": "" }, True),
      ("1st", { "1st": "1st", "last": "", "nick": "" }, True),
      # When a contact publishes both 1st and last, we have to join them
      # together in a stupid anglo-centric way, like iChat does.
      ("1st last", { "1st": "1st", "last": "last" }, True),
      # Nickname should be preferred as the alias to 1st or last. Since we
      # don't report nicknames in ContactInfo, and nothing else has changed
      # from the last update, no ContactInfo changes should be announced.
      ("nickname", { "1st": "1st", "last": "last", "nick": "nickname" }, False),
      # If the contact stops publishing any of this stuff, we should fall back
      # to their JID as their alias.
      (contact_name, {}, True) ]:
        txt = basic_txt.copy()
        txt.update(dict)

        announcer.set(txt)

        a = wait_for_aliases_changed (q, handle)
        assert a == alias, (a, alias, txt)

        if expect_contact_info_changed:
            info = wait_for_contact_info_changed(q, handle)
            check_contact_info(info, dict)

        attrs = conn.Contacts.GetContactAttributes([handle],
            [cs.CONN_IFACE_ALIASING], True)[handle]
        assertEquals(alias, attrs[cs.CONN_IFACE_ALIASING + "/alias"])

        check_all_contact_info_methods(conn, handle, dict)

    for keys in [ # Check a few neat transitions, with no empty fields
                  { "email": "*****@*****.**" },
                  { "jid": "*****@*****.**", "email": "*****@*****.**" },
                  { "jid": "*****@*****.**" },
                  # Check that empty fields are treated as if omitted
                  { "email": "*****@*****.**", "jid": "" },
                  { "jid": "*****@*****.**", "email": "" },
                ]:
        txt = basic_txt.copy()
        txt.update(keys)

        announcer.set(txt)
        info = wait_for_contact_info_changed(q, handle)
        check_contact_info(info, keys)

        check_all_contact_info_methods(conn, handle, keys)

    # Try an invalid handle. Request should return InvalidHandle.
    # (Technically so should RefreshContactInfo but I am lazy.)
    call_async(q, conn.ContactInfo, 'RequestContactInfo', 42)
    q.expect('dbus-error', method='RequestContactInfo', name=cs.INVALID_HANDLE)

    # Try a valid handle for whom we have no data from the network.
    # Request should fail.
    h = conn.Contacts.GetContactByID('rthrtha@octopus', [])[0]
    call_async(q, conn.ContactInfo, 'RequestContactInfo', h)
    q.expect('dbus-error', method='RequestContactInfo', name=cs.NOT_AVAILABLE)
def test(q, bus, conn):
    forbidden = [EventPattern('dbus-signal', signal='ServiceAdded'),
                 EventPattern('dbus-signal', signal='ServiceRemoved')]
    q.forbid_events(forbidden)

    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0, 0])

    # announce a contact with the right caps
    ver = compute_caps_hash([], [], banshee)
    txt_record = { "txtvers": "1", "status": "avail",
        "node": CLIENT_NAME, "ver": ver, "hash": "sha-1"}
    contact_name = "test-service@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, txt_record)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener=listener)
    incoming = e.connection

    # Salut looks up its capabilities
    event = q.expect('stream-iq', connection=incoming,
        query_ns=ns.DISCO_INFO)
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assertEquals(CLIENT_NAME + '#' + ver, query_node.attributes['node'])

    contact_handle = conn.RequestHandles(cs.HT_CONTACT, [contact_name])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = CLIENT_NAME + '#' + ver
    x = query.addElement((ns.X_DATA, 'x'))
    x['type'] = 'result'

    # FORM_TYPE
    field = x.addElement((None, 'field'))
    field['var'] = 'FORM_TYPE'
    field['type'] = 'hidden'
    field.addElement((None, 'value'), content='urn:ytstenut:capabilities#org.gnome.Banshee')

    # type
    field = x.addElement((None, 'field'))
    field['var'] = 'type'
    field.addElement((None, 'value'), content='application')

    # name
    field = x.addElement((None, 'field'))
    field['var'] = 'name'
    field.addElement((None, 'value'), content='en_GB/Banshee Media Player')
    field.addElement((None, 'value'), content='fr/Banshee Lecteur de Musique')

    # capabilities
    field = x.addElement((None, 'field'))
    field['var'] = 'capabilities'
    field.addElement((None, 'value'), content='urn:ytstenut:capabilities:yts-caps-audio')
    field.addElement((None, 'value'), content='urn:ytstenut:data:jingle:rtp')

    incoming.send(result)

    # this will be fired as text channel caps will be fired
    q.expect('dbus-signal', signal='ContactCapabilitiesChanged',
             predicate=lambda e: contact_handle in e.args[0])

    # add evince
    tmp = banshee.copy()
    tmp.update(evince)
    ver = compute_caps_hash([], [], tmp)
    txt_record['ver'] = ver
    announcer.update(txt_record)

    # Salut looks up our capabilities
    event = q.expect('stream-iq', connection=incoming,
        query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        CLIENT_NAME + '#' + txt_record['ver']

    # send good reply
    result['id'] = event.stanza['id']
    query['node'] = CLIENT_NAME + '#' + ver

    x = query.addElement((ns.X_DATA, 'x'))
    x['type'] = 'result'

    # FORM_TYPE
    field = x.addElement((None, 'field'))
    field['var'] = 'FORM_TYPE'
    field['type'] = 'hidden'
    field.addElement((None, 'value'), content='urn:ytstenut:capabilities#org.gnome.Evince')

    # type
    field = x.addElement((None, 'field'))
    field['var'] = 'type'
    field.addElement((None, 'value'), content='application')

    # name
    field = x.addElement((None, 'field'))
    field['var'] = 'name'
    field.addElement((None, 'value'), content='en_GB/Evince Picture Viewer')
    field.addElement((None, 'value'), content='fr/Evince uh, ow do you say')

    # capabilities
    field = x.addElement((None, 'field'))
    field['var'] = 'capabilities'
    field.addElement((None, 'value'), content='urn:ytstenut:capabilities:pics')

    incoming.send(result)

    # this will be fired as text channel caps will be fired
    q.expect('dbus-signal', signal='ContactCapabilitiesChanged',
             predicate=lambda e: contact_handle in e.args[0])

    # now finally ensure the sidecar
    path, props = conn.Future.EnsureSidecar(ycs.STATUS_IFACE)
    assertEquals({}, props)

    status = ProxyWrapper(bus.get_object(conn.bus_name, path),
                          ycs.STATUS_IFACE, {})

    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({contact_name: {
                'org.gnome.Banshee':
                    ('application',
                     {'en_GB': 'Banshee Media Player',
                      'fr': 'Banshee Lecteur de Musique'},
                     ['urn:ytstenut:capabilities:yts-caps-audio',
                      'urn:ytstenut:data:jingle:rtp']),
                  'org.gnome.Evince':
                      ('application',
                       {'en_GB': 'Evince Picture Viewer',
                        'fr': 'Evince uh, ow do you say'},
                       ['urn:ytstenut:capabilities:pics'])}
                }, discovered)
def connect_two_accounts(q, bus, conn):
    # first connection: connect
    contact1_name = "testsuite" + "@" + get_host_name()
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[cs.CONN_STATUS_CONNECTED, cs.CSR_NONE_SPECIFIED])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with other channels announces.
    wait_for_contact_list(q, conn)

    # second connection: connect
    conn2_params = {
        'published-name': 'testsuite2',
        'first-name': 'test2',
        'last-name': 'suite2',
        }
    contact2_name = "testsuite2" + "@" + get_host_name()
    conn2 = make_connection(bus, lambda x: None, conn2_params)
    conn2.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[cs.CONN_STATUS_CONNECTED, cs.CSR_NONE_SPECIFIED])

    wait_for_contact_list(q, conn2)

    # first connection: get the contact list
    publish_handle = conn.RequestHandles(cs.HT_LIST, ["publish"])[0]
    conn1_publish = conn.RequestChannel(cs.CHANNEL_TYPE_CONTACT_LIST,
        cs.HT_LIST, publish_handle, False)
    conn1_publish_proxy = bus.get_object(conn.bus_name, conn1_publish)

    # second connection: get the contact list
    publish_handle = conn2.RequestHandles(cs.HT_LIST, ["publish"])[0]
    conn2_publish = conn2.RequestChannel(cs.CHANNEL_TYPE_CONTACT_LIST,
        cs.HT_LIST, publish_handle, False)
    conn2_publish_proxy = bus.get_object(conn2.bus_name, conn2_publish)

    # first connection: wait to see contact2
    # The signal MembersChanged may be already emitted... check the Members
    # property first
    contact2_handle_on_conn1 = 0
    conn1_members = conn1_publish_proxy.Get(cs.CHANNEL_IFACE_GROUP, 'Members',
            dbus_interface=cs.PROPERTIES_IFACE)
    for h in conn1_members:
        name = conn.InspectHandles(cs.HT_CONTACT, [h])[0]
        if name == contact2_name:
            contact2_handle_on_conn1 = h
    while contact2_handle_on_conn1 == 0:
        e = q.expect('dbus-signal', signal='MembersChanged',
            path=conn1_publish)
        for h in e.args[1]:
            name = conn.InspectHandles(cs.HT_CONTACT, [h])[0]
            if name == contact2_name:
                contact2_handle_on_conn1 = h

    # second connection: wait to see contact1
    # The signal MembersChanged may be already emitted... check the Members
    # property first
    contact1_handle_on_conn2 = 0
    conn2_members = conn2_publish_proxy.Get(
            'org.freedesktop.Telepathy.Channel.Interface.Group', 'Members',
            dbus_interface='org.freedesktop.DBus.Properties')
    for h in conn2_members:
        name = conn2.InspectHandles(cs.HT_CONTACT, [h])[0]
        if name == contact1_name:
            contact1_handle_on_conn2 = h
    while contact1_handle_on_conn2 == 0:
        e = q.expect('dbus-signal', signal='MembersChanged',
            path=conn2_publish)
        for h in e.args[1]:
            name = conn2.InspectHandles(cs.HT_CONTACT, [h])[0]
            if name == contact1_name:
                contact1_handle_on_conn2 = h

    return contact1_name, conn2, contact2_name, contact2_handle_on_conn1, contact1_handle_on_conn2
def test(q, bus, conn):
    self_name = 'testsuite' + '@' + avahitest.get_host_name()

    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with the muc ones announces.
    wait_for_contact_list(q, conn)

    # check if we can request roomlist channels
    properties = conn.GetAll(
            tp_name_prefix + '.Connection.Interface.Requests',
            dbus_interface='org.freedesktop.DBus.Properties')
    assert ({tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
             tp_name_prefix + '.Channel.TargetHandleType': cs.HT_ROOM,
             },
             [tp_name_prefix + '.Channel.TargetHandle',
              tp_name_prefix + '.Channel.TargetID'],
             ) in properties.get('RequestableChannelClasses'),\
                     properties['RequestableChannelClasses']

    requestotron = dbus.Interface(conn,
            tp_name_prefix + '.Connection.Interface.Requests')

    # create muc channel using new API
    call_async(q, requestotron, 'CreateChannel',
            { tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
              tp_name_prefix + '.Channel.TargetHandleType': cs.HT_ROOM,
              tp_name_prefix + '.Channel.TargetID': 'my-second-room',
              })

    ret, new_sig = q.expect_many(
        EventPattern('dbus-return', method='CreateChannel'),
        EventPattern('dbus-signal', signal='NewChannels'),
        )
    path2 = ret.value[0]
    chan = make_channel_proxy(conn, path2, "Channel")

    props = ret.value[1]
    assert props[tp_name_prefix + '.Channel.ChannelType'] ==\
            cs.CHANNEL_TYPE_TEXT
    assert props[tp_name_prefix + '.Channel.TargetHandleType'] == cs.HT_ROOM
    assert props[tp_name_prefix + '.Channel.TargetID'] == 'my-second-room'
    assert props[tp_name_prefix + '.Channel.Requested'] == True
    assert props[tp_name_prefix + '.Channel.InitiatorHandle'] \
            == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert props[tp_name_prefix + '.Channel.InitiatorID'] \
            == self_name

    assert new_sig.args[0][0][0] == path2
    assert new_sig.args[0][0][1] == props

    # ensure roomlist channel
    handle = props[tp_name_prefix + '.Channel.TargetHandle']
    yours, ensured_path, ensured_props = ret.value = requestotron.EnsureChannel(
            { tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
              tp_name_prefix + '.Channel.TargetHandleType': cs.HT_ROOM,
              tp_name_prefix + '.Channel.TargetHandle': handle,
              })

    assert not yours
    assert ensured_path == path2, (ensured_path, path2)

    conn.Disconnect()

    q.expect_many(
            EventPattern('dbus-signal', signal='Closed',
                path=path2),
            EventPattern('dbus-signal', signal='ChannelClosed', args=[path2]),
            EventPattern('dbus-signal', signal='StatusChanged', args=[2, 1]),
            )
コード例 #22
0
def test(q, bus, conn):
    self_name = 'testsuite' + '@' + avahitest.get_host_name()

    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with the muc ones announces.
    wait_for_contact_list(q, conn)

    # check if we can request roomlist channels
    properties = conn.GetAll(tp_name_prefix + '.Connection.Interface.Requests',
                             dbus_interface='org.freedesktop.DBus.Properties')
    assert ({tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
             tp_name_prefix + '.Channel.TargetHandleType': cs.HT_ROOM,
             },
             [tp_name_prefix + '.Channel.TargetHandle',
              tp_name_prefix + '.Channel.TargetID'],
             ) in properties.get('RequestableChannelClasses'),\
                     properties['RequestableChannelClasses']

    requestotron = dbus.Interface(
        conn, tp_name_prefix + '.Connection.Interface.Requests')

    # create muc channel using new API
    call_async(
        q, requestotron, 'CreateChannel', {
            tp_name_prefix + '.Channel.ChannelType': cs.CHANNEL_TYPE_TEXT,
            tp_name_prefix + '.Channel.TargetHandleType': cs.HT_ROOM,
            tp_name_prefix + '.Channel.TargetID': 'my-second-room',
        })

    ret, new_sig = q.expect_many(
        EventPattern('dbus-return', method='CreateChannel'),
        EventPattern('dbus-signal', signal='NewChannels'),
    )
    path2 = ret.value[0]
    chan = make_channel_proxy(conn, path2, "Channel")

    props = ret.value[1]
    assert props[tp_name_prefix + '.Channel.ChannelType'] ==\
            cs.CHANNEL_TYPE_TEXT
    assert props[tp_name_prefix + '.Channel.TargetHandleType'] == cs.HT_ROOM
    assert props[tp_name_prefix + '.Channel.TargetID'] == 'my-second-room'
    assert props[tp_name_prefix + '.Channel.Requested'] == True
    assert props[tp_name_prefix + '.Channel.InitiatorHandle'] \
            == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert props[tp_name_prefix + '.Channel.InitiatorID'] \
            == self_name

    assert new_sig.args[0][0][0] == path2
    assert new_sig.args[0][0][1] == props

    # ensure roomlist channel
    handle = props[tp_name_prefix + '.Channel.TargetHandle']
    yours, ensured_path, ensured_props = ret.value = requestotron.EnsureChannel(
        {
            tp_name_prefix + '.Channel.ChannelType': cs.CHANNEL_TYPE_TEXT,
            tp_name_prefix + '.Channel.TargetHandleType': cs.HT_ROOM,
            tp_name_prefix + '.Channel.TargetHandle': handle,
        })

    assert not yours
    assert ensured_path == path2, (ensured_path, path2)

    conn.Disconnect()

    q.expect_many(
        EventPattern('dbus-signal', signal='Closed', path=path2),
        EventPattern('dbus-signal', signal='ChannelClosed', args=[path2]),
        EventPattern('dbus-signal', signal='StatusChanged', args=[2, 1]),
    )
コード例 #23
0
def connect_two_accounts(q, bus, conn):
    # first connection: connect
    contact1_name = "testsuite" + "@" + get_host_name()
    conn.Connect()
    q.expect('dbus-signal',
             signal='StatusChanged',
             args=[cs.CONN_STATUS_CONNECTED, cs.CSR_NONE_SPECIFIED])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with other channels announces.
    wait_for_contact_list(q, conn)

    # second connection: connect
    conn2_params = {
        'published-name': 'testsuite2',
        'first-name': 'test2',
        'last-name': 'suite2',
    }
    contact2_name = "testsuite2" + "@" + get_host_name()
    conn2 = make_connection(bus, lambda x: None, conn2_params)
    conn2.Connect()
    q.expect('dbus-signal',
             signal='StatusChanged',
             args=[cs.CONN_STATUS_CONNECTED, cs.CSR_NONE_SPECIFIED])

    wait_for_contact_list(q, conn2)

    # first connection: get the contact list
    publish_handle = conn.RequestHandles(cs.HT_LIST, ["publish"])[0]
    conn1_publish = conn.RequestChannel(cs.CHANNEL_TYPE_CONTACT_LIST,
                                        cs.HT_LIST, publish_handle, False)
    conn1_publish_proxy = bus.get_object(conn.bus_name, conn1_publish)

    # second connection: get the contact list
    publish_handle = conn2.RequestHandles(cs.HT_LIST, ["publish"])[0]
    conn2_publish = conn2.RequestChannel(cs.CHANNEL_TYPE_CONTACT_LIST,
                                         cs.HT_LIST, publish_handle, False)
    conn2_publish_proxy = bus.get_object(conn2.bus_name, conn2_publish)

    # first connection: wait to see contact2
    # The signal MembersChanged may be already emitted... check the Members
    # property first
    contact2_handle_on_conn1 = 0
    conn1_members = conn1_publish_proxy.Get(cs.CHANNEL_IFACE_GROUP,
                                            'Members',
                                            dbus_interface=cs.PROPERTIES_IFACE)
    for h in conn1_members:
        name = conn.InspectHandles(cs.HT_CONTACT, [h])[0]
        if name == contact2_name:
            contact2_handle_on_conn1 = h
    while contact2_handle_on_conn1 == 0:
        e = q.expect('dbus-signal',
                     signal='MembersChanged',
                     path=conn1_publish)
        for h in e.args[1]:
            name = conn.InspectHandles(cs.HT_CONTACT, [h])[0]
            if name == contact2_name:
                contact2_handle_on_conn1 = h

    # second connection: wait to see contact1
    # The signal MembersChanged may be already emitted... check the Members
    # property first
    contact1_handle_on_conn2 = 0
    conn2_members = conn2_publish_proxy.Get(
        'org.freedesktop.Telepathy.Channel.Interface.Group',
        'Members',
        dbus_interface='org.freedesktop.DBus.Properties')
    for h in conn2_members:
        name = conn2.InspectHandles(cs.HT_CONTACT, [h])[0]
        if name == contact1_name:
            contact1_handle_on_conn2 = h
    while contact1_handle_on_conn2 == 0:
        e = q.expect('dbus-signal',
                     signal='MembersChanged',
                     path=conn2_publish)
        for h in e.args[1]:
            name = conn2.InspectHandles(cs.HT_CONTACT, [h])[0]
            if name == contact1_name:
                contact1_handle_on_conn2 = h

    return contact1_name, conn2, contact2_name, contact2_handle_on_conn1, contact1_handle_on_conn2
コード例 #24
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = {"txtvers": "1", "status": "avail"}

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name = conn.Properties.Get(cs.CONN, "SelfID")

    contact_name = "test-text-channel@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # create a clique room
    basic_txt = {"txtvers": "0"}
    AvahiAnnouncer("myroom", "_clique._udp", 41377, basic_txt)

    # connect a stream
    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added',
                 name=self_handle_name,
                 protocol=avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service=service)

    xmpp_connection = connect_to_stream(q, contact_name, self_handle_name,
                                        str(e.pt), e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason

    e = q.expect('stream-opened', connection=xmpp_connection)

    # send an invitation
    message = domish.Element(('', 'message'))
    message['type'] = 'normal'
    message.addElement('body', content='You got a Clique chatroom invitation')
    invite = message.addElement((NS_CLIQUE, 'invite'))
    invite.addElement('roomname', content='myroom')
    invite.addElement('reason', content='Inviting to this room')
    invite.addElement('address', content='127.0.0.1')
    invite.addElement('port', content='41377')
    xmpp_connection.send(message)

    # group channel is created
    e = q.expect('dbus-signal',
                 signal='NewChannel',
                 predicate=lambda e: e.args[1] == cs.CHANNEL_TYPE_TEXT and e.
                 args[2] == cs.HT_ROOM)
    path = e.args[0]
    channel = make_channel_proxy(conn, path, 'Channel')
    props_iface = dbus.Interface(bus.get_object(conn.object.bus_name, path),
                                 dbus.PROPERTIES_IFACE)

    q.expect('dbus-signal', signal='MembersChanged', path=path)

    lp_members = props_iface.Get(
        'org.freedesktop.Telepathy.Channel.Interface.Group',
        'LocalPendingMembers')

    assert len(lp_members) == 1
    added, actor, reason, msg = lp_members[0]

    assert added == self_handle
    assert actor == handle
    assert reason == 4  #invited
    assert msg == 'Inviting to this room'

    # decline invitation
    channel.Close()
    q.expect('dbus-signal', signal='Closed')
コード例 #25
0
def test(q, bus, conn):
    self_name = 'testsuite' + '@' + avahitest.get_host_name()

    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with the muc ones announces.
    wait_for_contact_list(q, conn)

    # check if we can request tube channels
    properties = conn.Properties.GetAll(cs.CONN_IFACE_REQUESTS)
    assert ({cs.CHANNEL_TYPE: cs.CHANNEL_TYPE_STREAM_TUBE,
             cs.TARGET_HANDLE_TYPE: cs.HT_ROOM},
             [cs.TARGET_HANDLE, cs.TARGET_ID, cs.STREAM_TUBE_SERVICE],
             ) in properties.get('RequestableChannelClasses'),\
                     properties['RequestableChannelClasses']

    # create muc channel using new API
    call_async(q, conn.Requests, 'CreateChannel',
            { cs.CHANNEL_TYPE: cs.CHANNEL_TYPE_STREAM_TUBE,
              cs.TARGET_HANDLE_TYPE: cs.HT_ROOM,
              cs.TARGET_ID: 'my-second-room',
              cs.STREAM_TUBE_SERVICE: 'loldongs',
              })

    ret, new_sig = q.expect_many(
        EventPattern('dbus-return', method='CreateChannel'),
        EventPattern('dbus-signal', signal='NewChannels'),
        )
    tube_path = ret.value[0]
    chan = wrap_channel(bus.get_object(conn.bus_name, tube_path),
                        'StreamTube')

    tube_props = ret.value[1]
    assert tube_props[cs.CHANNEL_TYPE] == cs.CHANNEL_TYPE_STREAM_TUBE
    assert tube_props[cs.TARGET_HANDLE_TYPE] == cs.HT_ROOM
    assert tube_props[cs.TARGET_ID] == 'my-second-room'
    assert tube_props[cs.REQUESTED] == True
    assert tube_props[cs.INITIATOR_HANDLE] == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert tube_props[cs.INITIATOR_ID] == self_name

    # text and tube channels are announced
    channels = new_sig.args[0]
    assert len(channels) == 1

    handle = tube_props[cs.TARGET_HANDLE]

    path, props = channels[0]
    assert props[cs.CHANNEL_TYPE] == cs.CHANNEL_TYPE_STREAM_TUBE
    assert path == tube_path
    assert props == tube_props
    assert props[cs.TARGET_HANDLE_TYPE] == cs.HT_ROOM
    assert props[cs.TARGET_HANDLE] == handle
    assert props[cs.TARGET_ID] == 'my-second-room'
    assert props[cs.INITIATOR_HANDLE] == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert props[cs.INITIATOR_ID] == self_name

    # ensure the same channel

# TODO: the muc channel doesn't bother to look at existing tubes
# before creating a new one. once that's fixed, uncomment this.
#    yours, ensured_path, _ = conn.Requests.EnsureChannel(
#            { cs.CHANNEL_TYPE: cs.CHANNEL_TYPE_STREAM_TUBE,
#              cs.TARGET_HANDLE_TYPE: cs.HT_ROOM,
#              cs.TARGET_HANDLE: handle,
#              cs.STREAM_TUBE_SERVICE: 'loldongs',
#              })

#    assert not yours
#    assert ensured_path == tube_path, (ensured_path, tube_path)

    conn.Disconnect()

    q.expect_many(
            EventPattern('dbus-signal', signal='Closed',
                path=tube_path),
            EventPattern('dbus-signal', signal='ChannelClosed', args=[tube_path]),
            EventPattern('dbus-signal', signal='StatusChanged', args=[2, 1]),
            )
コード例 #26
0
def test(q, bus, conn):
    self_name = 'testsuite' + '@' + get_host_name()

    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])

    basic_txt = { "txtvers": "1", "status": "avail" }
    contact_name = "test-request-im@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with the muc ones announces.
    wait_for_contact_list(q, conn)

    AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # check if we can request roomlist channels
    properties = conn.GetAll(
            tp_name_prefix + '.Connection.Interface.Requests',
            dbus_interface='org.freedesktop.DBus.Properties')
    assert ({tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
             tp_name_prefix + '.Channel.TargetHandleType': cs.HT_CONTACT,
             },
             [tp_name_prefix + '.Channel.TargetHandle',
              tp_name_prefix + '.Channel.TargetID'],
             ) in properties.get('RequestableChannelClasses'),\
                     properties['RequestableChannelClasses']

    # create muc channel
    requestotron = dbus.Interface(conn,
            tp_name_prefix + '.Connection.Interface.Requests')
    call_async(q, requestotron, 'CreateChannel',
            { tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
              tp_name_prefix + '.Channel.TargetHandleType': cs.HT_CONTACT,
              tp_name_prefix + '.Channel.TargetID': contact_name,
              })

    ret, new_sig = q.expect_many(
        EventPattern('dbus-return', method='CreateChannel'),
        EventPattern('dbus-signal', signal='NewChannels'),
        )
    path2 = ret.value[0]
    chan = make_channel_proxy(conn, path2, "Channel")

    props = ret.value[1]
    assert props[tp_name_prefix + '.Channel.ChannelType'] ==\
            cs.CHANNEL_TYPE_TEXT
    assert props[tp_name_prefix + '.Channel.TargetHandleType'] == cs.HT_CONTACT
    assert props[tp_name_prefix + '.Channel.TargetHandle'] == handle
    assert props[tp_name_prefix + '.Channel.TargetID'] == contact_name
    assert props[tp_name_prefix + '.Channel.Requested'] == True
    assert props[tp_name_prefix + '.Channel.InitiatorHandle'] \
            == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert props[tp_name_prefix + '.Channel.InitiatorID'] \
            == self_name

    assert new_sig.args[0][0][0] == path2
    assert new_sig.args[0][0][1] == props

    # ensure roomlist channel
    yours, ensured_path, ensured_props = requestotron.EnsureChannel(
            { tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_TEXT,
              tp_name_prefix + '.Channel.TargetHandleType': cs.HT_CONTACT,
              tp_name_prefix + '.Channel.TargetHandle': handle,
              })

    assert not yours
    assert ensured_path == path2, (ensured_path, path2)

    conn.Disconnect()

    q.expect_many(
            EventPattern('dbus-signal', signal='Closed',
                path=path2),
            EventPattern('dbus-signal', signal='ChannelClosed', args=[path2]),
            EventPattern('dbus-signal', signal='StatusChanged', args=[2, 1]),
            )
コード例 #27
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = { "txtvers": "1", "status": "avail" }

    contact_name = "test-text-channel@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    t = conn.Requests.CreateChannel({
        cs.CHANNEL_TYPE: cs.CHANNEL_TYPE_TEXT,
        cs.TARGET_HANDLE_TYPE: cs.HT_CONTACT,
        cs.TARGET_HANDLE: handle})[0]
    text_channel = make_channel_proxy(conn, t, "Channel.Type.Text")
    text_channel.Send(cs.MT_NORMAL, INCOMING_MESSAGE)

    e = q.expect('incoming-connection', listener = listener)
    incoming = e.connection

    e = q.expect('stream-message', connection = incoming)
    assert e.message_type == "chat"
    body = xpath.queryForNodes("/message/body",  e.stanza )
    assert map(str, body) == [ INCOMING_MESSAGE ]

    # drop the connection
    incoming.transport.loseConnection()

    # Now send a message to salut
    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name =  conn.Properties.Get(cs.CONN, "SelfID")


    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
        protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()


    e = q.expect('service-resolved', service = service)

    outbound = connect_to_stream(q, contact_name,
        self_handle_name, str(e.pt), e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason

    e = q.expect('stream-opened', connection = outbound)

    # connected to salut, now send a message
    message = domish.Element(('', 'message'))
    message['type'] = "chat"
    message.addElement('body', content=OUTGOING_MESSAGE)

    e.connection.send(message)

    e = q.expect('dbus-signal', signal='Received')
    assert e.args[2] == handle
    assert e.args[3] == cs.MT_NORMAL
    assert e.args[5] == OUTGOING_MESSAGE
コード例 #28
0
def test(q, bus, conn):
    call_async(q, conn.Future, 'EnsureSidecar', ycs.STATUS_IFACE)

    conn.Connect()

    # Now we're connected, the call we made earlier should return.
    e = q.expect('dbus-return', method='EnsureSidecar')
    path, props = e.value
    assertEquals({}, props)

    status = ProxyWrapper(bus.get_object(conn.bus_name, path),
                          ycs.STATUS_IFACE, {})

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)

    # announce a contact with the right caps
    ver = compute_caps_hash([], [], banshee)
    txt_record = {
        "txtvers": "1",
        "status": "avail",
        "node": CLIENT_NAME,
        "ver": ver,
        "hash": "sha-1"
    }
    contact_name = "test-service@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
                               txt_record)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener=listener)
    incoming = e.connection

    # Salut looks up its capabilities
    event = q.expect('stream-iq', connection=incoming, query_ns=ns.DISCO_INFO)
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assertEquals(CLIENT_NAME + '#' + ver, query_node.attributes['node'])

    contact_handle = conn.RequestHandles(cs.HT_CONTACT, [contact_name])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = CLIENT_NAME + '#' + ver
    x = query.addElement((ns.X_DATA, 'x'))
    x['type'] = 'result'

    # FORM_TYPE
    field = x.addElement((None, 'field'))
    field['var'] = 'FORM_TYPE'
    field['type'] = 'hidden'
    field.addElement((None, 'value'),
                     content='urn:ytstenut:capabilities#org.gnome.Banshee')

    # type
    field = x.addElement((None, 'field'))
    field['var'] = 'type'
    field.addElement((None, 'value'), content='application')

    # name
    field = x.addElement((None, 'field'))
    field['var'] = 'name'
    field.addElement((None, 'value'), content='en_GB/Banshee Media Player')
    field.addElement((None, 'value'), content='fr/Banshee Lecteur de Musique')

    # capabilities
    field = x.addElement((None, 'field'))
    field['var'] = 'capabilities'
    field.addElement((None, 'value'),
                     content='urn:ytstenut:capabilities:yts-caps-audio')
    field.addElement((None, 'value'), content='urn:ytstenut:data:jingle:rtp')

    incoming.send(result)

    # this will be fired as text channel caps will be fired
    _, e = q.expect_many(
        EventPattern('dbus-signal',
                     signal='ContactCapabilitiesChanged',
                     predicate=lambda e: contact_handle in e.args[0]),
        EventPattern('dbus-signal', signal='ServiceAdded'))

    contact_id, service_name, details = e.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Banshee', service_name)

    type, name_map, caps = details
    assertEquals('application', type)
    assertEquals(
        {
            'en_GB': 'Banshee Media Player',
            'fr': 'Banshee Lecteur de Musique'
        }, name_map)
    assertSameSets([
        'urn:ytstenut:capabilities:yts-caps-audio',
        'urn:ytstenut:data:jingle:rtp'
    ], caps)

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            contact_name: {
                'org.gnome.Banshee': ('application', {
                    'en_GB': 'Banshee Media Player',
                    'fr': 'Banshee Lecteur de Musique'
                }, [
                    'urn:ytstenut:capabilities:yts-caps-audio',
                    'urn:ytstenut:data:jingle:rtp'
                ])
            },
        }, discovered)

    # add evince
    tmp = banshee.copy()
    tmp.update(evince)
    ver = compute_caps_hash([], [], tmp)
    txt_record['ver'] = ver
    announcer.update(txt_record)

    # Salut looks up our capabilities
    event = q.expect('stream-iq',
                     connection=incoming,
                     query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        CLIENT_NAME + '#' + txt_record['ver']

    # send good reply
    result['id'] = event.stanza['id']
    query['node'] = CLIENT_NAME + '#' + ver

    x = query.addElement((ns.X_DATA, 'x'))
    x['type'] = 'result'

    # FORM_TYPE
    field = x.addElement((None, 'field'))
    field['var'] = 'FORM_TYPE'
    field['type'] = 'hidden'
    field.addElement((None, 'value'),
                     content='urn:ytstenut:capabilities#org.gnome.Evince')

    # type
    field = x.addElement((None, 'field'))
    field['var'] = 'type'
    field.addElement((None, 'value'), content='application')

    # name
    field = x.addElement((None, 'field'))
    field['var'] = 'name'
    field.addElement((None, 'value'), content='en_GB/Evince Picture Viewer')
    field.addElement((None, 'value'), content='fr/Evince uh, ow do you say')

    # capabilities
    field = x.addElement((None, 'field'))
    field['var'] = 'capabilities'
    field.addElement((None, 'value'), content='urn:ytstenut:capabilities:pics')

    incoming.send(result)

    e = q.expect('dbus-signal', signal='ServiceAdded')

    contact_id, service_name, details = e.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Evince', service_name)

    type, name_map, caps = details
    assertEquals('application', type)
    assertEquals(
        {
            'en_GB': 'Evince Picture Viewer',
            'fr': 'Evince uh, ow do you say'
        }, name_map)
    assertSameSets(['urn:ytstenut:capabilities:pics'], caps)

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            contact_name: {
                'org.gnome.Banshee': ('application', {
                    'en_GB': 'Banshee Media Player',
                    'fr': 'Banshee Lecteur de Musique'
                }, [
                    'urn:ytstenut:capabilities:yts-caps-audio',
                    'urn:ytstenut:data:jingle:rtp'
                ]),
                'org.gnome.Evince': ('application', {
                    'en_GB': 'Evince Picture Viewer',
                    'fr': 'Evince uh, ow do you say'
                }, ['urn:ytstenut:capabilities:pics'])
            }
        }, discovered)

    # remove evince
    ver = compute_caps_hash([], [], banshee)
    txt_record['ver'] = ver

    forbidden = [
        EventPattern('dbus-signal', signal='stream-iq', connection=incoming)
    ]
    q.forbid_events(forbidden)

    announcer.update(txt_record)

    e = q.expect('dbus-signal', signal='ServiceRemoved')

    contact_id, service_name = e.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Evince', service_name)

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            contact_name: {
                'org.gnome.Banshee': ('application', {
                    'en_GB': 'Banshee Media Player',
                    'fr': 'Banshee Lecteur de Musique'
                }, [
                    'urn:ytstenut:capabilities:yts-caps-audio',
                    'urn:ytstenut:data:jingle:rtp'
                ])
            },
        }, discovered)

    sync_stream(q, incoming)

    q.unforbid_events(forbidden)

    # now just evince
    ver = compute_caps_hash([], [], evince)
    txt_record['ver'] = ver
    announcer.update(txt_record)

    # Salut looks up our capabilities
    event = q.expect('stream-iq',
                     connection=incoming,
                     query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        CLIENT_NAME + '#' + txt_record['ver']

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = CLIENT_NAME + '#' + ver

    x = query.addElement((ns.X_DATA, 'x'))
    x['type'] = 'result'

    # FORM_TYPE
    field = x.addElement((None, 'field'))
    field['var'] = 'FORM_TYPE'
    field['type'] = 'hidden'
    field.addElement((None, 'value'),
                     content='urn:ytstenut:capabilities#org.gnome.Evince')

    # type
    field = x.addElement((None, 'field'))
    field['var'] = 'type'
    field.addElement((None, 'value'), content='application')

    # name
    field = x.addElement((None, 'field'))
    field['var'] = 'name'
    field.addElement((None, 'value'), content='en_GB/Evince Picture Viewer')
    field.addElement((None, 'value'), content='fr/Evince uh, ow do you say')

    # capabilities
    field = x.addElement((None, 'field'))
    field['var'] = 'capabilities'
    field.addElement((None, 'value'), content='urn:ytstenut:capabilities:pics')

    incoming.send(result)

    sa, sr = q.expect_many(
        EventPattern('dbus-signal', signal='ServiceAdded'),
        EventPattern('dbus-signal', signal='ServiceRemoved'))

    contact_id, service_name, details = sa.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Evince', service_name)

    type, name_map, caps = details
    assertEquals('application', type)
    assertEquals(
        {
            'en_GB': 'Evince Picture Viewer',
            'fr': 'Evince uh, ow do you say'
        }, name_map)
    assertSameSets(['urn:ytstenut:capabilities:pics'], caps)

    contact_id, service_name = sr.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Banshee', service_name)

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            contact_name: {
                'org.gnome.Evince': ('application', {
                    'en_GB': 'Evince Picture Viewer',
                    'fr': 'Evince uh, ow do you say'
                }, ['urn:ytstenut:capabilities:pics'])
            }
        }, discovered)

    # just banshee again
    ver = compute_caps_hash([], [], banshee)
    txt_record['ver'] = ver

    forbidden = [
        EventPattern('dbus-signal', signal='stream-iq', connection=incoming)
    ]
    q.forbid_events(forbidden)

    announcer.update(txt_record)

    sr, sa = q.expect_many(
        EventPattern('dbus-signal', signal='ServiceRemoved'),
        EventPattern('dbus-signal', signal='ServiceAdded'))

    contact_id, service_name = sr.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Evince', service_name)

    contact_id, service_name, details = sa.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Banshee', service_name)

    type, name_map, caps = details
    assertEquals('application', type)
    assertEquals(
        {
            'en_GB': 'Banshee Media Player',
            'fr': 'Banshee Lecteur de Musique'
        }, name_map)
    assertSameSets([
        'urn:ytstenut:capabilities:yts-caps-audio',
        'urn:ytstenut:data:jingle:rtp'
    ], caps)

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            contact_name: {
                'org.gnome.Banshee': ('application', {
                    'en_GB': 'Banshee Media Player',
                    'fr': 'Banshee Lecteur de Musique'
                }, [
                    'urn:ytstenut:capabilities:yts-caps-audio',
                    'urn:ytstenut:data:jingle:rtp'
                ])
            }
        }, discovered)

    sync_stream(q, incoming)

    q.unforbid_events(forbidden)

    # both again
    ver = compute_caps_hash([], [], tmp)
    txt_record['ver'] = ver
    announcer.update(txt_record)

    sa = q.expect('dbus-signal', signal='ServiceAdded')

    contact_id, service_name, details = sa.args
    assertEquals(contact_name, contact_id)
    assertEquals('org.gnome.Evince', service_name)

    type, name_map, caps = details
    assertEquals('application', type)
    assertEquals(
        {
            'en_GB': 'Evince Picture Viewer',
            'fr': 'Evince uh, ow do you say'
        }, name_map)
    assertSameSets(['urn:ytstenut:capabilities:pics'], caps)

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            contact_name: {
                'org.gnome.Banshee': ('application', {
                    'en_GB': 'Banshee Media Player',
                    'fr': 'Banshee Lecteur de Musique'
                }, [
                    'urn:ytstenut:capabilities:yts-caps-audio',
                    'urn:ytstenut:data:jingle:rtp'
                ]),
                'org.gnome.Evince': ('application', {
                    'en_GB': 'Evince Picture Viewer',
                    'fr': 'Evince uh, ow do you say'
                }, ['urn:ytstenut:capabilities:pics'])
            }
        }, discovered)

    sync_stream(q, incoming)

    # and finally, nothing
    ver = compute_caps_hash([], [], {})
    txt_record['ver'] = ver
    announcer.update(txt_record)

    # Salut looks up our capabilities
    event = q.expect('stream-iq',
                     connection=incoming,
                     query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        CLIENT_NAME + '#' + txt_record['ver']

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = CLIENT_NAME + '#' + ver

    incoming.send(result)

    q.expect_many(
        EventPattern('dbus-signal',
                     signal='ServiceRemoved',
                     args=[contact_name, 'org.gnome.Banshee']),
        EventPattern('dbus-signal',
                     signal='ServiceRemoved',
                     args=[contact_name, 'org.gnome.Evince']))

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)
コード例 #29
0
def test(q, bus, conn):
    # we won't be using any data forms, so these two shouldn't ever be
    # fired.
    q.forbid_events([
        EventPattern('dbus-signal', signal='ServiceAdded'),
        EventPattern('dbus-signal', signal='ServiceRemoved')
    ])

    call_async(q, conn.Future, 'EnsureSidecar', ycs.STATUS_IFACE)

    conn.Connect()

    # Now we're connected, the call we made earlier should return.
    e = q.expect('dbus-return', method='EnsureSidecar')
    path, props = e.value
    assertEquals({}, props)

    status = ProxyWrapper(bus.get_object(conn.bus_name, path),
                          ycs.STATUS_IFACE, {})

    # bad capability argument
    call_async(q, status, 'AdvertiseStatus', '', 'service.name', '')
    q.expect('dbus-error', method='AdvertiseStatus')

    # bad service name
    call_async(q, status, 'AdvertiseStatus', CAP_NAME, '', '')
    q.expect('dbus-error', method='AdvertiseStatus')

    # we can't test that the message type="headline" stanza is
    # actually received because it's thrown into the loopback stream
    # immediately.

    # announce a contact with the right caps
    ver = compute_caps_hash([], [CAP_NAME + '+notify'], {})
    txt_record = {
        "txtvers": "1",
        "status": "avail",
        "node": CLIENT_NAME,
        "ver": ver,
        "hash": "sha-1"
    }
    contact_name = "test-status@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
                               txt_record)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener=listener)
    incoming = e.connection

    # Salut looks up its capabilities
    event = q.expect('stream-iq', connection=incoming, query_ns=ns.DISCO_INFO)
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assertEquals(CLIENT_NAME + '#' + ver, query_node.attributes['node'])

    contact_handle = conn.RequestHandles(cs.HT_CONTACT, [contact_name])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = CLIENT_NAME + '#' + ver

    feature = query.addElement('feature')
    feature['var'] = CAP_NAME + '+notify'
    incoming.send(result)

    # this will be fired as text channel caps will be fired
    q.expect('dbus-signal',
             signal='ContactCapabilitiesChanged',
             predicate=lambda e: contact_handle in e.args[0])

    # okay now we know about the contact's caps, we can go ahead

    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)

    el = Element(('urn:ytstenut:status', 'status'))
    el['activity'] = 'messing-with-your-stuff'
    desc = el.addElement('ytstenut:description',
                         content='Yeah sorry about that')
    desc['xml:lang'] = 'en-GB'

    call_async(q, status, 'AdvertiseStatus', CAP_NAME, 'ants.in.their.pants',
               el.toXml())

    e, _, sig = q.expect_many(
        EventPattern('stream-message', connection=incoming),
        EventPattern('dbus-return', method='AdvertiseStatus'),
        EventPattern('dbus-signal',
                     signal='StatusChanged',
                     interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('messing-with-your-stuff', status_el['activity'])
    assertEquals('ants.in.their.pants', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])

    # check signal
    contact_id, capability, service_name, status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('ants.in.their.pants', service_name)
    assertNotEquals('', status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            'testsuite@testsuite': {
                CAP_NAME: {
                    'ants.in.their.pants': status_str
                }
            }
        }, discovered)

    # set another
    el = Element(('urn:ytstenut:status', 'status'))
    el['activity'] = 'rofling'
    desc = el.addElement('ytstenut:description', content='U MAD?')
    desc['xml:lang'] = 'en-GB'

    call_async(q, status, 'AdvertiseStatus', CAP_NAME, 'bananaman.on.holiday',
               el.toXml())

    e, _, sig = q.expect_many(
        EventPattern('stream-message', connection=incoming),
        EventPattern('dbus-return', method='AdvertiseStatus'),
        EventPattern('dbus-signal',
                     signal='StatusChanged',
                     interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('rofling', status_el['activity'])
    assertEquals('bananaman.on.holiday', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])

    # check signal
    contact_id, capability, service_name, bananaman_status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('bananaman.on.holiday', service_name)
    assertNotEquals('', bananaman_status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            'testsuite@testsuite': {
                CAP_NAME: {
                    'ants.in.their.pants': status_str,
                    'bananaman.on.holiday': bananaman_status_str
                }
            }
        }, discovered)

    # unset the status from one service
    call_async(q, status, 'AdvertiseStatus', CAP_NAME, 'ants.in.their.pants',
               '')

    e, _, sig = q.expect_many(
        EventPattern('stream-message', connection=incoming),
        EventPattern('dbus-return', method='AdvertiseStatus'),
        EventPattern('dbus-signal',
                     signal='StatusChanged',
                     interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('ants.in.their.pants', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])
    assert 'activity' not in status_el.attributes
    assertEquals([], status_el.children)

    # check signal
    contact_id, capability, service_name, status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('ants.in.their.pants', service_name)
    assertEquals('', status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals(
        {
            'testsuite@testsuite': {
                CAP_NAME: {
                    'bananaman.on.holiday': bananaman_status_str
                }
            }
        }, discovered)

    # unset the status from the other service
    call_async(q, status, 'AdvertiseStatus', CAP_NAME, 'bananaman.on.holiday',
               '')

    e, _, sig = q.expect_many(
        EventPattern('stream-message', connection=incoming),
        EventPattern('dbus-return', method='AdvertiseStatus'),
        EventPattern('dbus-signal',
                     signal='StatusChanged',
                     interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('bananaman.on.holiday', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])
    assert 'activity' not in status_el.attributes
    assertEquals([], status_el.children)

    # check signal
    contact_id, capability, service_name, status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('bananaman.on.holiday', service_name)
    assertEquals('', status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE,
                            'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)
コード例 #30
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = {"txtvers": "1", "status": "avail"}

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name = conn.Properties.Get(cs.CONN, "SelfID")

    contact_name = "test-muc@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    requests_iface = dbus.Interface(conn, cs.CONN_IFACE_REQUESTS)

    # Create a connection to send the muc invite
    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added',
                 name=self_handle_name,
                 protocol=avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service=service)

    outbound = connect_to_stream(q, contact_name, self_handle_name, str(e.pt),
                                 e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason
    e = q.expect('stream-opened', connection=outbound)

    # connected to Salut, now send the muc invite
    msg = domish.Element((None, 'message'))
    msg['to'] = self_handle_name
    msg['from'] = contact_name
    msg['type'] = 'normal'
    body = msg.addElement('body',
                          content='You got a Clique chatroom invitation')
    invite = msg.addElement((NS_CLIQUE, 'invite'))
    invite.addElement('roomname', content='my-room')
    invite.addElement('reason', content='Inviting to this room')
    # FIXME: we should create a real Clique room and use its IP and port.
    # Hardcode values for now. The IP is a multicast address.
    invite.addElement('address', content='239.255.71.249')
    invite.addElement('port', content='62472')
    outbound.send(msg)

    e = q.expect('dbus-signal',
                 signal='NewChannels',
                 predicate=lambda e: e.args[0][0][1][cs.CHANNEL_TYPE] == cs.
                 CHANNEL_TYPE_TEXT)
    channels = e.args[0]
    assert len(channels) == 1
    path, props = channels[0]
    channel = make_channel_proxy(conn, path, "Channel")
    channel_group = make_channel_proxy(conn, path, "Channel.Interface.Group")

    # check channel properties
    # org.freedesktop.Telepathy.Channel D-Bus properties
    assert props[cs.CHANNEL_TYPE] == cs.CHANNEL_TYPE_TEXT
    assertContains(cs.CHANNEL_IFACE_GROUP, props[cs.INTERFACES])
    assertContains(cs.CHANNEL_IFACE_MESSAGES, props[cs.INTERFACES])
    assert props[cs.TARGET_ID] == 'my-room'
    assert props[cs.TARGET_HANDLE_TYPE] == HT_ROOM
    assert props[cs.REQUESTED] == False
    assert props[cs.INITIATOR_HANDLE] == handle
    assert props[cs.INITIATOR_ID] == contact_name

    # we are added to local pending
    e = q.expect('dbus-signal', signal='MembersChanged')
    msg, added, removed, lp, rp, actor, reason = e.args
    assert msg == 'Inviting to this room'
    assert added == []
    assert removed == []
    assert lp == [self_handle]
    assert rp == []
    assert actor == handle
    assert reason == 4  # invited

    # TODO: join the muc, check if we are added to remote-pending and then
    # to members. This would need some tweak in Salut and/or the test framework
    # as Clique takes too much time to join the room and so the event times
    # out.

    # TODO: test sending invitations

    # FIXME: fd.o #30531: this ought to work, but doesn't
    #channel_group.RemoveMembersWithReason([self_handle], "bored now", 0)
    channel.Close()
    q.expect('dbus-signal', signal='Closed')
def test(q, bus, conn):
    # we won't be using any data forms, so these two shouldn't ever be
    # fired.
    q.forbid_events([EventPattern('dbus-signal', signal='ServiceAdded'),
                     EventPattern('dbus-signal', signal='ServiceRemoved')])

    call_async(q, conn.Future, 'EnsureSidecar', ycs.STATUS_IFACE)

    conn.Connect()

    # Now we're connected, the call we made earlier should return.
    e = q.expect('dbus-return', method='EnsureSidecar')
    path, props = e.value
    assertEquals({}, props)

    status = ProxyWrapper(bus.get_object(conn.bus_name, path),
                          ycs.STATUS_IFACE, {})

    # bad capability argument
    call_async(q, status, 'AdvertiseStatus', '', 'service.name', '')
    q.expect('dbus-error', method='AdvertiseStatus')

    # bad service name
    call_async(q, status, 'AdvertiseStatus', CAP_NAME, '', '')
    q.expect('dbus-error', method='AdvertiseStatus')

    # we can't test that the message type="headline" stanza is
    # actually received because it's thrown into the loopback stream
    # immediately.

    # announce a contact with the right caps
    ver = compute_caps_hash([], [CAP_NAME + '+notify'], {})
    txt_record = { "txtvers": "1", "status": "avail",
        "node": CLIENT_NAME, "ver": ver, "hash": "sha-1"}
    contact_name = "test-status@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port, txt_record)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener=listener)
    incoming = e.connection

    # Salut looks up its capabilities
    event = q.expect('stream-iq', connection=incoming,
        query_ns=ns.DISCO_INFO)
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assertEquals(CLIENT_NAME + '#' + ver, query_node.attributes['node'])

    contact_handle = conn.RequestHandles(cs.HT_CONTACT, [contact_name])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = CLIENT_NAME + '#' + ver

    feature = query.addElement('feature')
    feature['var'] = CAP_NAME + '+notify'
    incoming.send(result)

    # this will be fired as text channel caps will be fired
    q.expect('dbus-signal', signal='ContactCapabilitiesChanged',
             predicate=lambda e: contact_handle in e.args[0])

    # okay now we know about the contact's caps, we can go ahead

    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)

    el = Element(('urn:ytstenut:status', 'status'))
    el['activity'] = 'messing-with-your-stuff'
    desc = el.addElement('ytstenut:description', content='Yeah sorry about that')
    desc['xml:lang'] = 'en-GB'

    call_async(q, status, 'AdvertiseStatus', CAP_NAME,
               'ants.in.their.pants', el.toXml())

    e, _, sig = q.expect_many(EventPattern('stream-message', connection=incoming),
                              EventPattern('dbus-return', method='AdvertiseStatus'),
                              EventPattern('dbus-signal', signal='StatusChanged',
                                           interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('messing-with-your-stuff', status_el['activity'])
    assertEquals('ants.in.their.pants', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])

    # check signal
    contact_id, capability, service_name, status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('ants.in.their.pants', service_name)
    assertNotEquals('', status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({'testsuite@testsuite': {CAP_NAME: {'ants.in.their.pants': status_str}}},
                 discovered)

    # set another
    el = Element(('urn:ytstenut:status', 'status'))
    el['activity'] = 'rofling'
    desc = el.addElement('ytstenut:description', content='U MAD?')
    desc['xml:lang'] = 'en-GB'

    call_async(q, status, 'AdvertiseStatus', CAP_NAME,
               'bananaman.on.holiday', el.toXml())

    e, _, sig = q.expect_many(EventPattern('stream-message', connection=incoming),
                              EventPattern('dbus-return', method='AdvertiseStatus'),
                              EventPattern('dbus-signal', signal='StatusChanged',
                                           interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('rofling', status_el['activity'])
    assertEquals('bananaman.on.holiday', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])

    # check signal
    contact_id, capability, service_name, bananaman_status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('bananaman.on.holiday', service_name)
    assertNotEquals('', bananaman_status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({'testsuite@testsuite': {CAP_NAME: {
                    'ants.in.their.pants': status_str,
                    'bananaman.on.holiday': bananaman_status_str}}},
                 discovered)

    # unset the status from one service
    call_async(q, status, 'AdvertiseStatus', CAP_NAME,
               'ants.in.their.pants', '')

    e, _, sig = q.expect_many(EventPattern('stream-message', connection=incoming),
                              EventPattern('dbus-return', method='AdvertiseStatus'),
                              EventPattern('dbus-signal', signal='StatusChanged',
                                           interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('ants.in.their.pants', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])
    assert 'activity' not in status_el.attributes
    assertEquals([], status_el.children)

    # check signal
    contact_id, capability, service_name, status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('ants.in.their.pants', service_name)
    assertEquals('', status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({'testsuite@testsuite': {CAP_NAME: {
                    'bananaman.on.holiday': bananaman_status_str}}},
                 discovered)

    # unset the status from the other service
    call_async(q, status, 'AdvertiseStatus', CAP_NAME,
               'bananaman.on.holiday', '')

    e, _, sig = q.expect_many(EventPattern('stream-message', connection=incoming),
                              EventPattern('dbus-return', method='AdvertiseStatus'),
                              EventPattern('dbus-signal', signal='StatusChanged',
                                           interface=ycs.STATUS_IFACE))

    # check message
    message = e.stanza
    event = message.children[0]
    items = event.children[0]
    item = items.children[0]
    status_el = item.children[0]

    assertEquals('status', status_el.name)
    assertEquals('bananaman.on.holiday', status_el['from-service'])
    assertEquals(CAP_NAME, status_el['capability'])
    assert 'activity' not in status_el.attributes
    assertEquals([], status_el.children)

    # check signal
    contact_id, capability, service_name, status_str = sig.args
    assertEquals(CAP_NAME, capability)
    assertEquals('bananaman.on.holiday', service_name)
    assertEquals('', status_str)

    # check property
    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredStatuses',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)
コード例 #32
0
def test(q, bus, conn):
    contact_name = "test-hct@" + get_host_name()

    call_async(q, conn.Future, 'EnsureSidecar', ycs.STATUS_IFACE)
    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0, 0])

    e = q.expect('dbus-return', method='EnsureSidecar')
    path, props = e.value
    assertEquals({}, props)

    status = ProxyWrapper(bus.get_object(conn.bus_name, path),
                          ycs.STATUS_IFACE, {})

    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)

    self_handle = conn.GetSelfHandle()
    self_handle_name =  conn.InspectHandles(cs.HT_CONTACT, [self_handle])[0]

    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
        protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()

    q.expect('service-resolved', service=service)

    # now update the caps
    conn.ContactCapabilities.UpdateCapabilities([
        ('well.gnome.name', [],
         ['org.freedesktop.ytstenut.xpmn.Channel/uid/org.gnome.Banshee',
          'org.freedesktop.ytstenut.xpmn.Channel/type/application',
          'org.freedesktop.ytstenut.xpmn.Channel/name/en_GB/Banshee Media Player',
          'org.freedesktop.ytstenut.xpmn.Channel/name/fr/Banshee Lecteur de Musique',
          'org.freedesktop.ytstenut.xpmn.Channel/caps/urn:ytstenut:capabilities:yts-caps-audio',
          'org.freedesktop.ytstenut.xpmn.Channel/caps/urn:ytstenut:data:jingle:rtp'])])

    e, _ = q.expect_many(EventPattern('service-resolved', service=service),
                         EventPattern('dbus-signal', signal='ServiceAdded'))
    node = txt_get_key(e.txt, 'node')
    ver = txt_get_key(e.txt, 'ver')

    # don't check the hash here because it could change in salut and
    # it would break this test even though it wouldn't /actually/ be
    # broken

    outbound = connect_to_stream(q, contact_name,
        self_handle_name, str(e.pt), e.port)
    e = q.expect('connection-result')
    assert e.succeeded, e.reason
    e = q.expect('stream-opened', connection=outbound)

    # ask what this ver means
    request = \
        elem_iq(outbound, 'get', from_=contact_name)(
          elem(ns.DISCO_INFO, 'query', node=(node + '#' + ver))
        )
    outbound.send(request)

    # receive caps
    e = q.expect('stream-iq', connection=outbound,
                 query_ns=ns.DISCO_INFO, iq_id=request['id'])

    iq = e.stanza
    query = iq.children[0]

    x = None
    for child in query.children:
        if child.name == 'x' and child.uri == ns.X_DATA:
            # we should only have one child
            assert x is None
            x = child
            # don't break here as we can waste time to make sure x
            # isn't assigned twice

    assert x is not None

    for field in x.children:
        if field['var'] == 'FORM_TYPE':
            assertEquals('hidden', field['type'])
            assertEquals('urn:ytstenut:capabilities#org.gnome.Banshee',
                         field.children[0].children[0])
        elif field['var'] == 'type':
            assertEquals('application', field.children[0].children[0])
        elif field['var'] == 'name':
            names = [a.children[0] for a in field.children]
            assertLength(2, names)
            assertContains('en_GB/Banshee Media Player', names)
            assertContains('fr/Banshee Lecteur de Musique', names)
        elif field['var'] == 'capabilities':
            caps = [a.children[0] for a in field.children]
            assertLength(2, caps)
            assertContains('urn:ytstenut:capabilities:yts-caps-audio', caps)
            assertContains('urn:ytstenut:data:jingle:rtp', caps)
        else:
            assert False

    # now add another service
    forbidden = [EventPattern('dbus-signal', signal='ServiceRemoved')]
    q.forbid_events(forbidden)

    conn.ContactCapabilities.UpdateCapabilities([
        ('another.nice.gname', [],
         ['org.freedesktop.ytstenut.xpmn.Channel/uid/org.gnome.Eog',
          'org.freedesktop.ytstenut.xpmn.Channel/type/application',
          'org.freedesktop.ytstenut.xpmn.Channel/name/en_GB/Eye Of Gnome',
          'org.freedesktop.ytstenut.xpmn.Channel/name/it/Occhio Di uno Gnomo',
          'org.freedesktop.ytstenut.xpmn.Channel/caps/urn:ytstenut:capabilities:yts-picz'])])

    e = q.expect('dbus-signal', signal='ServiceAdded')

    sync_dbus(bus, q, conn)

    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({'testsuite@testsuite':
                      {'org.gnome.Banshee': ('application',
                                             {'en_GB': 'Banshee Media Player',
                                              'fr': 'Banshee Lecteur de Musique'},
                                             ['urn:ytstenut:capabilities:yts-caps-audio',
                                              'urn:ytstenut:data:jingle:rtp']),
                       'org.gnome.Eog': ('application',
                                         {'en_GB': 'Eye Of Gnome',
                                          'it': 'Occhio Di uno Gnomo'},
                                         ['urn:ytstenut:capabilities:yts-picz'])}},
                 discovered)

    q.unforbid_events(forbidden)

    forbidden = [EventPattern('dbus-signal', signal='ServiceRemoved',
                              args=[self_handle_name, 'org.gnome.Eog'])]
    q.forbid_events(forbidden)

    conn.ContactCapabilities.UpdateCapabilities([
            ('well.gnome.name', [], [])])

    e = q.expect('dbus-signal', signal='ServiceRemoved',
                 args=[self_handle_name, 'org.gnome.Banshee'])

    sync_dbus(bus, q, conn)

    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({'testsuite@testsuite':
                      {'org.gnome.Eog': ('application',
                                         {'en_GB': 'Eye Of Gnome',
                                          'it': 'Occhio Di uno Gnomo'},
                                         ['urn:ytstenut:capabilities:yts-picz'])}},
                 discovered)

    q.unforbid_events(forbidden)

    conn.ContactCapabilities.UpdateCapabilities([
            ('another.nice.gname', [], [])])

    e = q.expect('dbus-signal', signal='ServiceRemoved',
                 args=[self_handle_name, 'org.gnome.Eog'])

    discovered = status.Get(ycs.STATUS_IFACE, 'DiscoveredServices',
                            dbus_interface=dbus.PROPERTIES_IFACE)
    assertEquals({}, discovered)
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])
    basic_txt = { "txtvers": "1", "status": "avail" }

    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name =  conn.Properties.Get(cs.CONN, "SelfID")

    contact_name = "test-muc@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)

    AvahiAnnouncer(contact_name, "_presence._tcp", port, basic_txt)

    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    requests_iface = dbus.Interface(conn, cs.CONN_IFACE_REQUESTS)

    # Create a connection to send the muc invite
    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
        protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()

    e = q.expect('service-resolved', service = service)

    outbound = connect_to_stream(q, contact_name,
        self_handle_name, str(e.pt), e.port)

    e = q.expect('connection-result')
    assert e.succeeded, e.reason
    e = q.expect('stream-opened', connection = outbound)

    # connected to Salut, now send the muc invite
    msg = domish.Element((None, 'message'))
    msg['to'] = self_handle_name
    msg['from'] = contact_name
    msg['type'] = 'normal'
    body = msg.addElement('body', content='You got a Clique chatroom invitation')
    invite = msg.addElement((NS_CLIQUE, 'invite'))
    invite.addElement('roomname', content='my-room')
    invite.addElement('reason', content='Inviting to this room')
    # FIXME: we should create a real Clique room and use its IP and port.
    # Hardcode values for now. The IP is a multicast address.
    invite.addElement('address', content='239.255.71.249')
    invite.addElement('port', content='62472')
    outbound.send(msg)

    e = q.expect('dbus-signal', signal='NewChannels',
            predicate=lambda e:
                e.args[0][0][1][cs.CHANNEL_TYPE] == cs.CHANNEL_TYPE_TEXT)
    channels = e.args[0]
    assert len(channels) == 1
    path, props = channels[0]
    channel = make_channel_proxy(conn, path, "Channel")
    channel_group = make_channel_proxy(conn, path, "Channel.Interface.Group")

    # check channel properties
    # org.freedesktop.Telepathy.Channel D-Bus properties
    assert props[cs.CHANNEL_TYPE] == cs.CHANNEL_TYPE_TEXT
    assertContains(cs.CHANNEL_IFACE_GROUP, props[cs.INTERFACES])
    assertContains(cs.CHANNEL_IFACE_MESSAGES, props[cs.INTERFACES])
    assert props[cs.TARGET_ID] == 'my-room'
    assert props[cs.TARGET_HANDLE_TYPE] == HT_ROOM
    assert props[cs.REQUESTED] == False
    assert props[cs.INITIATOR_HANDLE] == handle
    assert props[cs.INITIATOR_ID] == contact_name

    # we are added to local pending
    e = q.expect('dbus-signal', signal='MembersChanged')
    msg, added, removed, lp, rp, actor, reason = e.args
    assert msg == 'Inviting to this room'
    assert added == []
    assert removed == []
    assert lp == [self_handle]
    assert rp == []
    assert actor == handle
    assert reason == 4       # invited

    # TODO: join the muc, check if we are added to remote-pending and then
    # to members. This would need some tweak in Salut and/or the test framework
    # as Clique takes too much time to join the room and so the event times
    # out.

    # TODO: test sending invitations

    # FIXME: fd.o #30531: this ought to work, but doesn't
    #channel_group.RemoveMembersWithReason([self_handle], "bored now", 0)
    channel.Close()
    q.expect('dbus-signal', signal='Closed')
def test_ft_caps_from_contact(q, bus, conn, client):

    conn_caps_iface = dbus.Interface(conn, cs.CONN_IFACE_CONTACT_CAPS)
    conn_contacts_iface = dbus.Interface(conn, cs.CONN_IFACE_CONTACTS)

    # send presence with FT capa
    ver = compute_caps_hash([], [ns.IQ_OOB], {})
    txt_record = { "txtvers": "1", "status": "avail",
        "node": client, "ver": ver, "hash": "sha-1"}
    contact_name = "test-caps-ft@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
            txt_record)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener = listener)
    incoming = e.connection

    # Salut looks up our capabilities
    event = q.expect('stream-iq', connection = incoming,
        query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        client + '#' + ver, (query_node.attributes['node'], client, ver)

    contact_handle = conn_contacts_iface.GetContactByID(contact_name, [])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = client + '#' + ver

    feature = query.addElement('feature')
    feature['var'] = ns.IQ_OOB
    incoming.send(result)

    # FT capa is announced
    e = q.expect('dbus-signal', signal='ContactCapabilitiesChanged',
            predicate=lambda e: contact_handle in e.args[0])
    caps = e.args[0][contact_handle]
    assertContains(ft_caps, caps)

    # check the Contacts interface give the same caps
    caps_via_contacts_iface = conn_contacts_iface.GetContactAttributes(
            [contact_handle], [cs.CONN_IFACE_CONTACT_CAPS], False) \
            [contact_handle][cs.CONN_IFACE_CONTACT_CAPS + '/capabilities']
    assert caps_via_contacts_iface == caps, caps_via_contacts_iface

    # check if Salut announces the OOB capa
    self_handle = conn.Properties.Get(cs.CONN, "SelfHandle")
    self_handle_name =  conn.Properties.Get(cs.CONN, "SelfID")

    AvahiListener(q).listen_for_service("_presence._tcp")
    e = q.expect('service-added', name = self_handle_name,
            protocol = avahi.PROTO_INET)
    service = e.service
    service.resolve()

    receive_presence_and_ask_caps(q, incoming, service, contact_name)

    # capa announced without FT
    ver = compute_caps_hash([], ["http://telepathy.freedesktop.org/xmpp/pony"], {})
    txt_record = { "txtvers": "1", "status": "avail",
        "node": client, "ver": ver, "hash": "sha-1"}
    contact_name = "test-caps-ft2@" + get_host_name()
    listener, port = setup_stream_listener(q, contact_name)
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
            txt_record)

    # this is the first presence, Salut connects to the contact
    e = q.expect('incoming-connection', listener = listener)
    incoming = e.connection

    # Salut looks up our capabilities
    event = q.expect('stream-iq', connection = incoming,
        query_ns='http://jabber.org/protocol/disco#info')
    query_node = xpath.queryForNodes('/iq/query', event.stanza)[0]
    assert query_node.attributes['node'] == \
        client + '#' + ver, (query_node.attributes['node'], client, ver)

    contact_handle = conn_contacts_iface.GetContactByID(contact_name, [])[0]

    # send good reply
    result = make_result_iq(event.stanza)
    query = result.firstChildElement()
    query['node'] = client + '#' + ver

    feature = query.addElement('feature')
    feature['var'] = "http://telepathy.freedesktop.org/xmpp/pony"
    incoming.send(result)

    # the FT capability is not announced
    e = q.expect('dbus-signal', signal='ContactCapabilitiesChanged')
    caps = e.args[0][contact_handle]
    assertDoesNotContain(ft_caps, caps)

    # check the Contacts interface give the same caps
    caps_via_contacts_iface = conn_contacts_iface.GetContactAttributes(
            [contact_handle], [cs.CONN_IFACE_CONTACT_CAPS], False) \
            [contact_handle][cs.CONN_IFACE_CONTACT_CAPS + '/capabilities']
    assert caps_via_contacts_iface == caps, caps_via_contacts_iface

    # no capabilites announced (assume FT is supported to insure interop)
    txt_record = { "txtvers": "1", "status": "avail"}
    contact_name = "test-caps-ft-no-capa2@" + get_host_name()
    contact_handle = conn_contacts_iface.GetContactByID(contact_name, [])[0]
    listener, port = setup_stream_listener(q, contact_name)
    announcer = AvahiAnnouncer(contact_name, "_presence._tcp", port,
            txt_record)

    # FT capa is announced
    e = q.expect('dbus-signal', signal='ContactCapabilitiesChanged',
            predicate=lambda e: contact_handle in e.args[0].keys())

    caps = e.args[0][contact_handle]
    assertContains(ft_caps, caps)

    # check the Contacts interface give the same caps
    caps_via_contacts_iface = conn_contacts_iface.GetContactAttributes(
            [contact_handle], [cs.CONN_IFACE_CONTACT_CAPS], False) \
            [contact_handle][cs.CONN_IFACE_CONTACT_CAPS + '/capabilities']
    assert caps_via_contacts_iface == caps, caps_via_contacts_iface
コード例 #35
0
def test(q, bus, conn):
    conn.Connect()
    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])


    activity_txt = { "type": "org.laptop.HelloMesh",
            "name": "HelloMesh",
            "color": "#7b83c1,#260993",
            "txtvers": "0",
            "activity-id": ACTIVITY_ID,
            "room": ACTIVITY_ID
          }

    # Listen for announcements
    l = AvahiListener(q).listen_for_service("_olpc-activity1._udp")

    # Assert that the testsuite doesn't announce the activity
    service_name = ACTIVITY_ID + ":" + TESTSUITE_PUBLISHED_NAME + "@" + get_host_name()
    forbiden_event = EventPattern('service-added', name=service_name)
    q.forbid_events([forbiden_event])

    contact_name = PUBLISHED_NAME + "@" + get_host_name()

    activity_name = ACTIVITY_ID + ":" + PUBLISHED_NAME + "@" + get_host_name()

    AvahiAnnouncer(contact_name, "_presence._tcp", 1234, {})

    act_hostname = ACTIVITY_ID + ":" + PUBLISHED_NAME + \
        "._clique._udp." + get_domain_name()
    act_address = "239.253.70.70"

    announce_address(act_hostname, act_address)

    # FIXME, if we use the same name as the running salut will MembersChanged
    # isn't signalled later on, needs to be fixed.
    AvahiAnnouncer(ACTIVITY_ID + ":" + PUBLISHED_NAME,
        "_clique._udp", 12345, {}, hostname = act_hostname)
    AvahiAnnouncer(activity_name, "_olpc-activity1._udp",
      0, activity_txt)

    # Publish a contact, now get it's handle
    handle = wait_for_contact_in_publish(q, bus, conn, contact_name)

    # Assert that the remote handles signals it joined the activity
    while True:
      e = q.expect('dbus-signal', signal = 'ActivitiesChanged')
      if e.args[0] == handle and e.args[1] != []:
          assert len(e.args[1]) == 1
          assert e.args[1][0][0] == ACTIVITY_ID
          activity_handle = e.args[1][0][1]
          break

    act_prop_iface = dbus.Interface(conn, cs.ACTIVITY_PROPERTIES)
    act_properties = act_prop_iface.GetProperties(activity_handle)
    assert act_properties['private'] == False
    assert act_properties['color'] == activity_txt['color']
    assert act_properties['name'] == activity_txt['name']
    assert act_properties['type'] == activity_txt['type']

    room_channel = conn.RequestChannel(CHANNEL_TYPE_TEXT,
        HT_ROOM, activity_handle, True)

    q.expect('dbus-signal', signal='MembersChanged', path=room_channel,
        args = [u'', [1L], [], [], [], 1L, 0L])

    # Make it public that we joined the activity
    q.unforbid_events([forbiden_event])
    buddy_info_iface = dbus.Interface(conn, cs.BUDDY_INFO)
    buddy_info_iface.SetActivities([(ACTIVITY_ID, activity_handle)])

    q.expect('service-added',
        name = ACTIVITY_ID + ":" + TESTSUITE_PUBLISHED_NAME +
            "@" + get_host_name())

    buddy_info_iface.SetActivities([])

    q.expect('service-removed',
        name = ACTIVITY_ID + ":" + TESTSUITE_PUBLISHED_NAME +
            "@" + get_host_name())
コード例 #36
0
def test(q, bus, conn):
    self_name = 'testsuite' + '@' + avahitest.get_host_name()

    conn.Connect()

    q.expect('dbus-signal', signal='StatusChanged', args=[0L, 0L])

    # FIXME: this is a hack to be sure to have all the contact list channels
    # announced so they won't interfere with the roomlist ones announces.
    wait_for_contact_list(q, conn)

    # check if we can request roomlist channels
    properties = conn.GetAll(tp_name_prefix + '.Connection.Interface.Requests',
                             dbus_interface='org.freedesktop.DBus.Properties')
    assert ({tp_name_prefix + '.Channel.ChannelType':
                cs.CHANNEL_TYPE_ROOM_LIST,
             tp_name_prefix + '.Channel.TargetHandleType': 0,
             },
             [],
             ) in properties.get('RequestableChannelClasses'),\
                     properties['RequestableChannelClasses']

    requestotron = dbus.Interface(
        conn, tp_name_prefix + '.Connection.Interface.Requests')

    # create roomlist channel using new API
    call_async(
        q, requestotron, 'CreateChannel', {
            tp_name_prefix + '.Channel.ChannelType': cs.CHANNEL_TYPE_ROOM_LIST,
            tp_name_prefix + '.Channel.TargetHandleType': 0,
        })

    ret, new_sig = q.expect_many(
        EventPattern('dbus-return', method='CreateChannel'),
        EventPattern('dbus-signal', signal='NewChannels'),
    )
    path2 = ret.value[0]
    chan2 = wrap_channel(bus.get_object(conn.bus_name, path2), "RoomList")

    props = ret.value[1]
    assert props[tp_name_prefix + '.Channel.ChannelType'] ==\
            cs.CHANNEL_TYPE_ROOM_LIST
    assert props[tp_name_prefix + '.Channel.TargetHandleType'] == 0
    assert props[tp_name_prefix + '.Channel.TargetHandle'] == 0
    assert props[tp_name_prefix + '.Channel.TargetID'] == ''
    assert props[tp_name_prefix + '.Channel.Requested'] == True
    assert props[tp_name_prefix + '.Channel.InitiatorHandle'] \
            == conn.Properties.Get(cs.CONN, "SelfHandle")
    assert props[tp_name_prefix + '.Channel.InitiatorID'] \
            == self_name
    assert props[tp_name_prefix + '.Channel.Type.RoomList.Server'] == ''

    assert new_sig.args[0][0][0] == path2
    assert new_sig.args[0][0][1] == props

    assert chan2.Properties.Get(cs.CHANNEL_TYPE_ROOM_LIST, 'Server') == ''

    # ensure roomlist channel
    yours, ensured_path, ensured_props = requestotron.EnsureChannel({
        tp_name_prefix + '.Channel.ChannelType':
        cs.CHANNEL_TYPE_ROOM_LIST,
        tp_name_prefix + '.Channel.TargetHandleType':
        0,
    })

    assert not yours
    assert ensured_path == path2, (ensured_path, path2)

    # Closing roomlist channels crashed Salut for a while.
    chan2.Close()
    q.expect_many(
        EventPattern('dbus-signal', signal='Closed', path=path2),
        EventPattern('dbus-signal', signal='ChannelClosed', args=[path2]),
    )

    conn.Disconnect()

    q.expect_many(
        EventPattern('dbus-signal', signal='StatusChanged', args=[2, 1]), )