Exemple #1
0
def test_list_applications_under_team(client, zk, test_token, fake_team,
                                      minimal_mode, present, expected):
    for name in present:
        if minimal_mode:
            zk.ensure_path('/huskar/config/%s' % name)
            sleep(0.1)
        else:
            Application.create(name, fake_team.id)

    if minimal_mode:
        r = client.get('/api/team/%s+1s' % Team.DEFAULT_NAME,
                       headers={'Authorization': test_token})
        assert r.status_code == 404
        assert r.json['status'] == 'NotFound'

        r = client.get('/api/team/%s' % Team.DEFAULT_NAME,
                       headers={'Authorization': test_token})
        assert_response_ok(r)
        assert set(expected).issubset(r.json['data'])
    else:
        r = client.get('/api/team/%s+1s' % fake_team.team_name,
                       headers={'Authorization': test_token})
        assert r.status_code == 404
        assert r.json['status'] == 'NotFound'

        r = client.get('/api/team/%s' % fake_team.team_name,
                       headers={'Authorization': test_token})
        assert_response_ok(r)
        assert r.json['data'] == expected
Exemple #2
0
    def _create(self, ignore_existed=False):
        team_name = request.values['team'].strip()
        application_name = request.values['application'].strip()
        validate_fields(application_schema,
                        {'name': application_name, 'team_name': team_name})

        team = Team.get_by_name(team_name)
        if team is None:
            abort(400, 'team "%s" does not exist' % team_name)

        require_team_admin_or_site_admin(team)

        application = Application.get_by_name(application_name)
        if application is not None:
            if ignore_existed:
                return api_response()
            raise ApplicationExistedError(
                'application: {} has existed, application is globally '
                'unique'.format(application))

        try:
            application = Application.create(application_name, team.id)
        except NameOccupiedError:
            abort(400, 'The application name {0} has been occupied.'.format(
                application_name))
        audit_log.emit(
            audit_log.types.CREATE_APPLICATION, application=application,
            team=team)
        return api_response()
Exemple #3
0
def test_set_route_failed_dest_linked_empty_cluster(client, zk, test_team,
                                                    test_application,
                                                    test_application_token,
                                                    exist):
    dest_application_name = '%s_dest' % test_application.application_name
    Application.create(dest_application_name, test_team.id)
    test_application_name = test_application.application_name
    cluster_name = 'stable'
    dest_cluster_name = 'channel-stable-1'
    physical_cluster = 'foo.bar'
    path = '/huskar/service/%s/%s' % (dest_application_name, dest_cluster_name)
    data = json.dumps({'link': [physical_cluster]})
    zk.create(path, data, makepath=True)
    zk.ensure_path('/huskar/service/%s/%s' %
                   (test_application_name, cluster_name))
    if exist:
        zk.ensure_path('/huskar/service/%s/%s' %
                       (dest_application_name, physical_cluster))

    url = '/api/serviceroute/%s/%s/%s' % (test_application_name, cluster_name,
                                          dest_application_name)
    r = client.put(url,
                   data={
                       'cluster_name': dest_cluster_name,
                       'intent': 'direct'
                   },
                   headers={'Authorization': test_application_token})
    assert r.status_code == 400, r.data
    assert r.json['status'] == 'BadRequest'
    assert r.json['message'] == \
        'The target cluster %s is empty.' % dest_cluster_name
def test_create_application(db, zk, test_team, faker):
    application_name = faker.uuid4()[:8]
    stat = zk.exists('/huskar/service/%s' % application_name)
    assert stat is None

    application = Application.create(application_name, test_team.id)
    assert zk.exists('/huskar/service/%s' % application_name)

    assert application.id > 0
    assert application.application_name == application_name
    assert application.domain_name == application_name
    assert application.team_id == test_team.id
    assert application.team.team_name == test_team.team_name

    user = User.get_by_name(application_name)
    assert user is not None
    assert user.is_application
    assert not user.is_admin
    assert application.check_auth(Authority.WRITE, user.id)
    assert application.check_auth(Authority.READ, user.id)

    with raises(NameOccupiedError):
        Application.create(application_name, test_team.id)  # name conflicts

    application = Application.create('baz', test_team.id)
    assert application.application_name == 'baz'
def test_application_transfer_team(db, test_application, faker):
    orig_team_id = test_application.team_id
    dest_team = Team.create(faker.name())
    test_application.transfer_team(dest_team.id)
    application = Application.get_by_name(test_application.application_name)
    assert application.team_id == dest_team.id
    assert test_application.id not in Application.get_ids_by_team(orig_team_id)
    assert test_application.id in Application.get_ids_by_team(dest_team.id)
def test_get_application_by_name(db, test_application):
    application = Application.get_by_name(test_application.application_name)
    assert application is test_application
    assert application.domain_name == 'foo'

    application = Application.get_by_name(test_application.application_name +
                                          '1s')
    assert application is None
Exemple #7
0
def test_delete_route_noauth(client, zk, test_application, test_team,
                             test_token):
    Application.create('base.foo', test_team.id)
    url = '/api/serviceroute/%s/stable/base.foo' % (
        test_application.application_name)
    r = client.delete(url, headers={'Authorization': test_token})
    assert r.status_code == 400, r.data
    assert r.json['status'] == 'NoAuthError'
Exemple #8
0
def test_set_route_noauth(client, zk, test_application, test_team, test_token):
    Application.create('base.foo', test_team.id)
    url = '/api/serviceroute/%s/stable/base.foo' % (
        test_application.application_name)
    r = client.put(url,
                   data={'cluster_name': 'channel-stable-1'},
                   headers={'Authorization': test_token})
    assert r.status_code == 400, r.data
    assert r.json['status'] == 'NoAuthError'
def destroy_application(name):
    application = Application.get_by_name(name)
    if application is not None:
        Application.delete(application.id)
        logger.info('Removed application from DBMS: %s', name)

    for type_name in (SERVICE_SUBDOMAIN, SWITCH_SUBDOMAIN, CONFIG_SUBDOMAIN):
        path = '/huskar/%s/%s' % (type_name, name)
        if huskar_client.client.exists(path):
            huskar_client.client.delete(path, recursive=True)
            logger.info('Removed application from ZooKeeper: %s', path)
Exemple #10
0
def test_table_cache_expiration(faker, monkeypatch, db, test_team, ttl,
                                result_expected):
    monkeypatch.setattr(Application, 'TABLE_CACHE_EXPIRATION_TIME', ttl)
    application_name = faker.uuid4()[:8]
    application = Application.create(application_name, test_team.id)
    assert application

    cache_client = Application._cache_client
    raw_key = Application.gen_raw_key(application.id)
    key = cache_client._keygen(raw_key)
    assert int(cache_client.client.ttl(key)) == result_expected
Exemple #11
0
def test_unarchive_application(db, test_user, test_team, test_application,
                               test_application_auth):
    test_application.archive()
    assert Application.get_by_name(test_application.application_name) is None
    test_application.unarchive()
    assert Application.get_by_name(
        test_application.application_name) is not None

    test_application.archive()
    test_team.archive()
    test_application.unarchive()
    assert Application.get_by_name(test_application.application_name) is None
Exemple #12
0
def test_set_route_badintent(client, zk, test_team, test_application,
                             test_application_token):
    Application.create('base.foo', test_team.id)
    url = '/api/serviceroute/%s/stable/base.foo' % (
        test_application.application_name)
    r = client.put(url,
                   data={
                       'cluster_name': 'channel-stable-1',
                       'intent': 'freestyle'
                   },
                   headers={'Authorization': test_application_token})
    assert r.status_code == 400, r.data
    assert r.json['status'] == 'BadRequest'
    assert r.json['message'] == 'intent must be one of direct'
Exemple #13
0
    def put(self, webhook_id):
        """To update subscription settings of an application

        Request body schema same to ``POST`` method.

        :param application_name: The name of application.
        :param webhook_id: The id of webhook.
        :param webhoo_type: default 0, set universal with 1
        :status 200: thr request is successful.
        :status 404: The application or webhoook not found.
        """
        webhook = self._get_webhook_or_404(webhook_id)
        self._check_authority(webhook)

        data = request.get_json() or {}
        validate_fields(webhook_schema, data, partial=False)
        if not webhook.is_normal:
            webhook.update_url(data['webhook_url'])
            return api_response()

        application_name = request.args['application_name']
        application = Application.get_by_name(application_name)
        webhook.batch_unsubscribe(application.id)
        webhook.update_url(data['webhook_url'])
        for action_name in data.get('event_list', []):
            action_type = getattr(action_types, action_name)
            webhook.subscribe(application.id, action_type)
        return api_response()
Exemple #14
0
    def get(self, application_name, cluster_name, key):
        """Get the audit logs of specified instance key.

        :param application_name: The name of application.
        :param cluster_name: The name of clsuter.
        :param key: The key of instance.
        :query date: The date specified to search, default is today.
        :query start: The offset of pagination. Default is ``0``.
        :>header Authorization: Huskar Token (See :ref:`token`)
        :status 403: You don't have required authority.
        :status 501: The server is in minimal mode.
        :status 200: The result is in the response.
                     (See :ref:`Audit Log Schema <audit_schema>`)
        """
        check_application(application_name)
        check_cluster_name(cluster_name, application_name)

        start = request.args.get('start', type=int, default=0)
        application = Application.get_by_name(application_name)
        can_view_sensitive_data = AuditLog.can_view_sensitive_data(
            g.auth.id, self.instance_type, application.id)
        items = AuditLog.get_multi_by_instance_index(self.instance_type,
                                                     application.id,
                                                     cluster_name, key)
        items = items[start:start + 20]
        if not can_view_sensitive_data:
            items = [item.desensitize() for item in items]
        return api_response(audit_log_schema.dump(items, many=True).data)
Exemple #15
0
def test_get_team_application_token_with_unknown_application(
        client, db, test_team, admin_user, admin_token, application_name):
    application = Application.get_by_name(application_name)
    assert application is None

    r = client.post(
        '/api/team/%s/application/%s/token' %
        (test_team.team_name, application_name),
        data={'owner_email': admin_user.username + '@foo.bar'},
        headers={'Authorization': admin_token},
    )

    assert_response_ok(r)
    application = Application.get_by_name(application_name)
    assert application is not None
    user = User.get_by_token(settings.SECRET_KEY, r.json['data']['token'])
    assert user and user.username == application.application_name
Exemple #16
0
def test_create_application_cache_invalidation(db, test_team):
    assert Application.get_by_name('bar') is None
    assert len(Application.get_multi_by_team(test_team.id)) == 0
    assert len(Application.get_all()) == 0

    Application.create('bar', test_team.id)

    assert Application.get_by_name('bar') is not None
    assert len(Application.get_multi_by_team(test_team.id)) == 1
    assert len(Application.get_all()) == 1
Exemple #17
0
def test_set_route_with_dest_linked_cluster(client, zk, test_team,
                                            test_application, check_tree,
                                            test_application_token):
    dest_application_name = '%s_dest' % test_application.application_name
    Application.create(dest_application_name, test_team.id)
    test_application_name = test_application.application_name
    cluster_name = 'stable'
    dest_cluster_name = 'channel-stable-1'
    physical_cluster = 'foo.bar'
    path = '/huskar/service/%s/%s' % (dest_application_name, dest_cluster_name)
    data = json.dumps({'link': [physical_cluster]})
    zk.create(path, data, makepath=True)
    zk.ensure_path('/huskar/service/%s/%s' %
                   (test_application_name, cluster_name))
    zk.ensure_path('/huskar/service/%s/%s' %
                   (dest_application_name, physical_cluster))
    zk.ensure_path('/huskar/service/%s/%s/key' %
                   (dest_application_name, physical_cluster))

    url = '/api/serviceroute/%s/%s/%s' % (test_application_name, cluster_name,
                                          dest_application_name)
    r = client.put(url,
                   data={
                       'cluster_name': dest_cluster_name,
                       'intent': 'direct'
                   },
                   headers={'Authorization': test_application_token})
    assert_response_ok(r)
    result = [
        {
            'path':
            '/huskar/service/%s' % test_application_name,
            'data':
            '{"dependency":{"%s":["%s"]},"_version":"1"}' %
            (dest_application_name, cluster_name),
        },
        {
            'path':
            '/huskar/service/%s/%s' % (dest_application_name, cluster_name),
            'data':
            '{"route":{"%s":"%s"},"_version":"1"}' %
            (test_application_name, dest_cluster_name),
        },
    ]
    check_tree(result)
Exemple #18
0
def _optional_instance_indices(application_name, cluster_name, instance_key,
                               action_type):
    _, action_name = action_types[action_type].split('_', 1)
    instance_type = INSTANCE_TYPE_MAP[action_name.lower()]
    application = None
    with _suppress_exception(application_name=application_name):
        application = Application.get_by_name(application_name)
    if application:
        yield (instance_type, application.id, cluster_name, instance_key)
Exemple #19
0
def test_create_application_setup_default_zpath_oos(mocker, zk, test_team,
                                                    faker):
    application_name = faker.uuid4()[:8]
    mocker.patch.object(ServiceInfo, 'save', side_effect=OutOfSyncError())

    application = Application.create(application_name, test_team.id)
    assert application.id > 0
    stat = zk.exists('/huskar/service/%s' % application_name)
    assert stat is None
Exemple #20
0
def test_create_application_setup_default_zpath_bypass(mocker, zk, test_team,
                                                       faker):
    application_name = faker.uuid4()[:8]
    path = '/huskar/service/%s' % application_name
    zk.create(path, b'{}', makepath=True)

    application = Application.create(application_name, test_team.id)
    assert application.id > 0
    data, _ = zk.get(path)
    assert data == b'{}'
Exemple #21
0
def _optional_indices(application_name):
    application = None
    team = None
    with _suppress_exception(application_name=application_name):
        application = Application.get_by_name(application_name)
    with _suppress_exception(application_name=application_name):
        team = application and application.team
    if application:
        yield (TYPE_APPLICATION, application.id)
    if team:
        yield (TYPE_TEAM, team.id)
Exemple #22
0
def test_delete_team(team_foo, team_bar, user_foo):
    Application.create('biu', team_bar.id)
    TeamAdmin.ensure(team_foo.id, user_foo.id)

    # fill cache
    assert Team.get_by_name(team_foo.team_name) is team_foo
    assert Team.get_by_name(team_bar.team_name) is team_bar
    assert TeamAdmin.get_user_ids(team_foo.id) == [user_foo.id]

    Team.delete(team_foo.id)
    with raises(TeamNotEmptyError):
        Team.delete(team_bar.id)

    assert Team.get_by_name(team_foo.team_name) is None
    assert Team.get_by_name(team_bar.team_name) is not None
    assert Team.get(team_foo.id) is None
    assert Team.get(team_bar.id) is not None
    assert TeamAdmin.get_user_ids(team_foo.id) == []
    Team.delete(team_foo.id)
    assert Team.get(team_foo.id) is None
Exemple #23
0
def test_delete_application(db, test_user, test_team, test_application,
                            test_application_auth):
    assert Application.get_by_name(
        test_application.application_name) is test_application
    assert Application.get_multi_by_team(test_team.id) == [test_application]
    assert Application.get_all() == [test_application]

    Application.delete(test_application.id)

    assert Application.get_by_name(test_application.application_name) is None
    assert Application.get_multi_by_team(test_team.id) == []
    assert Application.get_all() == []
    assert ApplicationAuth.get(test_application_auth.id) is None
Exemple #24
0
def test_get_data_from_public_domain_application(client, zk, faker,
                                                 test_application,
                                                 test_application_token,
                                                 data_type):
    name = 'public.%s' % faker.uuid4()
    application = Application.create(name, test_application.team_id)
    path = '/huskar/%s/%s/foo/bar' % (data_type, application.application_name)
    url = '/api/%s/%s/foo?key=bar' % (data_type, application.application_name)
    zk.create(path, b'1', makepath=True)

    r = client.get(url, headers={'Authorization': test_application_token})
    assert_response_ok(r)
Exemple #25
0
def check_application(application_name):
    if is_application_blacklisted(application_name):
        raise ApplicationNotExistedError(
            'application: {} is blacklisted'.format(application_name))

    if g.auth.is_minimal_mode:
        return
    application = Application.get_by_name(application_name)
    if application is None:
        raise ApplicationNotExistedError(
            "application: {} doesn't exist".format(application_name))
    return application
Exemple #26
0
    def _find_target(self, name):
        if self.target_type is AuditLog.TYPE_SITE:
            return 0

        if self.target_type is AuditLog.TYPE_TEAM:
            team = Team.get_by_name(name)
            if team is not None:
                return team.id

        if self.target_type is AuditLog.TYPE_APPLICATION:
            application = Application.get_by_name(name)
            if application is not None:
                return application.id
Exemple #27
0
def test_set_route_failed_dest_empty_cluster(client, zk, test_team,
                                             test_application,
                                             test_application_token, exist):
    dest_application_name = '%s_dest' % test_application.application_name
    Application.create(dest_application_name, test_team.id)
    dest_cluster_name = 'channel-stable-1'
    if exist:
        zk.ensure_path('/huskar/service/%s/%s' %
                       (dest_application_name, dest_cluster_name))

    url = '/api/serviceroute/%s/stable/%s' % (
        test_application.application_name, dest_application_name)
    r = client.put(url,
                   data={
                       'cluster_name': dest_cluster_name,
                       'intent': 'direct'
                   },
                   headers={'Authorization': test_application_token})
    assert r.status_code == 400, r.data
    assert r.json['status'] == 'BadRequest'
    assert r.json['message'] == \
        'The target cluster %s is empty.' % dest_cluster_name
Exemple #28
0
def test_add_application_without_validation(client, mocker, test_user,
                                            admin_token, fake_team):
    invalid_name = '@_@::+1s'
    data = {'team': fake_team.team_name, 'application': invalid_name}
    headers = {'Authorization': admin_token}

    r = client.post('/api/application', data=data, headers=headers)
    assert r.status_code == 400
    assert r.json['status'] == 'ValidationError'
    assert json.loads(r.json['message'])['name'][0]
    assert Application.get_by_name(invalid_name) is None

    def fake_switch(name, default=True):
        if name == SWITCH_VALIDATE_SCHEMA:
            return False
        return default

    mocker.patch.object(switch, 'is_switched_on', fake_switch)

    r = client.post('/api/application', data=data, headers=headers)
    assert_response_ok(r)
    assert Application.get_by_name(invalid_name)
Exemple #29
0
    def get(self, team_name=None):
        """Gets the team list or application list.

        While ``team_name`` is specified, the application list in specified
        team will be responded. Otherwise, the team list will be responded.

        The response of team list looks like::

            {
              "status": "SUCCESS",
              "message": "",
              "data": {
                "teams": [{"name": "team-1", "desc": "team-1"},
                          {"name": "team-2"}, "desc": "team-1"]
              }
            }

        And the response of application list looks like::

            {
              "status": "SUCCESS",
              "message": "",
              "data": {
                "applications": ["base.foo", "base.bar"]
              }
            }

        :param team_name: The name of specified team.
        :<header Authorization: Huskar Token (See :ref:`token`)
        :status 404: The team with specified name is not found.
        :status 200: The team list or application list is responded.
        """
        if team_name:
            if g.auth.is_minimal_mode:
                if team_name != Team.DEFAULT_NAME:
                    abort(404, 'team "%s" does not exist' % team_name)
                applications = application_manifest.as_list()
            else:
                team = self._get_team_or_404(team_name)
                applications = Application.get_multi_by_team(team.id)
                applications = [x.application_name for x in applications]
            data = {'applications': applications}
        else:
            if g.auth.is_minimal_mode:
                data = {'teams': [{'name': Team.DEFAULT_NAME,
                                   'desc': Team.DEFAULT_NAME}]}
            else:
                teams = Team.get_all()
                data = {'teams': [{'name': x.team_name, 'desc': x.team_desc}
                                  for x in teams]}
        return api_response(data)
Exemple #30
0
def test_archive_team(db, team_foo, user_foo, user_bar):
    team_foo.grant_admin(user_foo.id)
    assert team_foo.is_active is True

    application = Application.create('biu', team_foo.id)
    assert application.is_active is True
    with raises(TeamNotEmptyError):
        team_foo.archive()

    application.archive()
    team_foo.archive()
    assert Team.get_by_name(team_foo.team_name) is None
    assert db.query(TeamAdmin.id).filter_by(
        team_id=team_foo.id, user_id=user_foo.id).first() is not None