Odds PoC
Overview
Odds PoC is the application (backend API) that provides Jester's content management. It handles the day-to-day operations โ creating, editing and deleting race information, articles, blogs, past blogs, categories, media and NG words โ and is also the entry point for AI generation.
The admin UI (user-web) drives this API.
Features
Race information
Manages the race information (auto racing, keirin, horse racing) that feeds AI article and blog generation.
| Action | Description |
|---|---|
| Register | Specify the racing type and upload the race result JSON file |
| Register a prediction | Attach a pre-race entry list and AI prediction marks (JSON) to an existing race |
| List | Browse races per racing type (with the status of the latest linked article) |
| Detail | Inspect a single race |
| Update | Change the race name or race result |
| Delete | Remove a race |
The racing type is inferred from the race id
Race ids are unique across racing types, so fetching, updating and deleting a race needs no type. Only listing requires specifying which sport to show.
Articles
Manages the 10-second race result summary articles, both hand-written and AI-generated.
| Action | Description |
|---|---|
| Manual creation | Enter the title and body directly |
| AI generation | Pick a race and title and let AI write the article |
| Regeneration | Rebuild a failed article, optionally with extra instructions |
| List | Browse articles (filterable by race and status) |
| Detail | Inspect a single article |
| Update | Change the content or publication window |
| Delete | Remove an article |
Past blogs
Manages past blog articles targeted for migration.
| Action | Description |
|---|---|
| Import | Register scraped past blog articles (a search vector is created at the same time) |
| List | Browse past blogs (filterable by race) |
| Detail | Inspect a single past blog |
| Update the category | Change the broad category; the vector is regenerated too |
| AI rewrite | Have AI rewrite the selected past blog |
Blogs
Manages AI-generated blog articles.
| Action | Description |
|---|---|
| AI generation (rewrite) | Have AI rewrite a selected past blog |
| AI generation (original) | Pick a race and have AI write a recap or a prediction |
| Manual creation | Enter the title and body directly |
| List | Browse blogs (filterable by race, racing type, category, origin, status and title) |
| Detail | Inspect a single blog |
| Update | Change the content, title or category |
| Delete | Remove a blog |
| Thumbnail generation | Have a thumbnail created from the race video |
| Related information | Insert links to similar blogs at the bottom of the article |
Categories
Manages the broad categories used to classify blogs.
| Action | Description |
|---|---|
| Create | Add a category |
| List | Browse categories |
| Detail | Inspect a single category |
| Update | Rename a category |
| Delete | Remove a category |
The category name decides the article design
When the blog HTML is assembled, the category name selects the article template (prediction / race result / generic). Renaming a category changes how blogs look.
Media
Manages images and videos, including AI-generated thumbnails.
| Action | Description |
|---|---|
| Upload | Register a new media file |
| List | Browse media (filterable by type) |
| Detail | Inspect a single media item |
| Update | Replace the file or its metadata |
| Delete | Remove a media item |
NG words
Manages the prohibited words used to screen generated text.
| Action | Description |
|---|---|
| Create | Add a prohibited word |
| List | Browse prohibited words |
| Detail | Inspect a single entry |
| Update | Change the word |
| Delete | Remove an entry |
Health checks
| Action | Description |
|---|---|
| Liveness | Confirm the API responds |
| Deep check | Confirm the database connection as well |
Common rules
Deletion
Deleting does not immediately remove the data; it is marked as deleted, so an accidental deletion still leaves a record.
The exception is a blog left with an empty body after a failed generation, which is removed completely โ leaving it in the list would get in the way of regenerating.
Listing
Lists support page size and page switching. They are ordered by most recently updated by default (the race list is ordered by most recent race date).
Asynchronous work
AI generation requests (articles, blogs, thumbnails) return as soon as they are accepted; the actual work runs in the background. Completion shows up as a status change ("generating" โ "draft").
Related-information generation is the exception: it is synchronous and returns the updated blog immediately.
Related features
- Article Generation: AI-generated 10-second race result summaries
- Blog Generation: rewriting past blogs and writing race recaps / predictions
- Thumbnail Generation: creating thumbnails from race videos