{"openapi":"3.1.0","info":{"title":"FastAPI","version":"0.1.0"},"paths":{"/login":{"get":{"summary":"Login Form","description":"Show the login page, or bounce on when already logged in.","operationId":"login_form_login_get","parameters":[{"name":"next","in":"query","required":false,"schema":{"type":"string","default":"/stalemate/dashboard","title":"Next"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/auth/github":{"get":{"summary":"Github Start","description":"Send the browser to GitHub to log in.","operationId":"github_start_auth_github_get","parameters":[{"name":"next","in":"query","required":false,"schema":{"type":"string","default":"/stalemate/dashboard","title":"Next"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/auth/github/callback":{"get":{"summary":"Github Callback","description":"Finish the GitHub round trip: check the state, the account, keep the token.","operationId":"github_callback_auth_github_callback_get","parameters":[{"name":"code","in":"query","required":false,"schema":{"type":"string","default":"","title":"Code"}},{"name":"state","in":"query","required":false,"schema":{"type":"string","default":"","title":"State"}},{"name":"error","in":"query","required":false,"schema":{"type":"string","default":"","title":"Error"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/logout":{"post":{"summary":"Logout","description":"Forget the session. The stored GitHub token stays: background syncing should\nnot stop because a browser logged out.","operationId":"logout_logout_post","requestBody":{"content":{"application/x-www-form-urlencoded":{"schema":{"$ref":"#/components/schemas/Body_logout_logout_post"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/bench/":{"get":{"summary":"List Bench","description":"Every recorded target, with its measurements.","operationId":"list_bench_ollama_bench__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"summary":"Create Target","description":"Create a target, or update the one that already has this model+tag.","operationId":"create_target_ollama_bench__post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TargetIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/bench":{"get":{"summary":"List Bench","description":"Every recorded target, with its measurements.","operationId":"list_bench_ollama_bench_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"summary":"Create Target","description":"Create a target, or update the one that already has this model+tag.","operationId":"create_target_ollama_bench_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TargetIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/bench/lookup":{"get":{"summary":"Lookup Bench","description":"Resolve a model+tag to its target.","operationId":"lookup_bench_ollama_bench_lookup_get","parameters":[{"name":"model","in":"query","required":true,"schema":{"type":"string","title":"Model"}},{"name":"tag","in":"query","required":false,"schema":{"type":"string","default":"latest","title":"Tag"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/bench/missing":{"get":{"summary":"Missing Bench","description":"Catalogue models that fit in VRAM and have never been benchmarked.\n\nOnly tag sizes already in the week-long disk cache are considered, so this\nnever triggers a scrape of its own; `unresolved` counts the models whose\nsizes the browser sweep has not fetched yet.","operationId":"missing_bench_ollama_bench_missing_get","parameters":[{"name":"sort","in":"query","required":false,"schema":{"type":"string","default":"newest","title":"Sort"}},{"name":"vram","in":"query","required":false,"schema":{"type":"number","default":0,"title":"Vram"}},{"name":"headroom","in":"query","required":false,"schema":{"type":"number","default":0,"title":"Headroom"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/bench/{target_id}":{"patch":{"summary":"Update Target","description":"Change the fields of one target.","operationId":"update_target_ollama_bench__target_id__patch","parameters":[{"name":"target_id","in":"path","required":true,"schema":{"type":"integer","title":"Target Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/TargetIn"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"delete":{"summary":"Delete Target","description":"Remove a target and everything measured for it.","operationId":"delete_target_ollama_bench__target_id__delete","parameters":[{"name":"target_id","in":"path","required":true,"schema":{"type":"integer","title":"Target Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/bench/{target_id}/measurement":{"put":{"summary":"Save Measurement","description":"Store one language of one run, replacing what was there.","operationId":"save_measurement_ollama_bench__target_id__measurement_put","parameters":[{"name":"target_id","in":"path","required":true,"schema":{"type":"integer","title":"Target Id"}}],"requestBody":{"required":true,"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MeasurementIn"}}}},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"delete":{"summary":"Delete Measurement","description":"Forget one language of one run.","operationId":"delete_measurement_ollama_bench__target_id__measurement_delete","parameters":[{"name":"target_id","in":"path","required":true,"schema":{"type":"integer","title":"Target Id"}},{"name":"run_kind","in":"query","required":true,"schema":{"type":"string","title":"Run Kind"}},{"name":"language","in":"query","required":true,"schema":{"type":"string","title":"Language"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/":{"get":{"summary":"Dashboard Page","description":"The page; it loads its data from /stalemate/dashboard/data.","operationId":"dashboard_page_stalemate_dashboard__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/dashboard":{"get":{"summary":"Dashboard Page","description":"The page; it loads its data from /stalemate/dashboard/data.","operationId":"dashboard_page_stalemate_dashboard_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/dashboard/data":{"get":{"summary":"Dashboard Data","description":"Every work item, plus what the pickers need (tasks, projects, repositories).","operationId":"dashboard_data_stalemate_dashboard_data_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/dashboard/refresh":{"post":{"summary":"Refresh","description":"Sync with GitHub and Odoo now, instead of waiting for the next ten minutes.","operationId":"refresh_stalemate_dashboard_refresh_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/dashboard/link":{"post":{"summary":"Link","description":"Link (or explicitly unlink, with an empty target) a branch or repository.","operationId":"link_stalemate_dashboard_link_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/link/reset":{"post":{"summary":"Link Reset","description":"Undo a manual link or unlink.","operationId":"link_reset_stalemate_dashboard_link_reset_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/LinkResetIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/park":{"post":{"summary":"Park","description":"Snooze or hide an item, a repository or a project.","operationId":"park_stalemate_dashboard_park_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ParkIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/unpark":{"post":{"summary":"Unpark","description":"Bring a snoozed or hidden thing back.","operationId":"unpark_stalemate_dashboard_unpark_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/UnparkIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/plan":{"post":{"summary":"Plan","description":"Set when an item is meant to happen: an own deadline, a stretch on the timeline, or both.","operationId":"plan_stalemate_dashboard_plan_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/PlanIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/order":{"post":{"summary":"Order","description":"Store the order items were dragged into, for the custom sort.","operationId":"order_stalemate_dashboard_order_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OrderIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/action":{"post":{"summary":"Queue Action","description":"Queue a stalemate action. The worker does not run these yet; they show as\nqueued on the dashboard and can be cancelled there.","operationId":"queue_action_stalemate_dashboard_action_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/ActionIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/action/{job_id}/cancel":{"post":{"summary":"Cancel Action","description":"Withdraw a queued action.","operationId":"cancel_action_stalemate_dashboard_action__job_id__cancel_post","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"integer","title":"Job Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/merge":{"post":{"summary":"Merge","description":"Merge a pull request with the logged-in account's token.","operationId":"merge_stalemate_dashboard_merge_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/MergeIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/dashboard/branch/delete":{"post":{"summary":"Delete Branch","description":"Delete one of my branches on GitHub, typically one whose PR was merged.\n\nOnly branches the dashboard lists (so mine, and never a default branch):\nthis is a cleanup button, not a general way to delete refs.","operationId":"delete_branch_stalemate_dashboard_branch_delete_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/BranchIn"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/deepswe/":{"get":{"summary":"Deepswe Home","description":"Render the DeepSWE score-vs-cost chart page.","operationId":"deepswe_home_deepswe__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/deepswe/data":{"get":{"summary":"Deepswe Data","description":"Return the upstream leaderboard JSON from a short-lived in-memory cache.","operationId":"deepswe_data_deepswe_data_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/":{"get":{"summary":"Get Routes","description":"Route that retrieves a list of unique route paths registered in the application.\n\nArgs:\n    request (Request): The request object.\n\nReturns:\n    Response: A rendered index containing the registered route paths and descriptions.","operationId":"get_routes__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"summary":"Generate","description":"Generate an open graph image for an OpengraphRequest.","operationId":"generate__post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpengraphRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ping":{"get":{"summary":"Ping","description":"Endpoint for Health check","operationId":"ping_ping_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/savings-graph":{"get":{"summary":"Savings Graph","description":"Route that serves a savings graph image. It checks a cache for a fresh     image and generates a new one if needed.\n\nArgs:\n    _: Request: The request object (unused in this function).\n    secret (str): token so not everyone can see my savings :)\n    cache (TTLCache[str, bytes]): A cache object for storing and retrieving graph images.\n    design: new (default) or old\n    uncache: set to 1 to force invalidate cache\n\nReturns:\n    Response: A FastAPI response containing the image data.","operationId":"savings_graph_savings_graph_get","parameters":[{"name":"secret","in":"query","required":false,"schema":{"type":"string","default":"","title":"Secret"}},{"name":"design","in":"query","required":false,"schema":{"type":"string","default":"new","title":"Design"}},{"name":"uncache","in":"query","required":false,"schema":{"type":"string","default":"0","title":"Uncache"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/":{"get":{"summary":"Ollama Home","description":"Render the \"which Ollama models fit my GPU\" page.","operationId":"ollama_home_ollama__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/ollama/catalogue":{"get":{"summary":"Ollama Catalogue","description":"List every published model, from an hourly cache of ollama.com/library.","operationId":"ollama_catalogue_ollama_catalogue_get","parameters":[{"name":"sort","in":"query","required":false,"schema":{"type":"string","default":"newest","title":"Sort"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/ollama/variants":{"get":{"summary":"Ollama Variants","description":"Return the tags and download sizes of up to a dozen models.","operationId":"ollama_variants_ollama_variants_get","parameters":[{"name":"models","in":"query","required":true,"schema":{"type":"array","items":{"type":"string"},"title":"Models"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/opengraph/demo":{"get":{"summary":"Demo","description":"Generate a demo opengraph image.","operationId":"demo_opengraph_demo_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/opengraph/generate":{"get":{"summary":"Generate","description":"Generate an open graph image for an OpengraphRequest.","operationId":"generate_opengraph_generate_get","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpengraphRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"summary":"Generate","description":"Generate an open graph image for an OpengraphRequest.","operationId":"generate_opengraph_generate_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpengraphRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/generate":{"get":{"summary":"Generate","description":"Generate an open graph image for an OpengraphRequest.","operationId":"generate_generate_get","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpengraphRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"post":{"summary":"Generate","description":"Generate an open graph image for an OpengraphRequest.","operationId":"generate_generate_post","requestBody":{"content":{"application/json":{"schema":{"$ref":"#/components/schemas/OpengraphRequest"}}},"required":true},"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/jobs":{"get":{"summary":"Get Jobs","description":"List all jobs and its next execution time.","operationId":"get_jobs_jobs_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/jobs/{job_id}":{"get":{"summary":"Get Job","description":"Get task info about a specific job id.","operationId":"get_job_jobs__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","title":"Job Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/results":{"get":{"summary":"Results All","description":"Get all results for all jobs.","operationId":"results_all_results_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/results/{job_id}":{"get":{"summary":"Results","description":"Get all results for a specific job id.","operationId":"results_results__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"string","title":"Job Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/debug":{"get":{"summary":"Debug","description":"Push the newest task result to Notion and return the result.","operationId":"debug_debug_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/execute/test-discord":{"get":{"summary":"Test Discord Form","description":"Show a button that sends the Discord test notification, without sending anything.\n\nOpening a URL must not send a message: browsers fetch address-bar suggestions\nahead of time and link previews fetch pasted URLs, and each of those GETs used\nto post a test notification. Only the POST from this form sends one.","operationId":"test_discord_form_execute_test_discord_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}},"post":{"summary":"Test Discord","description":"Send a test notification to Discord, to check the bot token and channel.\n\nNot a scheduled job (so it never fires on its own) and it touches no monitor\nstate: it only exercises the same shared discord module the monitors use.\nPOST only, see `test_discord_form`.\n\nReturns:\n    Response: Whether Discord is configured and whether it accepted the message.","operationId":"test_discord_execute_test_discord_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/execute/":{"get":{"summary":"List Executable Jobs","description":"List all active jobs (with URL to execute the job from the web).","operationId":"list_executable_jobs_execute__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/execute/{job}":{"get":{"summary":"Execute Job","description":"Execute a scheduled job and handle its result or exceptions.\n\nArgs:\n    _: Request: The request object (unused in this function).\n    job (str): The name of the job to execute.\n    bg (BackgroundTasks): BackgroundTasks object to queue background tasks.\n\nReturns:\n    Response: A JSON response with the result of the job or an error message.\n\nRaises:\n    abort (Exception): If the specified job is not found.\n    Exception: If an unexpected exception occurs during job execution.\n\nExample:\n    # Execute a scheduled job named \"my_job\" and handle its result or exceptions.\n    response = await execute_job(Request(), \"my_job\", BackgroundTasks())","operationId":"execute_job_execute__job__get","parameters":[{"name":"job","in":"path","required":true,"schema":{"type":"string","title":"Job"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/food-regenerate":{"get":{"summary":"Daily Fridge Manual","description":"Manually run the 'daily fridge' task.","operationId":"daily_fridge_manual_food_regenerate_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/":{"get":{"summary":"Stalemate Home","description":"Render the overview.","operationId":"stalemate_home_stalemate__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/data":{"get":{"summary":"Stalemate Data","description":"The same state as JSON, for anything that would rather not scrape the page.","operationId":"stalemate_data_stalemate_data_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/scan":{"post":{"summary":"Trigger Scan","description":"Rescan every repository now, instead of waiting for Monday.","operationId":"trigger_scan_stalemate_scan_post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}}}}},"/stalemate/run/{task}/{owner}/{repo}":{"post":{"summary":"Trigger Fix","description":"Hand one task on one repository to an agent now.\n\nThe worker still applies its own guardrails - an open pull request on that\ntask's branch, a missing scan, an unknown task - so this only decides *when*\nsomething is attempted, never *whether* the result is trustworthy.\n\nArgs:\n    task (str): Which migration.\n    owner (str): The GitHub user or organisation.\n    repo (str): The repository name.\n    agent (str): Run it on this agent specifically. Omitted is the default\n        everything else uses: whichever agent is healthy, failing over to\n        the other. A named one is pinned, health and failover both skipped.\nReturns:\n    Response: The queued job.\n\nRaises:\n    HTTPException: 400 when `agent` is not an agent. Falling back to \"any\"\n        on a typo would silently answer a different question than the one\n        the picker was used to ask. 409 when this repository and task are\n        already queued or running: the page disables the button for that,\n        but a direct POST would otherwise queue a second one.","operationId":"trigger_fix_stalemate_run__task___owner___repo__post","parameters":[{"name":"task","in":"path","required":true,"schema":{"type":"string","title":"Task"}},{"name":"owner","in":"path","required":true,"schema":{"type":"string","title":"Owner"}},{"name":"repo","in":"path","required":true,"schema":{"type":"string","title":"Repo"}},{"name":"agent","in":"query","required":false,"schema":{"type":"string","default":"","title":"Agent"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/exclude/{owner}/{repo}":{"post":{"summary":"Exclude Repository","description":"Leave one repository out of future scans and fixes.\n\nArgs:\n    owner: The GitHub owner from the current scan.\n    repo: The repository name from the current scan.\n\nReturns:\n    The exclusion row.\n\nRaises:\n    HTTPException: 409 when the page is stale and the repository can no\n        longer be excluded from its current scan row.","operationId":"exclude_repository_stalemate_exclude__owner___repo__post","parameters":[{"name":"owner","in":"path","required":true,"schema":{"type":"string","title":"Owner"}},{"name":"repo","in":"path","required":true,"schema":{"type":"string","title":"Repo"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/include/{owner}/{repo}":{"post":{"summary":"Include Repository","description":"Include an excluded repository in the next scan.\n\nArgs:\n    owner: The GitHub owner to include again.\n    repo: The repository name to include again.\n\nReturns:\n    A confirmation object.\n\nRaises:\n    HTTPException: 409 when the page is stale and the exclusion is gone.","operationId":"include_repository_stalemate_include__owner___repo__post","parameters":[{"name":"owner","in":"path","required":true,"schema":{"type":"string","title":"Owner"}},{"name":"repo","in":"path","required":true,"schema":{"type":"string","title":"Repo"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/stalemate/log/{job_id}":{"get":{"summary":"Job Log","description":"The tail of one job's agent transcript.\n\nArgs:\n    job_id (int): The job id.\n\nReturns:\n    Response: Plain text, or a note when there is nothing to show.","operationId":"job_log_stalemate_log__job_id__get","parameters":[{"name":"job_id","in":"path","required":true,"schema":{"type":"integer","title":"Job Id"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/tts/":{"get":{"summary":"Home Tts","description":"Home route for the TTS (Text-to-Speech) service.\n\nReturns:\n    tuple[str, int]: A tuple containing a message and an HTTP status code (e.g., 400).","operationId":"home_tts_tts__get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"prefixItems":[{"type":"string"},{"type":"integer"}],"type":"array","maxItems":2,"minItems":2,"title":"Response Home Tts Tts  Get"}}}}}},"post":{"summary":"Home Tts","description":"Home route for the TTS (Text-to-Speech) service.\n\nReturns:\n    tuple[str, int]: A tuple containing a message and an HTTP status code (e.g., 400).","operationId":"home_tts_tts__post","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"prefixItems":[{"type":"string"},{"type":"integer"}],"type":"array","maxItems":2,"minItems":2,"title":"Response Home Tts Tts  Post"}}}}}}},"/tts/{text}":{"post":{"summary":"Generate Tts","description":"Route to generate TTS based on the provided text.\n\nArgs:\n    text (str): The input text for TTS generation.\n\nReturns:\n    None\n\nRaises:\n    abort (Exception): If encoding type is not specified.\n\nNotes:\n    - This route is used for text without specifying the encoding type.\n    - It raises an error if the encoding type is not provided in the route.\n\nExample:\n    # Access this route to generate TTS from raw text:\n    generate_tts(\"Hello World\")","operationId":"generate_tts_tts__text__post","parameters":[{"name":"text","in":"path","required":true,"schema":{"type":"string","title":"Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"get":{"summary":"Generate Tts","description":"Route to generate TTS based on the provided text.\n\nArgs:\n    text (str): The input text for TTS generation.\n\nReturns:\n    None\n\nRaises:\n    abort (Exception): If encoding type is not specified.\n\nNotes:\n    - This route is used for text without specifying the encoding type.\n    - It raises an error if the encoding type is not provided in the route.\n\nExample:\n    # Access this route to generate TTS from raw text:\n    generate_tts(\"Hello World\")","operationId":"generate_tts_tts__text__get","parameters":[{"name":"text","in":"path","required":true,"schema":{"type":"string","title":"Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/tts/raw/{text}":{"post":{"summary":"Generate Tts Raw","description":"Route to generate TTS from raw (unencoded) text.\n\nArgs:\n    text (str): The input text for TTS generation.\n\nReturns:\n    Response: A FastAPI response containing the TTS audio.\n\nExample:\n    # Access this route to generate TTS from raw text:\n    generate_tts_raw(\"Hello World\")","operationId":"generate_tts_raw_tts_raw__text__post","parameters":[{"name":"text","in":"path","required":true,"schema":{"type":"string","title":"Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"get":{"summary":"Generate Tts Raw","description":"Route to generate TTS from raw (unencoded) text.\n\nArgs:\n    text (str): The input text for TTS generation.\n\nReturns:\n    Response: A FastAPI response containing the TTS audio.\n\nExample:\n    # Access this route to generate TTS from raw text:\n    generate_tts_raw(\"Hello World\")","operationId":"generate_tts_raw_tts_raw__text__get","parameters":[{"name":"text","in":"path","required":true,"schema":{"type":"string","title":"Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/tts/b64/{encoded_text}":{"post":{"summary":"Generate Tts B64","description":"Route to generate TTS from base64 encoded text.\n\nArgs:\n    encoded_text (str): The base64 encoded text for TTS generation.\n\nReturns:\n    Response: A FastAPI response containing the TTS audio.\n\nExample:\n    # Access this route to generate TTS from base64 encoded text:\n    generate_tts_b64(\"aGk-\")","operationId":"generate_tts_b64_tts_b64__encoded_text__post","parameters":[{"name":"encoded_text","in":"path","required":true,"schema":{"type":"string","title":"Encoded Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"get":{"summary":"Generate Tts B64","description":"Route to generate TTS from base64 encoded text.\n\nArgs:\n    encoded_text (str): The base64 encoded text for TTS generation.\n\nReturns:\n    Response: A FastAPI response containing the TTS audio.\n\nExample:\n    # Access this route to generate TTS from base64 encoded text:\n    generate_tts_b64(\"aGk-\")","operationId":"generate_tts_b64_tts_b64__encoded_text__get","parameters":[{"name":"encoded_text","in":"path","required":true,"schema":{"type":"string","title":"Encoded Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/tts/b58/{encoded_text}":{"post":{"summary":"Generate Tts B58","description":"Route to generate TTS from base58 encoded text.\n\nArgs:\n    encoded_text (str): The base58 encoded text for TTS generation.\n\nReturns:\n    Response: A FastAPI response containing the TTS audio.\n\nExample:\n    # Access this route to generate TTS from base58 encoded text:\n    generate_tts_b58(\"8wr\")","operationId":"generate_tts_b58_tts_b58__encoded_text__post","parameters":[{"name":"encoded_text","in":"path","required":true,"schema":{"type":"string","title":"Encoded Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}},"get":{"summary":"Generate Tts B58","description":"Route to generate TTS from base58 encoded text.\n\nArgs:\n    encoded_text (str): The base58 encoded text for TTS generation.\n\nReturns:\n    Response: A FastAPI response containing the TTS audio.\n\nExample:\n    # Access this route to generate TTS from base58 encoded text:\n    generate_tts_b58(\"8wr\")","operationId":"generate_tts_b58_tts_b58__encoded_text__get","parameters":[{"name":"encoded_text","in":"path","required":true,"schema":{"type":"string","title":"Encoded Text"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/python/supported":{"get":{"summary":"Python Supported","description":"Retrieve a list of officially supported Python versions.\n\nReturns:\n    list[str]: A list of officially supported Python versions.","operationId":"python_supported_python_supported_get","responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"items":{"type":"string"},"type":"array","title":"Response Python Supported Python Supported Get"}}}}}}},"/python/user/{username}":{"get":{"summary":"Packages For User","description":"Retrieve information about packages associated with a specific user on PyPI.\n\nArgs:\n    username (str): The username of the PyPI user.\n\nReturns:\n    dict[str, dict[str, list[str]]]: A dictionary containing package information,\n        including supported, missing, and deprecated Python versions.","operationId":"packages_for_user_python_user__username__get","parameters":[{"name":"username","in":"path","required":true,"schema":{"type":"string","title":"Username"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":{"type":"object","additionalProperties":{"type":"array","items":{"type":"string"}}},"title":"Response Packages For User Python User  Username  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/python/package/{package}":{"get":{"summary":"Package Info","description":"Retrieve information about a specific package on PyPI, including its supported Python versions.\n\nArgs:\n    package (str): The name of the package on PyPI.\n\nReturns:\n    dict[str, list[str]]: A dictionary containing information about\n        supported, missing, and deprecated Python versions for the package.","operationId":"package_info_python_package__package__get","parameters":[{"name":"package","in":"path","required":true,"schema":{"type":"string","title":"Package"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{"type":"object","additionalProperties":{"type":"array","items":{"type":"string"}},"title":"Response Package Info Python Package  Package  Get"}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/youtube/":{"get":{"summary":"Yt Home","description":"Handles the GET request to the '/youtube' endpoint.\n\nIt takes a URL parameter with a default value of an empty string.\nIt renders the 'youtube.html' template with the provided URL.\n\nArgs:\n    url (str): The URL to be rendered in the 'youtube.html' template. Defaults to an empty string.\n\nReturns:\n    HTMLResponse: The rendered 'youtube.html' template with the provided URL.","operationId":"yt_home_youtube__get","parameters":[{"name":"v","in":"query","required":false,"schema":{"type":"string","default":"","title":"V"}},{"name":"url","in":"query","required":false,"schema":{"type":"string","default":"","title":"Url"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/youtube/watch":{"get":{"summary":"Yt Watch","description":"Handles the GET request to the '/youtube/watch' endpoint. It takes an optional URL parameter.\n\nUsed via HTMX by /youtube\n\nIf the URL is provided and valid, it fetches the streaming URLs for the video and audio of the YouTube video\nand renders them in the 'video.html' template. If the URL is not provided or invalid, it returns an empty response\nor an error message.\n\nArgs:\n    url (str | None): The URL of the YouTube video to watch. Defaults to None.\n\nReturns:\n    HTMLResponse: The rendered 'video.html' template with the video and audio streaming URLs if the URL is valid,\n    an empty response if the URL is not provided, or an error message if the URL is invalid.","operationId":"yt_watch_youtube_watch_get","parameters":[{"name":"v","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"V"}},{"name":"url","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/youtube/watch/{url}":{"get":{"summary":"Yt Watch","description":"Handles the GET request to the '/youtube/watch' endpoint. It takes an optional URL parameter.\n\nUsed via HTMX by /youtube\n\nIf the URL is provided and valid, it fetches the streaming URLs for the video and audio of the YouTube video\nand renders them in the 'video.html' template. If the URL is not provided or invalid, it returns an empty response\nor an error message.\n\nArgs:\n    url (str | None): The URL of the YouTube video to watch. Defaults to None.\n\nReturns:\n    HTMLResponse: The rendered 'video.html' template with the video and audio streaming URLs if the URL is valid,\n    an empty response if the URL is not provided, or an error message if the URL is invalid.","operationId":"yt_watch_youtube_watch__url__get","parameters":[{"name":"url","in":"path","required":true,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Url"}},{"name":"v","in":"query","required":false,"schema":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"V"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}},"/youtube/stream":{"get":{"summary":"Yt Stream","description":"Proxy an extracted Google video stream so its signed URL stays server-side.","operationId":"yt_stream_youtube_stream_get","parameters":[{"name":"url","in":"query","required":true,"schema":{"type":"string","title":"Url"}}],"responses":{"200":{"description":"Successful Response","content":{"application/json":{"schema":{}}}},"422":{"description":"Validation Error","content":{"application/json":{"schema":{"$ref":"#/components/schemas/HTTPValidationError"}}}}}}}},"components":{"schemas":{"ActionIn":{"properties":{"action":{"type":"string","title":"Action"},"repo":{"type":"string","title":"Repo"},"branch":{"type":"string","title":"Branch","default":""},"pr_url":{"type":"string","title":"Pr Url","default":""}},"type":"object","required":["action","repo"],"title":"ActionIn","description":"Queue a stalemate action for a branch or pull request."},"Body_logout_logout_post":{"properties":{"next_url":{"type":"string","title":"Next Url","default":"/"}},"type":"object","title":"Body_logout_logout_post"},"BranchIn":{"properties":{"repo":{"type":"string","title":"Repo"},"branch":{"type":"string","title":"Branch"}},"type":"object","required":["repo","branch"],"title":"BranchIn","description":"One branch, e.g. to delete once its pull request is merged."},"HTTPValidationError":{"properties":{"detail":{"items":{"$ref":"#/components/schemas/ValidationError"},"type":"array","title":"Detail"}},"type":"object","title":"HTTPValidationError"},"LinkIn":{"properties":{"kind":{"type":"string","enum":["branch-task","repo-project"],"title":"Kind"},"source":{"type":"string","title":"Source"},"target":{"type":"string","title":"Target","default":""}},"type":"object","required":["kind","source"],"title":"LinkIn","description":"Link a branch to a task, or a repository to a project."},"LinkResetIn":{"properties":{"kind":{"type":"string","enum":["branch-task","repo-project"],"title":"Kind"},"source":{"type":"string","title":"Source"}},"type":"object","required":["kind","source"],"title":"LinkResetIn","description":"Forget a link so auto-linking decides again."},"MeasurementIn":{"properties":{"run_kind":{"type":"string","title":"Run Kind"},"language":{"type":"string","title":"Language"},"samples":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Samples"},"correctness":{"anyOf":[{"type":"number","maximum":1.0,"minimum":0.0},{"type":"null"}],"title":"Correctness"},"duration_s":{"anyOf":[{"type":"number","minimum":0.0},{"type":"null"}],"title":"Duration S"}},"type":"object","required":["run_kind","language"],"title":"MeasurementIn","description":"One language of one run."},"MergeIn":{"properties":{"repo":{"type":"string","title":"Repo"},"number":{"type":"integer","title":"Number"},"head_sha":{"type":"string","pattern":"^[0-9a-fA-F]{40}$","title":"Head Sha"},"method":{"type":"string","enum":["merge","squash","rebase"],"title":"Method","default":"merge"}},"type":"object","required":["repo","number","head_sha"],"title":"MergeIn","description":"Merge a pull request."},"OpengraphRequest":{"properties":{"icon":{"type":"string","title":"Icon"},"title":{"type":"string","title":"Title"},"img":{"type":"string","title":"Img"},"template":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Template"}},"type":"object","required":["icon","title","img"],"title":"OpengraphRequest","description":"Required request data to generate an opengraph image with."},"OrderIn":{"properties":{"items":{"items":{"items":{"type":"string"},"type":"array"},"type":"array","maxItems":1000,"minItems":1,"title":"Items"}},"type":"object","required":["items"],"title":"OrderIn","description":"A hand-picked order: every item's keys, first to last."},"ParkIn":{"properties":{"scope":{"type":"string","enum":["item","repo","project"],"title":"Scope"},"ref":{"type":"string","title":"Ref"},"until":{"anyOf":[{"type":"string","format":"date-time"},{"type":"null"}],"title":"Until"}},"type":"object","required":["scope","ref"],"title":"ParkIn","description":"Snooze something until a moment, or (without `until`) hide it for good."},"PlanIn":{"properties":{"keys":{"items":{"type":"string"},"type":"array","maxItems":5,"minItems":1,"title":"Keys"},"deadline":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Deadline"},"start":{"anyOf":[{"type":"string","format":"date"},{"type":"null"}],"title":"Start"},"days":{"type":"integer","maximum":90.0,"minimum":1.0,"title":"Days","default":1}},"type":"object","required":["keys"],"title":"PlanIn","description":"An item's own deadline and plan, as a whole: what is left out is cleared."},"TargetIn":{"properties":{"model":{"type":"string","title":"Model","default":""},"tag":{"type":"string","title":"Tag","default":""},"source":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Source"},"status":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Status"},"memory_bytes":{"anyOf":[{"type":"integer"},{"type":"null"}],"title":"Memory Bytes"},"gpu_fraction":{"anyOf":[{"type":"number","maximum":1.0,"minimum":0.0},{"type":"null"}],"title":"Gpu Fraction"},"notes":{"anyOf":[{"type":"string"},{"type":"null"}],"title":"Notes"}},"type":"object","title":"TargetIn","description":"A target to create, or the fields of one to change."},"UnparkIn":{"properties":{"scope":{"type":"string","enum":["item","repo","project"],"title":"Scope"},"ref":{"type":"string","title":"Ref"}},"type":"object","required":["scope","ref"],"title":"UnparkIn","description":"Bring something back."},"ValidationError":{"properties":{"loc":{"items":{"anyOf":[{"type":"string"},{"type":"integer"}]},"type":"array","title":"Location"},"msg":{"type":"string","title":"Message"},"type":{"type":"string","title":"Error Type"}},"type":"object","required":["loc","msg","type"],"title":"ValidationError"}}}}