Пример #1
0
def test_api_challenge_get_solves_ctftime_public():
    """Can a public user get /api/v1/challenges/<challenge_id>/solves if ctftime is over"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-7"):
        set_config('challenge_visibility', 'public')
        gen_challenge(app.db)
        with app.test_client() as client:
            r = client.get('/api/v1/challenges/1/solves')
            assert r.status_code == 200
            set_config(
                'start', '1507089600'
            )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
            set_config('end', '1507262400'
                       )  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
            r = client.get('/api/v1/challenges/1/solves', json="")
            assert r.status_code == 403
    destroy_ctfd(app)
Пример #2
0
def test_admins_can_preview_hints():
    """Test that admins are able to bypass restrictions and preview hints with ?preview=true"""
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        gen_hint(app.db, challenge_id=1, cost=100)
        client = login_as_user(app, name="admin", password="******")
        r = client.get('/api/v1/hints/1')
        assert r.status_code == 200
        hint = r.get_json()
        assert hint.get('content') is None

        r = client.get('/api/v1/hints/1?preview=true')
        assert r.status_code == 200
        hint = r.get_json()
        assert hint['data']['content'] == "This is a hint"
    destroy_ctfd(app)
Пример #3
0
def test_api_challenge_get_ctftime_public():
    """Can a public user get /api/v1/challenges/<challenge_id> if ctftime is over"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-7"):
        set_config("challenge_visibility", "public")
        gen_challenge(app.db)
        with app.test_client() as client:
            r = client.get("/api/v1/challenges/1")
            assert r.status_code == 200
            set_config(
                "start", "1507089600"
            )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
            set_config("end", "1507262400"
                       )  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
            r = client.get("/api/v1/challenges/1")
            assert r.status_code == 403
    destroy_ctfd(app)
Пример #4
0
def test_api_challenge_get_solves_ctf_frozen():
    """Test users can only see challenge solves that happened before freeze time"""
    app = create_ctfd()
    with app.app_context():
        register_user(app, name="user1", email="*****@*****.**")
        register_user(app, name="user2", email="*****@*****.**")

        # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        set_config("freeze", "1507262400")
        with freeze_time("2017-10-4"):
            chal = gen_challenge(app.db)
            chal_id = chal.id
            gen_solve(app.db, user_id=2, challenge_id=chal_id)
            chal2 = gen_challenge(app.db)
            chal2_id = chal2.id

        with freeze_time("2017-10-8"):
            chal2 = gen_solve(app.db, user_id=2, challenge_id=chal2_id)

            # There should now be two solves assigned to the same user.
            assert Solves.query.count() == 2

            client = login_as_user(app, name="user2")

            # Challenge 1 should have one solve
            r = client.get("/api/v1/challenges/1/solves")
            data = r.get_json()["data"]
            assert len(data) == 1

            # Challenge 2 should have a solve shouldn't be shown to the user
            r = client.get("/api/v1/challenges/2/solves")
            data = r.get_json()["data"]
            assert len(data) == 0

            # Admins should see data as an admin with no modifications
            admin = login_as_user(app, name="admin")
            r = admin.get("/api/v1/challenges/2/solves")
            data = r.get_json()["data"]
            assert len(data) == 1

            # But should see as a user if the preview param is passed
            r = admin.get("/api/v1/challenges/2/solves?preview=true")
            data = r.get_json()["data"]
            assert len(data) == 0

    destroy_ctfd(app)
Пример #5
0
def test_api_challenge_get_verified_emails():
    """Can a verified email load /api/v1/challenges/<challenge_id>"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-5"):
        set_config('start', '1507089600')  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
        set_config('end', '1507262400')  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        set_config('verify_emails', True)
        gen_challenge(app.db)
        gen_user(app.db, name='user_name', email='*****@*****.**', password='******', verified=True)
        register_user(app)
        client = login_as_user(app)
        registered_client = login_as_user(app, 'user_name', 'password')
        r = client.get('/api/v1/challenges/1', json="")
        assert r.status_code == 403
        r = registered_client.get('/api/v1/challenges/1')
        assert r.status_code == 200
    destroy_ctfd(app)
Пример #6
0
def test_api_challenge_attempt_post_admin():
    """Can an admin user post /api/v1/challenges/attempt"""
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        gen_flag(app.db, 1)
        with login_as_user(app, 'admin') as client:
            r = client.post('/api/v1/challenges/attempt', json={"challenge_id": 1, "submission": "wrong_flag"})
            assert r.status_code == 200
            assert r.get_json()['data']['status'] == 'incorrect'
            r = client.post('/api/v1/challenges/attempt', json={"challenge_id": 1, "submission": "flag"})
            assert r.status_code == 200
            assert r.get_json()['data']['status'] == 'correct'
            r = client.post('/api/v1/challenges/attempt', json={"challenge_id": 1, "submission": "flag"})
            assert r.status_code == 200
            assert r.get_json()['data']['status'] == 'already_solved'
    destroy_ctfd(app)
Пример #7
0
def test_api_challenge_get_ctftime_private():
    """Can a private user get /api/v1/challenges/<challenge_id> if ctftime is over"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-7"):
        gen_challenge(app.db)
        register_user(app)
        client = login_as_user(app)
        r = client.get("/api/v1/challenges/1")
        assert r.status_code == 200
        set_config("start", "1507089600"
                   )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
        set_config(
            "end",
            "1507262400")  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        r = client.get("/api/v1/challenges/1")
        assert r.status_code == 403
    destroy_ctfd(app)
Пример #8
0
def test_hidden_users_should_not_influence_scores():
    app = create_ctfd()
    with app.app_context():
        register_user(app,
                      name="user1",
                      email="*****@*****.**",
                      password="******")
        register_user(app,
                      name="user2",
                      email="*****@*****.**",
                      password="******")
        register_user(app,
                      name="user3",
                      email="*****@*****.**",
                      password="******")

        user = Users.query.filter_by(name="user3").first()
        user.hidden = True
        app.db.session.commit()

        client1 = login_as_user(app, name="user1", password="******")

        # User 1 solves 1st challenge
        chal1 = gen_challenge(app.db)
        gen_solve(app.db, user_id=2, challenge_id=chal1.id)

        # User 2 solves 2nd challenge
        chal2 = gen_challenge(app.db)
        gen_solve(app.db, user_id=3, challenge_id=chal2.id)

        # User 3 solves both
        gen_solve(app.db, user_id=4, challenge_id=chal1.id)
        gen_solve(app.db, user_id=4, challenge_id=chal2.id)

        scores = get_scores(client1)

        for entry in scores:
            assert entry["name"] != "user3"

        user1 = Users.query.filter_by(name="user1").first()
        assert user1.place == "1st"

        user2 = Users.query.filter_by(name="user2").first()
        assert user2.place == "2nd"
    destroy_ctfd(app)
Пример #9
0
def test_users_cannot_preview_hints():
    """Test that users aren't able to preview hints"""
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        gen_hint(app.db, challenge_id=1, cost=100)
        register_user(app)
        client = login_as_user(app)
        r = client.get('/api/v1/hints/1')
        assert r.status_code == 200
        hint = r.get_json()
        assert hint.get('content') is None

        r = client.get('/api/v1/hints/1?preview=true')
        assert r.status_code == 200
        hint = r.get_json()
        assert hint['data'].get('content') is None
    destroy_ctfd(app)
Пример #10
0
def test_api_challenge_solves_visibility():
    """Can the api load /api/v1/challenges/<challenge_id>/solves if challenge_visibility is private/public"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-5"):
        set_config('start', '1507089600'
                   )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
        set_config(
            'end',
            '1507262400')  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        set_config('challenge_visibility', 'public')
        gen_challenge(app.db)
        with app.test_client() as client:
            r = client.get('/api/v1/challenges/1/solves')
            assert r.status_code == 200
            set_config('challenge_visibility', 'private')
            r = client.get('/api/v1/challenges/1/solves')
            assert r.status_code == 302
    destroy_ctfd(app)
Пример #11
0
def test_api_challenge_solves_user_visibility():
    """Can the user load /api/v1/challenges/<challenge_id>/solves if challenge_visibility is private/public"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-5"):
        set_config("start", "1507089600"
                   )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
        set_config(
            "end",
            "1507262400")  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        gen_challenge(app.db)
        register_user(app)
        client = login_as_user(app)
        r = client.get("/api/v1/challenges/1/solves")
        assert r.status_code == 200
        set_config("challenge_visibility", "public")
        r = client.get("/api/v1/challenges/1/solves")
        assert r.status_code == 200
    destroy_ctfd(app)
Пример #12
0
def test_api_challenge_visibility():
    """Can the api load /api/v1/challenges/<challenge_id> if challenge_visibility is private/public"""
    app = create_ctfd()
    with app.app_context(), freeze_time("2017-10-5"):
        set_config("start", "1507089600"
                   )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
        set_config(
            "end",
            "1507262400")  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        set_config("challenge_visibility", "public")
        with app.test_client() as client:
            gen_challenge(app.db)
            r = client.get("/api/v1/challenges/1")
            assert r.status_code == 200
            set_config("challenge_visibility", "private")
            r = client.get("/api/v1/challenges/1")
            assert r.status_code == 302
    destroy_ctfd(app)
Пример #13
0
def test_api_submissions_post_admin():
    """Can a user post /api/v1/submissions if admin"""
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        with login_as_user(app, name="admin") as client:
            r = client.post(
                "/api/v1/submissions",
                json={
                    "provided": "MARKED AS SOLVED BY ADMIN",
                    "user_id": 1,
                    "team_id": None,
                    "challenge_id": "1",
                    "type": "correct",
                },
            )
            assert r.status_code == 200
    destroy_ctfd(app)
Пример #14
0
def test_scoreboard_team_score():
    """Is a user's submitted flag reflected on the team's score on /scoreboard"""
    app = create_kmactf(user_mode="teams")
    with app.app_context():
        user = gen_user(app.db, name="user")
        team = gen_team(app.db)
        user.team_id = team.id
        team.members.append(user)
        gen_challenge(app.db)
        gen_flag(app.db, 1)
        app.db.session.commit()
        with login_as_user(app) as client:
            flag = {"challenge_id": 1, "submission": "flag"}
            client.post("/api/v1/challenges/attempt", json=flag)
        standings = get_standings()
        assert standings[0][2] == "team_name"
        assert standings[0][3] == 100
    destroy_kmactf(app)
def test_challenge_board_under_view_after_ctf():
    """Test that the challenge board does not show an error under view_after_ctf"""
    app = create_ctfd()
    with app.app_context():
        set_config("view_after_ctf", True)
        set_config("start", "1507089600"
                   )  # Wednesday, October 4, 2017 12:00:00 AM GMT-04:00 DST
        set_config(
            "end",
            "1507262400")  # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST

        register_user(app)
        client = login_as_user(app)

        gen_challenge(app.db)
        gen_flag(app.db, challenge_id=1, content="flag")

        gen_challenge(app.db)
        gen_flag(app.db, challenge_id=2, content="flag")

        # CTF is ongoing. Normal operation.
        with freeze_time("2017-10-5"):
            r = client.get("/challenges")
            assert r.status_code == 200
            assert "has ended" not in r.get_data(as_text=True)

            data = {"submission": "flag", "challenge_id": 1}
            r = client.post("/api/v1/challenges/attempt", json=data)
            assert r.status_code == 200
            assert r.get_json()["data"]["status"] == "correct"
            assert Solves.query.count() == 1

        # CTF is now over. There should be a message and challenges should show submission status but not store solves
        with freeze_time("2017-10-7"):
            r = client.get("/challenges")
            assert r.status_code == 200
            assert "has ended" in r.get_data(as_text=True)

            data = {"submission": "flag", "challenge_id": 2}
            r = client.post("/api/v1/challenges/attempt", json=data)
            assert r.status_code == 200
            assert r.get_json()["data"]["status"] == "correct"
            assert Solves.query.count() == 1
    destroy_ctfd(app)
Пример #16
0
def test_import_ctf():
    """Test that CTFd can import a CTF"""
    app = create_ctfd()
    if not app.config.get("SQLALCHEMY_DATABASE_URI").startswith("sqlite"):
        with app.app_context():
            base_user = "******"
            for x in range(10):
                user = base_user + str(x)
                user_email = user + "@ctfd.io"
                gen_user(app.db, name=user, email=user_email)

            for x in range(9):
                chal = gen_challenge(app.db, name="chal_name{}".format(x))
                gen_flag(app.db, challenge_id=chal.id, content="flag")

            chal = gen_challenge(app.db,
                                 name="chal_name10",
                                 requirements={"prerequisites": [1]})
            gen_flag(app.db, challenge_id=chal.id, content="flag")

            app.db.session.commit()

            backup = export_ctf()

            with open("export.test_import_ctf.zip", "wb") as f:
                f.write(backup.read())
    destroy_ctfd(app)

    app = create_ctfd()
    # TODO: These databases should work but they don't...
    if not app.config.get("SQLALCHEMY_DATABASE_URI").startswith("sqlite"):
        with app.app_context():
            import_ctf("export.test_import_ctf.zip")

            if not app.config.get("SQLALCHEMY_DATABASE_URI").startswith(
                    "postgres"):
                # TODO: Dig deeper into why Postgres fails here
                assert Users.query.count() == 11
                assert Challenges.query.count() == 10
                assert Flags.query.count() == 10

                chal = Challenges.query.filter_by(name="chal_name10").first()
                assert chal.requirements == {"prerequisites": [1]}
    destroy_ctfd(app)
Пример #17
0
def test_hint_team_unlock():
    """Is a user's unlocked hint reflected on other team members"""
    app = create_ctfd(user_mode="teams")
    with app.app_context():
        user = gen_user(app.db)
        second_user = gen_user(app.db,
                               name="user",
                               email="*****@*****.**")
        team = gen_team(app.db)
        user.team_id = team.id
        second_user.team_id = team.id
        team.members.append(user)
        team.members.append(second_user)
        chal = gen_challenge(app.db)
        gen_hint(app.db, chal.id, content="hint", cost=1, type="standard")
        # Give the points to the user that doesn't unlock
        # Users that unlock hints should be able to unlock but cost their team points
        gen_award(app.db, user_id=3, team_id=team.id)
        app.db.session.commit()
        with login_as_user(app, name="user_name") as client:
            # Assert that we don't see a hint
            r = client.get("/api/v1/hints/1")
            assert r.get_json()["data"].get("content") is None

            # Unlock the hint
            client.post("/api/v1/unlocks", json={"target": 1, "type": "hints"})

            # Assert that we see a hint
            r = client.get("/api/v1/hints/1")
            assert r.get_json()["data"].get("content")
        with login_as_user(app) as second_client:
            # Assert that we see a hint
            r = second_client.get("/api/v1/hints/1")
            assert r.get_json()["data"].get("content")

            # Assert that we can't double unlock
            r = second_client.post("/api/v1/unlocks",
                                   json={
                                       "target": 1,
                                       "type": "hints"
                                   })
            assert r.status_code == 400
            assert (r.get_json()["errors"]["target"] ==
                    "You've already unlocked this this target")

            # Assert that we see a hint
            r = second_client.get("/api/v1/hints/1")
            assert r.json["data"]["content"] == "hint"

            # Verify standings
            # We start with 100 points from the award.
            # We lose a point because we unlock successfully once
            standings = get_standings()
            assert standings[0][2] == "team_name"
            assert standings[0][3] == 99
    destroy_ctfd(app)
Пример #18
0
def test_api_challenge_get_solves_verified_emails():
    """Can a verified email get /api/v1/challenges/<challenge_id>/solves"""
    app = create_ctfd()
    with app.app_context():
        set_config('verify_emails', True)
        gen_challenge(app.db)
        gen_user(app.db,
                 name='user_name',
                 email='*****@*****.**',
                 password='******',
                 verified=True)
        register_user(app)
        client = login_as_user(app)
        registered_client = login_as_user(app, 'user_name', 'password')
        r = client.get('/api/v1/challenges/1/solves', json="")
        assert r.status_code == 403
        r = registered_client.get('/api/v1/challenges/1/solves')
        assert r.status_code == 200
    destroy_ctfd(app)
def test_api_flag_patch_admin():
    """Can a user patch /api/v1/flags/<flag_id> if admin"""
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        gen_flag(app.db, 1)
        with login_as_user(app, "admin") as client:
            r = client.patch(
                "/api/v1/flags/1",
                json={
                    "content": "flag_edit",
                    "data": "",
                    "type": "static",
                    "id": "1"
                },
            )
            assert r.status_code == 200
            assert r.get_json()["data"]["content"] == "flag_edit"
    destroy_ctfd(app)
Пример #20
0
def test_api_team_captain_disbanding_only_inactive_teams():
    """Test that only teams that haven't conducted any actions can be disbanded"""
    app = create_ctfd(user_mode="teams")
    with app.app_context():
        user = gen_user(app.db, name="user")
        team = gen_team(app.db)
        team.members.append(user)
        user.team_id = team.id
        team.captain_id = 2
        user2 = gen_user(app.db, name="user2", email="*****@*****.**")
        team.members.append(user2)
        app.db.session.commit()

        gen_challenge(app.db)
        gen_flag(app.db, 1)
        gen_solve(app.db, user_id=3, team_id=1, challenge_id=1)

        with login_as_user(app) as client:
            r = client.delete("/api/v1/teams/me", json="")
            assert r.status_code == 403
            assert r.get_json() == {
                "success": False,
                "errors": {
                    "": [
                        "You cannot disband your team as it has participated in the event. "
                        "Please contact an admin to disband your team or remove a member."
                    ]
                },
            }

        user = gen_user(app.db, name="user3", email="*****@*****.**")
        team = gen_team(app.db, name="team2", email="*****@*****.**")
        print(user.id)
        team.members.append(user)
        user.team_id = team.id
        team.captain_id = user.id
        app.db.session.commit()
        with login_as_user(app, name="user3") as client:
            r = client.delete("/api/v1/teams/me", json="")
            print(r.get_json())
            assert r.status_code == 200
            assert r.get_json() == {"success": True}
    destroy_ctfd(app)
Пример #21
0
def test_api_post_comments_with_invalid_author_id():
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        register_user(app)
        with login_as_user(app, "admin") as admin:
            r = admin.post(
                "/api/v1/comments",
                json={
                    "content": "this is a challenge comment",
                    "type": "challenge",
                    "challenge_id": 1,
                    "author_id": 2,
                },
            )
            # Check that POST response has comment data
            assert r.status_code == 200
            resp = r.get_json()
            assert resp["data"]["author_id"] == 1
    destroy_ctfd(app)
Пример #22
0
def test_api_delete_comments():
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        with login_as_user(app, "admin") as admin:
            gen_comment(
                app.db,
                content="this is a challenge comment",
                author_id=1,
                challenge_id=1,
            )
            assert Comments.query.count() == 1

            # Check that the comment can be deleted
            r = admin.delete("/api/v1/comments/1", json="")
            assert r.status_code == 200
            resp = r.get_json()
            assert Comments.query.count() == 0
            assert resp["success"] is True
    destroy_ctfd(app)
Пример #23
0
def test_api_get_comments():
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        with login_as_user(app, "admin") as admin:
            gen_comment(
                app.db,
                content="this is a challenge comment",
                author_id=1,
                challenge_id=1,
            )
            r = admin.get("/api/v1/comments", json="")

            # Check that the comment shows up in the list of all comments
            assert r.status_code == 200
            resp = r.get_json()
            assert resp["data"][0]["content"] == "this is a challenge comment"
            assert "this is a challenge comment" in resp["data"][0]["html"]
            assert resp["data"][0]["type"] == "challenge"
    destroy_ctfd(app)
Пример #24
0
def test_api_user_get_solves_after_freze_time():
    """Can a user get /api/v1/users/<user_id>/solves after freeze time"""
    app = create_ctfd(user_mode="users")
    with app.app_context():
        register_user(app, name="user1", email="*****@*****.**")
        register_user(app, name="user2", email="*****@*****.**")

        # Friday, October 6, 2017 12:00:00 AM GMT-04:00 DST
        set_config("freeze", "1507262400")
        with freeze_time("2017-10-4"):
            chal = gen_challenge(app.db)
            chal_id = chal.id
            gen_solve(app.db, user_id=2, challenge_id=chal_id)
            chal2 = gen_challenge(app.db)
            chal2_id = chal2.id

        with freeze_time("2017-10-8"):
            chal2 = gen_solve(app.db, user_id=2, challenge_id=chal2_id)

            # There should now be two solves assigned to the same user.
            assert Solves.query.count() == 2

            # User 2 should have 2 solves when seen by themselves
            client = login_as_user(app, name="user1")
            r = client.get("/api/v1/users/me/solves")
            data = r.get_json()["data"]
            assert len(data) == 2

            # User 2 should have 1 solve when seen by another user
            client = login_as_user(app, name="user2")
            r = client.get("/api/v1/users/2/solves")
            data = r.get_json()["data"]
            assert len(data) == 1

            # Admins should see all solves for the user
            admin = login_as_user(app, name="admin")

            r = admin.get("/api/v1/users/2/solves")
            data = r.get_json()["data"]
            assert len(data) == 2
    destroy_ctfd(app)
Пример #25
0
def test_api_team_get_solves_after_freze_time():
    """Can a user get /api/v1/teams/<team_id>/solves after freeze time"""
    app = create_ctfd(user_mode="teams")
    with app.app_context():
        register_user(app)
        team = gen_team(app.db,
                        name="team1",
                        email="*****@*****.**",
                        member_count=1)

        team_member = team.members[0]
        tm_name = team_member.name

        set_config("freeze", "1507262400")
        with freeze_time("2017-10-4"):
            chal = gen_challenge(app.db)
            chal_id = chal.id
            gen_solve(app.db, user_id=3, team_id=1, challenge_id=chal_id)
            chal2 = gen_challenge(app.db)
            chal2_id = chal2.id

        with freeze_time("2017-10-8"):
            gen_solve(app.db, user_id=3, team_id=1, challenge_id=chal2_id)

            assert Solves.query.count() == 2

            with login_as_user(app) as client:
                r = client.get("/api/v1/teams/1/solves")
                data = r.get_json()["data"]
                assert len(data) == 1

            with login_as_user(app, name=tm_name) as client:
                r = client.get("/api/v1/teams/me/solves")
                data = r.get_json()["data"]
                assert len(data) == 2

            with login_as_user(app, name="admin") as client:
                r = client.get("/api/v1/teams/1/solves")
                data = r.get_json()["data"]
                assert len(data) == 2
    destroy_ctfd(app)
Пример #26
0
def test_challenges_model_access_plugin_class():
    """
    Test that the Challenges model can access its plugin class
    """
    app = create_ctfd()

    with app.app_context():
        from CTFd.plugins.challenges import get_chal_class

        chal = gen_challenge(app.db)
        assert chal.plugin_class == get_chal_class("standard")
    destroy_ctfd(app)
Пример #27
0
def test_api_challenges_get_solves_score_visibility():
    """Can a user get /api/v1/challenges/<challenge_id>/solves if score_visibility is public/private/admin"""
    app = create_ctfd()
    with app.app_context():
        set_config("challenge_visibility", "public")
        set_config("score_visibility", "public")
        gen_challenge(app.db)
        with app.test_client() as client:
            r = client.get("/api/v1/challenges/1/solves")
            assert r.status_code == 200
        set_config("challenge_visibility", "private")
        set_config("score_visibility", "private")
        register_user(app)
        private_client = login_as_user(app)
        r = private_client.get("/api/v1/challenges/1/solves")
        assert r.status_code == 200
        set_config("score_visibility", "admin")
        admin = login_as_user(app, "admin", "password")
        r = admin.get("/api/v1/challenges/1/solves")
        assert r.status_code == 200
    destroy_ctfd(app)
Пример #28
0
def test_api_challenge_get_solves_verified_emails():
    """Can a verified email get /api/v1/challenges/<challenge_id>/solves"""
    app = create_ctfd()
    with app.app_context():
        set_config("verify_emails", True)
        gen_challenge(app.db)
        gen_user(
            app.db,
            name="user_name",
            email="*****@*****.**",
            password="******",
            verified=True,
        )
        register_user(app)
        client = login_as_user(app)
        registered_client = login_as_user(app, "user_name", "password")
        r = client.get("/api/v1/challenges/1/solves", json="")
        assert r.status_code == 403
        r = registered_client.get("/api/v1/challenges/1/solves")
        assert r.status_code == 200
    destroy_ctfd(app)
Пример #29
0
def test_anonymous_users_view_public_challenges_without_team():
    """Test that if challenges are public, users without team can still view them"""
    app = create_ctfd(user_mode="teams")
    with app.app_context():
        register_user(app)
        gen_challenge(app.db)
        with app.test_client() as client:
            r = client.get("/challenges")
            assert r.status_code == 302
            assert r.location.startswith("http://localhost/login")

        set_config("challenge_visibility", "public")
        with app.test_client() as client:
            r = client.get("/challenges")
            assert r.status_code == 200

        with login_as_user(app) as client:
            r = client.get("/challenges")
            assert r.status_code == 302
            assert r.location.startswith("http://localhost/team")
    destroy_ctfd(app)
Пример #30
0
def test_invalid_requirements_are_rejected():
    """Test that invalid requirements JSON blobs are rejected by the API"""
    app = create_ctfd()
    with app.app_context():
        gen_challenge(app.db)
        gen_challenge(app.db)
        with login_as_user(app, "admin") as client:
            # Test None/null values
            r = client.patch("/api/v1/challenges/1",
                             json={"requirements": {
                                 "prerequisites": [None]
                             }})
            assert r.status_code == 400
            assert r.get_json() == {
                "success": False,
                "errors": {
                    "requirements":
                    ["Challenge requirements cannot have a null prerequisite"]
                },
            }
            # Test empty strings
            r = client.patch("/api/v1/challenges/1",
                             json={"requirements": {
                                 "prerequisites": [""]
                             }})
            assert r.status_code == 400
            assert r.get_json() == {
                "success": False,
                "errors": {
                    "requirements":
                    ["Challenge requirements cannot have a null prerequisite"]
                },
            }
            # Test a valid integer
            r = client.patch("/api/v1/challenges/1",
                             json={"requirements": {
                                 "prerequisites": [2]
                             }})
            assert r.status_code == 200
    destroy_ctfd(app)