コード例 #1
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_losers_advantage(client):
    """
        user with the lose_count of 3 and others with that of 0 attempt to
        apply a lottery
        test loser is more likely to win
        target_url: /lotteries/<id>/draw
    """
    users_num = 12

    idx = 1
    win_count = {i: 0 for i in range(1, users_num + 1)}     # user.id -> count

    with client.application.app_context():
        target_lottery = Lottery.query.get(idx)
        index = target_lottery.index

        users = User.query.order_by(User.id).all()[:users_num]
        users[0].lose_count = 3
        user0_id = users[0].id

        add_db(users2application(users, target_lottery))

        token = get_token(client, admin)

        resp = draw(client, token, idx, index)

        for winner_json in resp.get_json():
            winner_id = winner_json['id']
            win_count[winner_id] += 1

        # display info when this test fails
        print("final results of applications (1's lose_count == 3)")
        print(win_count)

        assert win_count[user0_id] > 0
コード例 #2
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_draw(client):
    """attempt to draw a lottery
        1. make some applications to one lottery
        2. draws the lottery
        3. test: status code
        4. test: DB is changed
        target_url: /lotteries/<id>/draw [POST]
    """
    idx = 1

    with client.application.app_context():
        target_lottery = Lottery.query.get(idx)
        index = target_lottery.index
        users = User.query.all()
        add_db(user2application(user, target_lottery) for user in users)

        token = get_token(client, admin)

        resp = draw(client, token, idx, index)

        assert resp.status_code == 200

        winners_id = [winner['id'] for winner in resp.get_json()]

        users = User.query.all()
        target_lottery = Lottery.query.get(idx)

        waiting_cnt = 0

        for user in users:
            application = get_application(user, target_lottery)

            if user.id in winners_id:
                assert application.status == 'won'
                assert user.win_count == 1
                assert user.lose_count == 0
                assert user.waiting_count == 0
            else:
                assert application.status in {'lose', 'waiting'}
                assert user.win_count == 0
                if application.status == 'waiting':
                    assert user.lose_count == 0
                    assert user.waiting_count == 1
                    waiting_cnt += 1
                else:
                    assert user.lose_count == 1
                    assert user.waiting_count == 0

        assert waiting_cnt == 3
コード例 #3
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_draw_lots_of_groups_and_normal(client):
    """attempt to draw a lottery as 2 groups of 2 members and 2 normal
            while WINNERS_NUM is 5
        1. make some applications to one lottery as groups
        2. draws the lottery
        3. test: status code
        4. test: DB is changed
        5. test: result of each member
        6. test: number of winners is less than 3
        target_url: /lotteries/<id>/draw [POST]
    """
    idx = 1
    members = (0, 1)
    reps = (2, 3)
    normals = (4, 5)

    with client.application.app_context():
        target_lottery = Lottery.query.get(idx)
        index = target_lottery.index
        users = User.query.all()

        member_apps = [user2application(users[i], target_lottery)
                       for i in chain(members, normals)]
        add_db(member_apps)

        rep_apps = [rep2application(users[rep], target_lottery,
                                    [member_apps[member]])
                    for rep, member in zip(reps, members)]
        add_db(rep_apps)

        token = get_token(client, admin)

        resp = draw(client, token, idx, index)

        assert resp.status_code == 200

        winners = resp.get_json()
        assert len(winners) == 5    # client.application.config['WINNERS_NUM']

        users = User.query.all()
        target_lottery = Lottery.query.get(idx)

        for rep, member in zip(reps, members):
            rep_status = get_application(users[rep], target_lottery).status
            member_status = \
                get_application(users[member], target_lottery).status

            assert rep_status == member_status
コード例 #4
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_draw_group(client):
    """attempt to draw a lottery as a group
        1. make some applications to one lottery as a group
        2. draws the lottery
        3. test: status code
        4. test: DB is changed
        5. test: result of each member (win)
        target_url: /lotteries/<id>/draw [POST]
    """
    idx = 1
    group_size = 3

    with client.application.app_context():
        target_lottery = Lottery.query.get(idx)
        index = target_lottery.index
        users = User.query.all()

        members_app = [user2application(user, target_lottery)
                       for user in users[1:group_size]]
        add_db(members_app)

        rep_application = user2application(
                users[0], target_lottery,
                is_rep=True,
                group_members=apps2members(members_app))

        add_db((rep_application,))  # 1-element tuple

        token = get_token(client, admin)

        resp = draw(client, token, idx, index)

        assert resp.status_code == 200

        users = User.query.all()
        target_lottery = Lottery.query.get(idx)

        rep_status = get_application(users[0], target_lottery).status

        assert rep_status == "won"
        assert users[0].win_count == 1

        for user in users[1:group_size]:
            application = get_application(user, target_lottery)
            assert application.status == "won"
            assert user.win_count == 1
コード例 #5
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_apply_member_consecutive(client):
    """attempt to apply after a member's previous won / lose / waiting
        test: win -> refused (because he/she should be watching a show)
        test: lose / waiting -> accepted
        target_url: /lotteries/<id> [POST]
    """
    idx1 = 1
    token_admin = get_token(client, admin)

    with client.application.app_context():
        lottery1 = Lottery.query.get(idx1)
        index1 = lottery1.index
        lottery2 = Lottery.query.filter_by(
            classroom_id=lottery1.classroom_id,
            index=lottery1.index + 1).one()
        idx2 = lottery2.id
        index2 = lottery2.index

        # 5 won, 2 lose, 3 waiting
        users = User.query.filter_by(authority='normal').limit(10).all()
        apps = users2application(users, lottery1)
        add_db(apps)

        draw_all(client, token_admin, index=index1)

        people = [Application.query.filter_by(status=s).first().user
                  for s in ('won', 'lose', 'waiting')]
        sids = [person.secret_id for person in people]
        tokens = [login(client, person.secret_id, '')['token']
                  for person in people]

        for i, (token_i, member_i) in enumerate(((0, 1), (2, 0), (1, 2))):
            with mock.patch('api.routes.api.get_time_index',
                            return_value=index2):
                resp = post(client, f'/lotteries/{idx2}',
                            token=tokens[token_i],
                            group_members=[sids[member_i]])
                if i == 2:
                    assert resp.status_code == 200
                else:
                    assert resp.status_code == 403
                    assert 'while watching' in resp.get_json()['message']
コード例 #6
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_apply_consecutive(client):
    """attempt to apply after previous won / lose / waiting
        test: win -> refused (because he/she should be watching a show)
        test: lose / waiting -> accepted
        target_url: /lotteries/<id> [POST]
    """
    idx1 = 1
    token_admin = get_token(client, admin)

    with client.application.app_context():
        lottery1 = Lottery.query.get(idx1)
        index1 = lottery1.index
        lottery2 = Lottery.query.filter_by(
            classroom_id=lottery1.classroom_id,
            index=lottery1.index + 1).one()
        idx2 = lottery2.id
        index2 = lottery2.index

        # 5 won, 2 lose, 3 waiting
        users = User.query.filter_by(authority='normal').limit(10).all()
        apps = users2application(users, lottery1)
        add_db(apps)
        user_sids = [user.secret_id for user in users]
        app_ids = [app.id for app in apps]

        draw_all(client, token_admin, index=index1)

        for user_sid, app_id in zip(user_sids, app_ids):
            app_after = Application.query.get(app_id)

            token = login(client, user_sid, '')['token']
            with mock.patch('api.routes.api.get_time_index',
                            return_value=index2):
                resp = post(client, f'/lotteries/{idx2}', token=token,
                            group_members=[])

            if app_after.status == 'won':
                assert resp.status_code == 403
                assert 'while watching a show' in resp.get_json()['message']
            else:
                assert resp.status_code == 200
コード例 #7
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_get_allapplications(client):
    """test proper infomation is returned from the API to a normal user
        target_url: /applications
    """
    with client.application.app_context():
        lottery = Lottery.query.get(1)
        user = User.query.filter_by(secret_id=test_user['secret_id']).one()

        apps = [user2application(user, lottery) for _ in range(2)]
        apps[1].created_on += datetime.timedelta(days=-1)

        add_db(apps)

        correct_resp = applications_schema.dump([apps[0]])[0]

        resp = as_user_get(client,
                           test_user['secret_id'],
                           test_user['g-recaptcha-response'],
                           '/applications')

        assert resp.get_json() == correct_resp
コード例 #8
0
ファイル: test_lottery.py プロジェクト: Sakuten/backend
def test_draw_lots_of_groups(client):
    """attempt to draw a lottery as 3 groups of 2 members and
            2 group of 3 members
            while WINNERS_NUM is 5 and WAITING_NUM is 3
        1. make some applications to one lottery as groups
        2. draws the lottery
        3. test: status code
        4. test: DB is changed
        5. test: result of each member
        6. test: number of winners is 5 (*not 4*)
        7. test: size of waiting list < 3
        target_url: /lotteries/<id>/draw [POST]
    """
    idx = 1
    groups = {0: [1], 2: [3], 4: [5, 6], 7: [8, 9]}    # rep -> members

    with client.application.app_context():
        target_lottery = Lottery.query.get(idx)
        index = target_lottery.index
        users = User.query.all()

        for rep, members in groups.items():
            members_app = [user2application(users[i], target_lottery)
                           for i in members]
            add_db(members_app)

            rep_app = rep2application(users[rep], target_lottery,
                                      apps2members(members_app))
            add_db([rep_app])

        token = get_token(client, admin)

        resp = draw(client, token, idx, index)

        assert resp.status_code == 200

        winners = resp.get_json()
        assert len(winners) == 5

        users = User.query.all()
        target_lottery = Lottery.query.get(idx)

        won_cnt = 0
        lose_cnt = 0
        waiting_cnt = 0
        for rep, members in groups.items():
            rep_status = get_application(users[rep], target_lottery).status
            members_status = (get_application(users[i], target_lottery).status
                              for i in members)

            assert all(status == rep_status for status in members_status)

            if rep_status == "won":
                won_cnt += 1 + len(members)
            elif rep_status == "lose":
                lose_cnt += 1 + len(members)
            else:
                # make sure "waiting-pending" does not leak out
                assert rep_status == "waiting"
                waiting_cnt += 1 + len(members)

        assert won_cnt == 5
        assert lose_cnt in {2, 3}
        assert waiting_cnt in {3, 2}
        assert lose_cnt + waiting_cnt == 5