June 17, 2025
Didn't realize the static CSS I used came with a dark mode configuration for free. I modified the code editor to include a dark theme to go along. Did some other user experience related stuff as well.
Finally, in preparation for shipping I implemented some basic ratelimits for sensitive endpoints like the submission endpoint. It's really nice that Flask makes stuff like this very easy.
This will probably be the last or second to last devlog before I ship :)
I made so many changes since the last devlog. I don't even remember some of them. But now the app should be in a very usable state.
There are some issues with ugly code and grading security. I'll begin fixing them up after I ship. I also want to add something like an admin panel in the future. Right now I implemented a very rudimentary problem parser. The current workflow is I prepare the problem on my computer, arrange into the proper directory structure, zip it, and send it over with Postman. A bit hacky.
On another note, these docker default container names are always really funny. Each grading worker runs in a new container so I have a lot of them to read.
The fixes have been getting smaller, it looks like I'm almost done.
I mainly implemented cosmetic fixes like the leaderboard tables. That one was a bit tricky to get right.
I also replaced the about page with an actual about page, so newcomers can understand the project. I didn't think it'd get that long but whatever.
I'm looking into deployment right now and ideally I would want to do it for free. I also would prefer it be easy to deploy, since that was one of the principles I wrote into the about section. Right now render.com seems to be the best option, with one small issue--they don't have persistent filesystems. What they do have, however, is a managed persistent Postgres database. I'm already using Postgres, so that's nice. But the thing is, I originally had plans to use something like a networked filesystem for things like testcases. Originally I had put them in the database for convenience. But the thing about testcases is that they are kind of in an awkward spot: they can get up to around 6 to 10 megabytes. But not all of them, either. I think the general practice would be to put them on a networked filesystem, or maybe object storage like S3. But honestly I really just want to have this thing be easy to get going. So I think keeping everything in a database is the move. I'll look into it more when it comes time for deployment.
Implemented a lot of fixes/small additions. Still more to come:
Ensure the contest start time is in local timezone
Show the contest duration
Show in progress mark for contests in progress
Ensure contests are sorted by id
Ensure problem names are sorted by letter
Add colors to the standings page
Cell width in standings page
Make the submission form look better
Find somewhere to put more information about languages, language version at the minimum
Change accepted color to stand out in my submissions page
Replace letter with problem
Syntax highlighting for code in the submission viewer
Make timestamp display in the local time
Have a link back to the problem
Add a copy button
Report time and memory usage
Have an indicator that shows allow/disallow feedback (sample case, compile error)
Continued implementing the submission limitations. It's kind of interesting: memory limit exceeded is a pretty tough verdict to determine. Memory errors are usually killed like any regular program is, so you need some heuristics to sort out the errors which are actually memory related. Furthermore I found out today that some languages like Python also have memory checks built into the interpreter, so those errors cause a fails in a different way, as opposed to one resulting from an executable made from compiled C++. I've decided the best course of actions is to avoid false positives whenever possible, so I report runtime error unless I'm absolutely sure the program exceeded memory limits.
So I forgot the devlog for last night. Yesterday I made some quick fixes in the timer code and the fetcher.
I also replaced the textarea for the submission box with Ace editor. I imagine when I do ship this thing, most people will probably just try to code a quick thing or two on the submission page, so having an actual code editor there might improve their experience.
Finally I began working on a submission viewer, since the my submissions page is obviously insufficient for any sort of proper online judge. It's not completed right now, so I'll just share a screenshot of my editor for the required attachment.
Today I finished a basic implementation of the contest leaderboards. They follow ICPC rules.
Before putting this project on hackclub, I had largely finished the internal object representation of the leaderboard already. Today I spent my time debugging that representation, as well as setting up the API and frontend.
I'm still pretty new to React. But with my work so far, I've found that managing requests is actually pretty annoying. I guess today was a breaking point of sorts, since I finally decided to look for a library that would make request handling easier. I found one called SWR, and that's what I used to help implement the leaderboard frontend. Later I'll refactor the rest of my frontend to use it.
I started this project during the beginning of summer. Today is my first day with it on hackclub.
Today I finally completed the overall behavior for the grading infrastructure. Yesterday I already worked out the dispatching system for the grading containers. So today, I just fixed a few minor issues and implemented the main grading service.
For now, I've settled with database polling to identify new submissions. In the future, when the project is complete, I hope to replace this with a queue service. That seems to be a more proper approach, which can scale much better. I've already taken steps to ensure the scalability of the app, so this seems to be a reasonable continuation.
This was widely regarded as a great move by everyone.