End-to-end guide for organizers — create problems, schedule a contest, manage teams, clarifications and ICPC standings.
This guide covers the web UI workflow for running a contest. The API uses events; the UI says contests. See Key terms and the API reference.
Before you start
Section titled “Before you start”- Deploy the stack (Getting started) or use a hosted instance.
- Register with an email listed in
ADMIN_EMAILSon the data layer to get admin access. See Authentication. - Seed data from
./dev-deploy.sh webincludes sample contests if you want to explore first.
Organizer checklist
Section titled “Organizer checklist”- Create or import problems (practice set).
- Create a contest with schedule, team mode, and attached problems.
- Let participants register (and join teams if enabled).
- Monitor clarifications during the window.
- End early if needed.
- Review standings (ICPC scoring).
- Clone the contest to rerun with new dates.
1. Create problems
Section titled “1. Create problems”Admin UI
Section titled “Admin UI”- Open Admin → Problems (
/platform/admin/problems). - Use Create problem — title, identifier, prompt (Markdown/LaTeX), difficulty, timeouts, memory limit, test cases.
- Mark public for the practice catalog, or keep private for contest-only use.
API (optional)
Section titled “API (optional)”POST /v1/problems as admin. See API reference.
Bulk import (CLI)
Section titled “Bulk import (CLI)”For ICPC-format folders:
nextjudge upload-challenge ./problems/a-plus-bnextjudge upload-challenge-suite ./icpc-archive/See CLI.
Note: Problem accept_timeout, execution_timeout, and memory_limit are stored and shown in the UI. The judge currently applies fixed nsjail defaults (10s run CPU, ~6 MB virtual memory) — see Judge service — limits.
2. Create a contest
Section titled “2. Create a contest”Admin UI
Section titled “Admin UI”- Go to Admin → Contests (
/platform/admin/contests). - Create contest — title, description, start/end times, teams toggle.
- Select problems from the catalog. Each problem is linked to the event with optional per-contest limits.
Validation on create:
- Title must be unique.
start_timemust not be more than ~5 minutes in the past.start_time<end_time.- Every
problem_idmust exist.
curl -s -X POST http://localhost:5000/v1/events \ -H "Authorization: $TOKEN" \ -H "Content-Type: application/json" \ -d '{ "title": "Spring Practice", "description": "Internal round", "start_time": "2026-04-01T18:00:00Z", "end_time": "2026-04-01T21:00:00Z", "teams": false, "user_id": "'"$USER_ID"'", "problems": [{ "problem_id": 1 }] }'Admin only. Optional per-problem overrides in problems[]: accept_timeout, execution_timeout, memory_limit, languages.
Edit and clone
Section titled “Edit and clone”- Edit metadata (title, schedule, teams) from the admin contest card. Problem attachments are not changed by edit — add problems via API or clone the contest.
- Clone contest copies settings and problems into a new event (useful for reruns).
3. Registration and teams
Section titled “3. Registration and teams”Self-registration
Section titled “Self-registration”Participants open Contests (/platform/contests), pick an event, and click Register. API: POST /v1/public/events/{event_id}/register.
Admin adds participants
Section titled “Admin adds participants”From the admin contest card → Add participants, or POST /v1/events/{event_id}/participants with { "user_id": "..." }.
Team contests (teams: true)
Section titled “Team contests (teams: true)”After registering, participants must create or join a team before submitting:
| Action | API |
|---|---|
| List teams | GET /v1/events/{id}/teams |
| Create team | POST /v1/events/{id}/teams { "name": "Team Ada" } |
| Join team | POST /v1/events/{id}/teams/{team_id}/join |
| My team | GET /v1/events/{id}/teams/me |
Rules: one team per user per event; team names unique per event. Standings remain per-user, not aggregated by team — teams gate registration and submission only.
Submission gating
Section titled “Submission gating”During the contest window, a user can submit only if:
start_time ≤ now ≤ end_time- They are registered (and on a team when
teams: true) - They have not already solved every problem in the event (full solve locks further submits)
Submissions include event_id in POST /v1/submissions.
4. Clarifications
Section titled “4. Clarifications”Participants ask questions from the contest detail page (Questions section).
| Action | API |
|---|---|
| Ask | POST /v1/events/{id}/questions { "question": "...", "problem_id": 1 } (problem_id optional) |
| List | GET /v1/events/{id}/questions |
| Answer | PUT /v1/events/{id}/questions/{question_id}/answer { "answer": "..." } |
UI visibility:
- Public clarifications — answered questions visible to everyone.
- Pending — visible to the author and admins.
- Admins answer via the UI; the API allows any authenticated user to answer (restrict at the proxy if needed).
Notifications: asking notifies other participants; answering notifies the question author. See Notifications.
5. End contest early
Section titled “5. End contest early”End now on the admin card or contest detail (POST /v1/events/{id}/end) sets end_time to the current time. Further submissions are rejected.
6. Standings (ICPC scoring)
Section titled “6. Standings (ICPC scoring)”The leaderboard uses GET /v1/events/{id}/attempts. Scoring is computed in the web app from attempt stats.
Per-problem solve time
Section titled “Per-problem solve time”minutes_to_solve = minutes from event.start_time to first AC on that problem(clamped to ≥ 0)
Penalty per solved problem
Section titled “Penalty per solved problem”wrong_before_ac = max(0, attempts - 1)problem_penalty = minutes_to_solve + 20 × wrong_before_ac- 20 minutes per wrong submission before first AC (ICPC standard).
- The AC submission counts in
attemptsbut adds no wrong penalty.
Ranking (tie-breakers)
Section titled “Ranking (tie-breakers)”- More problems solved — higher rank.
- Lower total penalty — better.
- Fewer total submissions — better.
Display
Section titled “Display”- Solved cell:
{attempts}/{minutes}(e.g.3/45). - Unsolved with tries:
{count}/--. - Penalty column: total minutes (e.g.
125m).
Full solve freeze
Section titled “Full solve freeze”When a user ACs every problem, their clock stops at the last AC timestamp. Later submissions are excluded from scoring, and they cannot submit again.
Limitations
Section titled “Limitations”| Topic | Behavior |
|---|---|
| Team events | Rankings are individual users |
| Penalty constant | 20 minutes — not configurable per event |
| Frozen board | Ended contests show frozen standings; data is live from the DB |
Problem acceptance stats: GET /v1/events/{id}/problems_stats. Personal progress: GET /v1/events/{id}/user_problem_status.
7. During the contest
Section titled “7. During the contest”- Monitor queue depth if submissions stay
PENDING— Troubleshooting. - Scale judges for large events — Deployment.
- Contest submissions in standings redact
source_codefor other users; owners see full detail.
What’s next
Section titled “What’s next”- Configuration — OAuth, env files, optional Elasticsearch
- API reference — automation and integrations
- CLI — bulk problem import and local testing