Exemplo n.º 1
0
    def test_record_twice(self):
        conference_id = CONFERENCE1_ID
        self.confd.set_conferences(
            MockConference(id=conference_id, name='conference'), )
        self.given_call_in_conference(CONFERENCE1_EXTENSION,
                                      caller_id_name='participant1')

        # record twice
        self.calld_client.conferences.record(conference_id)
        assert_that(
            calling(
                self.calld_client.conferences.record).with_args(conference_id),
            raises(CalldError).matching(
                has_properties({
                    'status_code': 400,
                    'error_id': 'conference-already-recorded',
                })))

        # stop record twice
        self.calld_client.conferences.stop_record(conference_id)
        assert_that(
            calling(self.calld_client.conferences.stop_record).with_args(
                conference_id),
            raises(CalldError).matching(
                has_properties({
                    'status_code': 400,
                    'error_id': 'conference-not-recorded',
                })))
    def test_multi_tenant(self):
        main_tenant_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_tenant_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        with self.source(main_tenant_client, self.valid_body) as result:
            assert_that(result,
                        has_entries(uuid=uuid_(), tenant_uuid=MAIN_TENANT))

        with self.source(main_tenant_client,
                         self.valid_body,
                         tenant_uuid=SUB_TENANT) as result:
            assert_that(result,
                        has_entries(uuid=uuid_(), tenant_uuid=SUB_TENANT))

        with self.source(sub_tenant_client, self.valid_body) as result:
            assert_that(result,
                        has_entries(uuid=uuid_(), tenant_uuid=SUB_TENANT))

        assert_that(
            calling(sub_tenant_client.phonebook_source.create).with_args(
                self.valid_body, tenant_uuid=MAIN_TENANT),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=401))),
        )

        with self.source(main_tenant_client, self.valid_body):
            assert_that(
                calling(sub_tenant_client.phonebook_source.create).with_args(
                    self.valid_body),
                not_(raises(Exception)),
            )
Exemplo n.º 3
0
    def test_put_multi_tenant(self, sub, main):
        main_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        assert_that(
            calling(self.edit).with_args(sub_client, main['uuid'], sub),
            not_(raises(Exception).matching(HTTP_409)),
        )

        assert_that(
            calling(self.edit).with_args(sub_client, main['uuid'],
                                         self.new_body),
            raises(Exception).matching(HTTP_404),
        )

        assert_that(
            calling(self.edit).with_args(main_client,
                                         main['uuid'],
                                         self.new_body,
                                         tenant_uuid=SUB_TENANT),
            raises(Exception).matching(HTTP_404),
        )

        assert_that(
            calling(self.edit).with_args(main_client, sub['uuid'],
                                         self.new_body),
            not_(raises(Exception)),
        )
Exemplo n.º 4
0
    def test_multi_tenant(self):
        main_tenant_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_tenant_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        with self.source(main_tenant_client, self.valid_body) as result:
            assert_that(result,
                        has_entries(uuid=uuid_(), tenant_uuid=MAIN_TENANT))

        with self.source(main_tenant_client,
                         self.valid_body,
                         tenant_uuid=SUB_TENANT) as result:
            assert_that(result,
                        has_entries(uuid=uuid_(), tenant_uuid=SUB_TENANT))

        with self.source(sub_tenant_client, self.valid_body) as result:
            assert_that(result,
                        has_entries(uuid=uuid_(), tenant_uuid=SUB_TENANT))

        assert_that(
            calling(sub_tenant_client.backends.create_source).with_args(
                'google', self.valid_body, tenant_uuid=MAIN_TENANT),
            raises(Exception).matching(HTTP_401),
        )

        with self.source(main_tenant_client, self.valid_body):
            assert_that(
                calling(sub_tenant_client.backends.create_source).with_args(
                    'google', self.valid_body),
                not_(raises(Exception)),
            )
    def test_put_multi_tenant(self, sub, main):
        main_tenant_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_tenant_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        assert_that(
            calling(sub_tenant_client.phonebook_source.edit).with_args(
                main['uuid'], sub),
            not_(
                raises(Exception).matching(
                    has_properties(response=has_properties(status_code=409)))),
        )

        try:
            sub_tenant_client.phonebook_source.edit(main['uuid'],
                                                    self.new_body)
        except Exception as e:
            self.assert_unknown_source_exception(main['uuid'], e)
        else:
            self.fail('Should have raised')

        assert_that(
            calling(main_tenant_client.phonebook_source.edit).with_args(
                sub['uuid'], self.new_body),
            not_(raises(Exception)),
        )
Exemplo n.º 6
0
    def test_that_two_policies_cannot_have_the_same_slug_and_tenant(
            self, tenant_uuid, policy_uuid):
        # Same slug different tenants no exception
        assert_that(
            calling(self.create_and_delete_policy).with_args(
                'foobar', slug='foobar', tenant_uuid=tenant_uuid),
            not_(raises(exceptions.DuplicatePolicyException)),
        )

        # Same tenant different slug no exception
        assert_that(
            calling(self.create_and_delete_policy).with_args('foobaz',
                                                             slug='foobaz'),
            not_(raises(exceptions.DuplicatePolicyException)),
        )

        # Same name same tenant
        assert_that(
            calling(self.create_and_delete_policy).with_args('foobar',
                                                             slug='foobar'),
            raises(exceptions.DuplicatePolicyException),
        )

        # Same name case insensitive same tenant
        assert_that(
            calling(self.create_and_delete_policy).with_args('fooBAR',
                                                             slug='fooBAR'),
            raises(exceptions.DuplicatePolicyException),
        )
Exemplo n.º 7
0
    def test_main_field(self):
        params = {'emails': [ONE, FIVE]}
        assert_that(
            calling(self.user_schema.load).with_args(params),
            raises(
                ValidationError,
                has_property(
                    "messages",
                    has_entries(_schema=contains_exactly(
                        'Only one address should be main')),
                ),
            ),
        )

        params = {'emails': [TWO]}
        assert_that(
            calling(self.user_schema.load).with_args(params),
            raises(
                ValidationError,
                has_property(
                    "messages",
                    has_entries(_schema=contains_exactly(
                        'At least one address should be main')),
                ),
            ),
        )
Exemplo n.º 8
0
    def test_user_policy_association(self, user_uuid, policy_uuid):
        self._user_dao.add_policy(user_uuid, policy_uuid)
        count = (self.session.query(func.count(
            models.UserPolicy.user_uuid)).filter(
                and_(
                    models.UserPolicy.user_uuid == user_uuid,
                    models.UserPolicy.policy_uuid == policy_uuid,
                )).scalar())

        assert_that(count, equal_to(1))

        assert_that(
            calling(self._user_dao.add_policy).with_args(
                user_uuid, policy_uuid),
            not_(raises(Exception)),
            'associating twice should not fail',
        )

        assert_that(
            calling(self._user_dao.add_policy).with_args(
                'unknown', policy_uuid),
            raises(exceptions.UnknownUserException),
            'unknown user',
        )

        assert_that(
            calling(self._user_dao.add_policy).with_args(user_uuid, 'unknown'),
            raises(exceptions.UnknownPolicyException),
            'unknown policy',
        )
Exemplo n.º 9
0
    def test_multi_tenant(self):
        main_tenant_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_tenant_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        assert_that(
            calling(self.contacts).with_args(sub_tenant_client,
                                             self.source_uuid),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=404))),
        )

        assert_that(
            calling(self.contacts).with_args(sub_tenant_client,
                                             self.source_uuid,
                                             tenant_uuid=MAIN_TENANT),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=401))),
        )

        assert_that(
            calling(self.contacts).with_args(main_tenant_client,
                                             self.source_uuid,
                                             tenant_uuid=SUB_TENANT),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=404))),
        )
Exemplo n.º 10
0
    def test_mute_participant_with_no_amid(self):
        conference_id = CONFERENCE1_ID
        self.confd.set_conferences(
            MockConference(id=conference_id, name='conference'), )
        self.given_call_in_conference(CONFERENCE1_EXTENSION,
                                      caller_id_name='participant1')
        participants = self.calld_client.conferences.list_participants(
            conference_id)
        participant = participants['items'][0]

        with self.amid_stopped():
            assert_that(
                calling(
                    self.calld_client.conferences.mute_participant).with_args(
                        conference_id, participant['id']),
                raises(CalldError).matching(
                    has_properties({
                        'status_code': 503,
                        'error_id': 'wazo-amid-error',
                    })))
            assert_that(
                calling(self.calld_client.conferences.unmute_participant).
                with_args(conference_id, participant['id']),
                raises(CalldError).matching(
                    has_properties({
                        'status_code': 503,
                        'error_id': 'wazo-amid-error',
                    })))
Exemplo n.º 11
0
    def test_get_multi_tenant(self, sub, main):
        main_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        response = main_client.backends.get_source(BACKEND, sub['uuid'])
        assert_that(response, equal_to(sub))

        assert_that(
            calling(main_client.backends.get_source).with_args(
                BACKEND, main['uuid'], tenant_uuid=SUB_TENANT
            ),
            raises(Exception).matching(HTTP_404),
        )

        assert_that(
            calling(sub_client.backends.get_source).with_args(BACKEND, main['uuid']),
            raises(Exception).matching(HTTP_404),
        )

        assert_that(
            calling(sub_client.backends.get_source).with_args(
                BACKEND, main['uuid'], tenant_uuid=MAIN_TENANT
            ),
            raises(Exception).matching(HTTP_401),
        )
Exemplo n.º 12
0
    def test_delete_multi_tenant(self, sub, main):
        main_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        assert_that(
            calling(sub_client.backends.delete_source).with_args(BACKEND, main['uuid']),
            raises(Exception).matching(HTTP_404),
        )

        assert_that(
            calling(sub_client.backends.delete_source).with_args(
                BACKEND, main['uuid'], tenant_uuid=MAIN_TENANT
            ),
            raises(Exception).matching(HTTP_401),
        )

        assert_that(
            calling(main_client.backends.delete_source).with_args(
                BACKEND, main['uuid'], tenant_uuid=SUB_TENANT
            ),
            raises(Exception).matching(HTTP_404),
        )

        assert_that(
            calling(main_client.backends.delete_source).with_args(BACKEND, sub['uuid']),
            not_(raises(Exception)),
        )
    def test_api_return_503(self, user):
        user_args = {'uuid': str(user.uuid), 'state': 'available'}
        self.stop_chatd_service()
        self.stop_amid_service()
        self.start_chatd_service()
        RestApiOkWaitStrategy().wait(self)

        assert_that(
            calling(self.chatd.user_presences.list),
            raises(ChatdError,
                   has_properties(error_id='not-initialized',
                                  status_code=503)),
        )

        assert_that(
            calling(self.chatd.user_presences.get).with_args(
                user_args['uuid']),
            raises(ChatdError,
                   has_properties(error_id='not-initialized',
                                  status_code=503)),
        )

        assert_that(
            calling(self.chatd.user_presences.update).with_args(user_args),
            raises(ChatdError,
                   has_properties(error_id='not-initialized',
                                  status_code=503)),
        )

        self.start_amid_service()
        PresenceInitOkWaitStrategy().wait(self)
        self.chatd.user_presences.list()
Exemplo n.º 14
0
    def test_login_pause_unpause_logoff_user_agent_without_user(
            self, user_line_extension):
        self.create_user_token(UNKNOWN_UUID)

        # get
        assert_that(
            calling(self.agentd.agents.get_user_agent_status),
            raises(AgentdClientError, has_properties(error=NO_SUCH_AGENT)),
        )

        # login
        assert_that(
            calling(self.agentd.agents.login_user_agent).with_args(
                user_line_extension['line_id']),
            raises(AgentdClientError, has_properties(error=NO_SUCH_AGENT)),
        )

        # pause
        assert_that(
            calling(self.agentd.agents.pause_user_agent),
            raises(AgentdClientError, has_properties(error=NO_SUCH_AGENT)),
        )

        # unpause
        assert_that(
            calling(self.agentd.agents.unpause_user_agent),
            raises(AgentdClientError, has_properties(error=NO_SUCH_AGENT)),
        )

        # logoff
        assert_that(
            calling(self.agentd.agents.logoff_user_agent),
            raises(AgentdClientError, has_properties(error=NO_SUCH_AGENT)),
        )
Exemplo n.º 15
0
    def test_address_field(self):
        params = {'emails': [ONE, SIX]}
        assert_that(
            calling(self.user_schema.load).with_args(params),
            raises(
                ValidationError,
                has_property(
                    "messages",
                    has_entries(emails=has_entry(1, has_key('address')))),
            ),
        )

        params = {'emails': [ONE, TWO, TWO]}
        assert_that(
            calling(self.user_schema.load).with_args(params),
            raises(
                ValidationError,
                has_property(
                    "messages",
                    has_entries(_schema=contains_exactly(
                        'The same address can only be used once')),
                ),
            ),
        )

        params = {}
        assert_that(
            calling(self.user_schema.load).with_args(params),
            raises(ValidationError, has_property("messages",
                                                 has_key('emails'))),
        )
Exemplo n.º 16
0
    def test_multi_tenant(self, sub, main):
        main_tenant_client = self.get_client(VALID_TOKEN_MAIN_TENANT)
        sub_tenant_client = self.get_client(VALID_TOKEN_SUB_TENANT)

        assert_that(
            calling(sub_tenant_client.displays.delete).with_args(main['uuid']),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=404))
            ),
        )

        assert_that(
            calling(main_tenant_client.displays.delete).with_args(
                main['uuid'], tenant_uuid=SUB_TENANT
            ),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=404))
            ),
        )

        assert_that(
            calling(sub_tenant_client.displays.delete).with_args(
                main['uuid'], tenant_uuid=MAIN_TENANT
            ),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=401))
            ),
        )

        assert_that(
            calling(main_tenant_client.displays.delete).with_args(sub['uuid']),
            not_(raises(Exception)),
        )
Exemplo n.º 17
0
    def test_mobile_workflow(self, tenant, user, token):
        self.client.tenant_uuid = tenant['uuid']
        self.client.external.create_config(auth_type=self.EXTERNAL_AUTH_TYPE,
                                           data=self.SECRET)

        response = self.client.external.get_config(self.EXTERNAL_AUTH_TYPE)
        assert_that(response, has_entries(self.SECRET))

        self.client.set_token(token['token'])

        assert_that(
            calling(self.client.external.get).with_args(
                self.EXTERNAL_AUTH_TYPE, user['uuid']),
            raises(requests.HTTPError).matching(
                has_property('response', has_properties(status_code=404))),
        )

        response = self.client.external.create(
            self.EXTERNAL_AUTH_TYPE,
            user['uuid'],
            {
                'token': 'TOKEN',
                'apns_token': 'APNS_VOIP_TOKEN',
                'apns_voip_token': 'APNS_VOIP_TOKEN',
                'apns_notification_token': 'APNS_NOTIFICATION_TOKEN',
            },
        )
        assert_that(
            response,
            has_entries(
                token='TOKEN',
                apns_token='APNS_VOIP_TOKEN',
                apns_voip_token='APNS_VOIP_TOKEN',
                apns_notification_token='APNS_NOTIFICATION_TOKEN',
            ),
        )
        response = self.client.external.get(self.EXTERNAL_AUTH_TYPE,
                                            user['uuid'])
        assert_that(
            response,
            has_entries(
                token='TOKEN',
                apns_token='APNS_VOIP_TOKEN',
                apns_voip_token='APNS_VOIP_TOKEN',
                apns_notification_token='APNS_NOTIFICATION_TOKEN',
            ),
        )

        response = self.get_sender_id(user)
        assert_that(response, has_entry('sender_id', 'fcm_sender_id'))

        self.client.external.delete(self.EXTERNAL_AUTH_TYPE, user['uuid'])
        assert_that(
            calling(self.client.external.get).with_args(
                self.EXTERNAL_AUTH_TYPE, user['uuid']),
            raises(requests.HTTPError).matching(
                has_property('response', has_properties(status_code=404))),
        )
Exemplo n.º 18
0
 def test_get_raw_error_invalid_token(self):
     provd = self.make_provd('invalid-token')
     with fixtures.Configuration(self._client) as config:
         assert_that(
             calling(provd.configs.get_raw).with_args(config['id']),
             raises(ProvdError).matching(has_properties('status_code',
                                                        401)))
     assert_that(
         calling(provd.configs.get_raw).with_args('invalid_id'),
         raises(ProvdError).matching(has_properties('status_code', 401)))
Exemplo n.º 19
0
 def test_add_errors(self):
     assert_that(
         calling(self._add_device).with_args('10.0.1.xx',
                                             '00:11:22:33:44:55'),
         raises(ProvdError).matching(has_properties('status_code', 400)))
     assert_that(
         calling(self._add_device).with_args('10.0.1.1',
                                             '00:11:22:33:44:55',
                                             id_='*&!"/invalid _'),
         raises(ProvdError).matching(has_properties('status_code', 400)))
Exemplo n.º 20
0
 def test_reconfigure_error_invalid_token(self):
     provd = self.make_provd(INVALID_TOKEN)
     with fixtures.Device(self._client) as device:
         assert_that(
             calling(provd.devices.reconfigure).with_args(device['id']),
             raises(ProvdError).matching(has_properties('status_code',
                                                        401)))
     assert_that(
         calling(provd.devices.reconfigure).with_args('unknown_id'),
         raises(ProvdError).matching(has_properties('status_code', 401)))
Exemplo n.º 21
0
    def test_put(self, foobar, other):
        assert_that(
            calling(self.client.backends.edit_source).with_args(
                BACKEND, foobar['uuid'], other
            ),
            raises(Exception).matching(HTTP_409),
        )

        assert_that(
            calling(self.client.backends.edit_source).with_args(
                BACKEND, UNKNOWN_UUID, self.new_body
            ),
            raises(Exception).matching(HTTP_404),
        )

        try:
            self.client.backends.edit_source(BACKEND, foobar['uuid'], {})
        except Exception as e:
            assert_that(e.response.status_code, equal_to(400))
            assert_that(
                e.response.json(),
                has_entries(
                    message=ANY,
                    error_id='invalid-data',
                    details=ANY,
                ),
            )
        else:
            self.fail('Should have raised')

        assert_that(
            calling(self.client.backends.edit_source).with_args(
                BACKEND, foobar['uuid'], self.new_body
            ),
            not_(raises(Exception)),
        )

        result = self.client.backends.get_source(BACKEND, foobar['uuid'])
        assert_that(
            result,
            has_entries(
                uuid=foobar['uuid'],
                tenant_uuid=foobar['tenant_uuid'],
                name='new',
                searched_columns=[
                    'givenName',
                    'surname',
                    'mobilePhone',
                    'businessPhones',
                ],
                first_matched_columns=['mobilePhone'],
                format_columns={'name': '{givenName} {surname}'},
            ),
        )
Exemplo n.º 22
0
 def test_delete(self, source):
     assert_that(
         calling(self.client.backends.delete_source).with_args(
             'google', source['uuid']),
         not_(raises(Exception)),
     )
     assert_that(
         calling(self.client.backends.get_source).with_args(
             'google', source['uuid']),
         raises(Exception).matching(HTTP_404),
     )
Exemplo n.º 23
0
 def test_get_packages_installed_error_invalid_token(self):
     provd = self.make_provd('invalid-token')
     with fixtures.Plugin(self._client):
         assert_that(
             calling(provd.plugins.get_packages_installed).with_args(PLUGIN_TO_INSTALL),
             raises(ProvdError).matching(has_properties('status_code', 401))
         )
     assert_that(
         calling(provd.plugins.get_packages_installed).with_args('unknown_id'),
         raises(ProvdError).matching(has_properties('status_code', 404))  # should be 401
     )
Exemplo n.º 24
0
    def test_invalid_field(self):
        query_string = {'username': 300 * 'a'}
        assert_that(
            calling(self.password_query_parameters_schema.load).with_args(query_string),
            raises(ValidationError, has_property("messages", not_(equal_to(None)))),
        )

        query_string = {'email': 'patate'}
        assert_that(
            calling(self.password_query_parameters_schema.load).with_args(query_string),
            raises(ValidationError, has_property("messages", not_(equal_to(None)))),
        )
Exemplo n.º 25
0
    def test_that_a_refresh_token_requires_a_client_id(self):
        body = {'refresh_token': 'the-token'}

        assert_that(
            calling(self.schema.load).with_args({'client_id': 'x', **body}),
            not_(raises(Exception)),
        )

        assert_that(
            calling(self.schema.load).with_args(body),
            raises(ValidationError).matching(has_properties(field_name='_schema')),
        )
Exemplo n.º 26
0
    def test_restrict_only_master_tenant(self):
        user_uuid = str(uuid.uuid4())
        calld = self.make_user_calld(user_uuid)
        assert_that(
            calling(calld.config.get),
            raises(CalldError, has_properties(status_code=401)),
        )

        assert_that(
            calling(calld.config.patch).with_args({}),
            raises(CalldError, has_properties(status_code=401)),
        )
Exemplo n.º 27
0
    def test_delete(self, display):
        assert_that(
            calling(self.client.displays.delete).with_args(display['uuid']),
            not_(raises(Exception)),
        )

        assert_that(
            calling(self.client.displays.delete).with_args(display['uuid']),
            raises(Exception).matching(
                has_properties(response=has_properties(status_code=404))
            ),
        )
Exemplo n.º 28
0
    def test_delete(self, uuid):
        assert_that(
            calling(self._policy_dao.delete).with_args(uuid,
                                                       [self.top_tenant_uuid]),
            not_(raises(Exception)),
        )

        assert_that(
            calling(self._policy_dao.delete).with_args(UNKNOWN_UUID,
                                                       [self.top_tenant_uuid]),
            raises(exceptions.UnknownPolicyException),
        )
Exemplo n.º 29
0
    def test_restrict_only_master_tenant(self):
        with self.set_token(TOKEN_SUB_TENANT):
            assert_that(
                calling(self.call_logd.config.get),
                raises(CallLogdError, has_properties(status_code=401)),
            )

        with self.set_token(TOKEN_SUB_TENANT):
            assert_that(
                calling(self.call_logd.config.patch).with_args({}),
                raises(CallLogdError, has_properties(status_code=401)),
            )
Exemplo n.º 30
0
    def test_put_record_stop_from_user(self):
        user_uuid = str(uuid.uuid4())
        token = self.given_user_token(user_uuid)
        self.calld_client.set_token(token)
        channel_id = self.given_call_not_stasis(user_uuid=user_uuid)
        other_channel_id = self.given_call_not_stasis()

        assert_that(
            calling(self.calld_client.calls.stop_record_from_user).with_args(UNKNOWN_UUID),
            raises(CalldError).matching(has_properties(status_code=404))
        )
        assert_that(
            calling(self.calld_client.calls.stop_record_from_user).with_args(other_channel_id),
            raises(CalldError).matching(has_properties(status_code=403))
        )

        routing_key = 'calls.*.updated'
        event_accumulator = self.bus.accumulator(routing_key)

        self.calld_client.calls.stop_record_from_user(channel_id)

        def event_received():
            assert_that(
                event_accumulator.accumulate(with_headers=True),
                has_items(
                    has_entries(
                        message=has_entries(
                            name='call_updated',
                            data=has_entries(
                                call_id=channel_id,
                                record_state='inactive'
                            )
                        ),
                        headers=has_entries(
                            name='call_updated',
                            tenant_uuid=VALID_TENANT,
                        )
                    )
                )
            )

        until.assert_(event_received, tries=10)

        assert_that(
            self.calld_client.calls.list_calls_from_user()['items'],
            has_items(has_entries(call_id=channel_id, record_state='inactive'))
        )

        # Should not raise an error on second record stop
        assert_that(
            calling(self.calld_client.calls.stop_record_from_user).with_args(channel_id),
            not_(raises(CalldError))
        )