first
This commit is contained in:
@@ -0,0 +1,584 @@
|
||||
openapi: 3.1.0
|
||||
info:
|
||||
title: Hermes API
|
||||
version: 0.1.0
|
||||
description: Native betting study prototype API.
|
||||
servers:
|
||||
- url: http://localhost:3000
|
||||
paths:
|
||||
/health:
|
||||
get:
|
||||
summary: Health check
|
||||
responses:
|
||||
'200':
|
||||
description: Service health
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/HealthResponse'
|
||||
/api/v1/session/start:
|
||||
post:
|
||||
summary: Start a session
|
||||
requestBody:
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/SessionStartRequest'
|
||||
responses:
|
||||
'201':
|
||||
description: Session started
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/SessionResponse'
|
||||
/api/v1/session/end:
|
||||
post:
|
||||
summary: End the current session
|
||||
responses:
|
||||
'200':
|
||||
description: Session ended
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/SessionResponse'
|
||||
/api/v1/session/me:
|
||||
get:
|
||||
summary: Inspect the current session
|
||||
responses:
|
||||
'200':
|
||||
description: Current session snapshot
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/SessionResponse'
|
||||
/api/v1/feed/next:
|
||||
get:
|
||||
summary: Fetch the next round
|
||||
responses:
|
||||
'200':
|
||||
description: Next event payload
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/Event'
|
||||
/api/v1/events/{event_id}:
|
||||
get:
|
||||
summary: Fetch an event
|
||||
parameters:
|
||||
- name: event_id
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
format: uuid
|
||||
responses:
|
||||
'200':
|
||||
description: Event
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/Event'
|
||||
/api/v1/events/{event_id}/manifest:
|
||||
get:
|
||||
summary: Fetch the event manifest
|
||||
parameters:
|
||||
- name: event_id
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
format: uuid
|
||||
responses:
|
||||
'200':
|
||||
description: Manifest
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/EventManifest'
|
||||
/api/v1/events/{event_id}/markets:
|
||||
get:
|
||||
summary: List markets for an event
|
||||
parameters:
|
||||
- name: event_id
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
format: uuid
|
||||
responses:
|
||||
'200':
|
||||
description: Markets
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/Market'
|
||||
/api/v1/markets/{market_id}/odds/current:
|
||||
get:
|
||||
summary: Fetch current odds for a market
|
||||
parameters:
|
||||
- name: market_id
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
format: uuid
|
||||
responses:
|
||||
'200':
|
||||
description: Current odds
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/OddsVersion'
|
||||
/api/v1/stream:
|
||||
get:
|
||||
summary: Live odds and state stream
|
||||
responses:
|
||||
'200':
|
||||
description: Server-sent events stream
|
||||
content:
|
||||
text/event-stream:
|
||||
schema:
|
||||
type: string
|
||||
/api/v1/bets/intent:
|
||||
post:
|
||||
summary: Submit a bet intent
|
||||
requestBody:
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/BetIntentRequest'
|
||||
responses:
|
||||
'201':
|
||||
description: Bet intent result
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/BetIntentResponse'
|
||||
/api/v1/bets/{bet_intent_id}:
|
||||
get:
|
||||
summary: Fetch a bet intent
|
||||
parameters:
|
||||
- name: bet_intent_id
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
format: uuid
|
||||
responses:
|
||||
'200':
|
||||
description: Bet intent
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/BetIntentResponse'
|
||||
/api/v1/events/{event_id}/result:
|
||||
get:
|
||||
summary: Fetch event result
|
||||
parameters:
|
||||
- name: event_id
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
format: uuid
|
||||
responses:
|
||||
'200':
|
||||
description: Result payload
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/Settlement'
|
||||
/api/v1/analytics/batch:
|
||||
post:
|
||||
summary: Ingest analytics batch
|
||||
requestBody:
|
||||
required: true
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/AnalyticsBatchRequest'
|
||||
responses:
|
||||
'202':
|
||||
description: Accepted
|
||||
/api/v1/experiments/config:
|
||||
get:
|
||||
summary: Fetch experiment config
|
||||
responses:
|
||||
'200':
|
||||
description: Experiment config
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/ExperimentConfig'
|
||||
/api/v1/localization/{locale_code}:
|
||||
get:
|
||||
summary: Fetch a localization bundle
|
||||
parameters:
|
||||
- name: locale_code
|
||||
in: path
|
||||
required: true
|
||||
schema:
|
||||
type: string
|
||||
enum: [en, sv]
|
||||
responses:
|
||||
'200':
|
||||
description: Localization bundle
|
||||
content:
|
||||
application/json:
|
||||
schema:
|
||||
$ref: '#/components/schemas/LocalizationBundle'
|
||||
/api/v1/admin/events:
|
||||
post:
|
||||
summary: Create an event
|
||||
responses:
|
||||
'201':
|
||||
description: Created
|
||||
/api/v1/admin/markets:
|
||||
post:
|
||||
summary: Create a market
|
||||
responses:
|
||||
'201':
|
||||
description: Created
|
||||
/api/v1/admin/odds:
|
||||
post:
|
||||
summary: Publish odds
|
||||
responses:
|
||||
'201':
|
||||
description: Created
|
||||
/api/v1/admin/settlements:
|
||||
post:
|
||||
summary: Publish a settlement
|
||||
responses:
|
||||
'201':
|
||||
description: Created
|
||||
components:
|
||||
schemas:
|
||||
HealthResponse:
|
||||
type: object
|
||||
required: [status, service_name, environment, version, uptime_ms, database_ready, redis_ready]
|
||||
properties:
|
||||
status:
|
||||
type: string
|
||||
service_name:
|
||||
type: string
|
||||
environment:
|
||||
type: string
|
||||
version:
|
||||
type: string
|
||||
uptime_ms:
|
||||
type: integer
|
||||
database_ready:
|
||||
type: boolean
|
||||
redis_ready:
|
||||
type: boolean
|
||||
SessionStartRequest:
|
||||
type: object
|
||||
properties:
|
||||
locale_code:
|
||||
type: string
|
||||
device_platform:
|
||||
type: string
|
||||
device_model:
|
||||
type: string
|
||||
os_version:
|
||||
type: string
|
||||
app_version:
|
||||
type: string
|
||||
SessionResponse:
|
||||
type: object
|
||||
required: [session_id, user_id, started_at, experiment_variant, app_version, locale_code, device_platform]
|
||||
properties:
|
||||
session_id:
|
||||
type: string
|
||||
format: uuid
|
||||
user_id:
|
||||
type: string
|
||||
format: uuid
|
||||
started_at:
|
||||
type: string
|
||||
format: date-time
|
||||
ended_at:
|
||||
type: string
|
||||
format: date-time
|
||||
nullable: true
|
||||
experiment_variant:
|
||||
type: string
|
||||
app_version:
|
||||
type: string
|
||||
device_model:
|
||||
type: string
|
||||
nullable: true
|
||||
os_version:
|
||||
type: string
|
||||
nullable: true
|
||||
locale_code:
|
||||
type: string
|
||||
device_platform:
|
||||
type: string
|
||||
Event:
|
||||
type: object
|
||||
required: [id, sport_type, source_ref, title_en, title_sv, status, lock_at, settle_at]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
sport_type:
|
||||
type: string
|
||||
source_ref:
|
||||
type: string
|
||||
title_en:
|
||||
type: string
|
||||
title_sv:
|
||||
type: string
|
||||
status:
|
||||
type: string
|
||||
preview_start_ms:
|
||||
type: integer
|
||||
preview_end_ms:
|
||||
type: integer
|
||||
reveal_start_ms:
|
||||
type: integer
|
||||
reveal_end_ms:
|
||||
type: integer
|
||||
lock_at:
|
||||
type: string
|
||||
format: date-time
|
||||
settle_at:
|
||||
type: string
|
||||
format: date-time
|
||||
EventManifest:
|
||||
type: object
|
||||
properties:
|
||||
event:
|
||||
$ref: '#/components/schemas/Event'
|
||||
media:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/EventMedia'
|
||||
markets:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/Market'
|
||||
EventMedia:
|
||||
type: object
|
||||
required: [id, event_id, media_type, hls_master_url, duration_ms]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
event_id:
|
||||
type: string
|
||||
format: uuid
|
||||
media_type:
|
||||
type: string
|
||||
hls_master_url:
|
||||
type: string
|
||||
poster_url:
|
||||
type: string
|
||||
nullable: true
|
||||
duration_ms:
|
||||
type: integer
|
||||
preview_start_ms:
|
||||
type: integer
|
||||
preview_end_ms:
|
||||
type: integer
|
||||
reveal_start_ms:
|
||||
type: integer
|
||||
reveal_end_ms:
|
||||
type: integer
|
||||
Market:
|
||||
type: object
|
||||
required: [id, event_id, question_key, market_type, status, lock_at, settlement_rule_key]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
event_id:
|
||||
type: string
|
||||
format: uuid
|
||||
question_key:
|
||||
type: string
|
||||
market_type:
|
||||
type: string
|
||||
status:
|
||||
type: string
|
||||
lock_at:
|
||||
type: string
|
||||
format: date-time
|
||||
settlement_rule_key:
|
||||
type: string
|
||||
outcomes:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/Outcome'
|
||||
Outcome:
|
||||
type: object
|
||||
required: [id, market_id, outcome_code, label_key, sort_order]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
market_id:
|
||||
type: string
|
||||
format: uuid
|
||||
outcome_code:
|
||||
type: string
|
||||
label_key:
|
||||
type: string
|
||||
sort_order:
|
||||
type: integer
|
||||
OddsVersion:
|
||||
type: object
|
||||
required: [id, market_id, version_no, created_at, is_current]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
market_id:
|
||||
type: string
|
||||
format: uuid
|
||||
version_no:
|
||||
type: integer
|
||||
created_at:
|
||||
type: string
|
||||
format: date-time
|
||||
is_current:
|
||||
type: boolean
|
||||
odds:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/OutcomeOdds'
|
||||
OutcomeOdds:
|
||||
type: object
|
||||
required: [id, odds_version_id, outcome_id, decimal_odds, fractional_num, fractional_den]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
odds_version_id:
|
||||
type: string
|
||||
format: uuid
|
||||
outcome_id:
|
||||
type: string
|
||||
format: uuid
|
||||
decimal_odds:
|
||||
type: number
|
||||
fractional_num:
|
||||
type: integer
|
||||
fractional_den:
|
||||
type: integer
|
||||
BetIntentRequest:
|
||||
type: object
|
||||
required: [session_id, event_id, market_id, outcome_id, idempotency_key, client_sent_at]
|
||||
properties:
|
||||
session_id:
|
||||
type: string
|
||||
format: uuid
|
||||
event_id:
|
||||
type: string
|
||||
format: uuid
|
||||
market_id:
|
||||
type: string
|
||||
format: uuid
|
||||
outcome_id:
|
||||
type: string
|
||||
format: uuid
|
||||
idempotency_key:
|
||||
type: string
|
||||
client_sent_at:
|
||||
type: string
|
||||
format: date-time
|
||||
BetIntentResponse:
|
||||
type: object
|
||||
required: [id, accepted, acceptance_code, server_received_at]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
accepted:
|
||||
type: boolean
|
||||
acceptance_code:
|
||||
type: string
|
||||
accepted_odds_version_id:
|
||||
type: string
|
||||
format: uuid
|
||||
nullable: true
|
||||
server_received_at:
|
||||
type: string
|
||||
format: date-time
|
||||
Settlement:
|
||||
type: object
|
||||
required: [id, market_id, settled_at, winning_outcome_id]
|
||||
properties:
|
||||
id:
|
||||
type: string
|
||||
format: uuid
|
||||
market_id:
|
||||
type: string
|
||||
format: uuid
|
||||
settled_at:
|
||||
type: string
|
||||
format: date-time
|
||||
winning_outcome_id:
|
||||
type: string
|
||||
format: uuid
|
||||
AnalyticsBatchRequest:
|
||||
type: object
|
||||
required: [events]
|
||||
properties:
|
||||
events:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/AnalyticsEventInput'
|
||||
AnalyticsEventInput:
|
||||
type: object
|
||||
required: [event_name, occurred_at]
|
||||
properties:
|
||||
event_name:
|
||||
type: string
|
||||
occurred_at:
|
||||
type: string
|
||||
format: date-time
|
||||
attributes:
|
||||
type: array
|
||||
items:
|
||||
$ref: '#/components/schemas/AttributeInput'
|
||||
AttributeInput:
|
||||
type: object
|
||||
required: [key, value]
|
||||
properties:
|
||||
key:
|
||||
type: string
|
||||
value:
|
||||
type: string
|
||||
ExperimentConfig:
|
||||
type: object
|
||||
properties:
|
||||
variant:
|
||||
type: string
|
||||
feature_flags:
|
||||
type: object
|
||||
additionalProperties:
|
||||
type: boolean
|
||||
LocalizationBundle:
|
||||
type: object
|
||||
required: [locale_code, values]
|
||||
properties:
|
||||
locale_code:
|
||||
type: string
|
||||
values:
|
||||
type: object
|
||||
additionalProperties:
|
||||
type: string
|
||||
ErrorResponse:
|
||||
type: object
|
||||
required: [code, message]
|
||||
properties:
|
||||
code:
|
||||
type: string
|
||||
message:
|
||||
type: string
|
||||
Reference in New Issue
Block a user