Files
ShadowMountPlus/docs/openapi.yaml
T

571 lines
15 KiB
YAML

openapi: 3.1.2
info:
title: ShadowMount HTTP API
version: "1"
description: |
HTTP/JSON API exposed by the ShadowMountPlus payload. The service has no
authentication and should only be exposed on a trusted network.
servers:
- url: http://127.0.0.1:10101
description: Default loopback endpoint on the PS5
- url: http://{address}:{port}
description: Configured network endpoint
variables:
address:
default: 192.168.1.50
description: PS5 IPv4 address or hostname
port:
default: "10101"
description: Value of api_port
security: []
tags:
- name: Service
- name: Images
- name: Games
paths:
/api/v1/version:
options:
operationId: preflightVersion
summary: CORS preflight
tags: [Service]
responses:
"204":
$ref: "#/components/responses/Preflight"
post:
operationId: getVersion
summary: Get API version and capabilities
tags: [Service]
requestBody:
$ref: "#/components/requestBodies/EmptyRequest"
responses:
"200":
$ref: "#/components/responses/VersionSuccess"
"400":
$ref: "#/components/responses/BadRequest"
"411":
$ref: "#/components/responses/LengthRequired"
"413":
$ref: "#/components/responses/PayloadTooLarge"
"415":
$ref: "#/components/responses/UnsupportedMediaType"
"431":
$ref: "#/components/responses/HeadersTooLarge"
"500":
$ref: "#/components/responses/InternalError"
"501":
$ref: "#/components/responses/NotImplemented"
/api/v1/images:
options:
operationId: preflightImages
summary: CORS preflight
tags: [Images]
responses:
"204":
$ref: "#/components/responses/Preflight"
post:
operationId: listImages
summary: Get the complete image snapshot
tags: [Images]
requestBody:
$ref: "#/components/requestBodies/EmptyRequest"
responses:
"200":
$ref: "#/components/responses/ImagesSuccess"
"400":
$ref: "#/components/responses/BadRequest"
"411":
$ref: "#/components/responses/LengthRequired"
"413":
$ref: "#/components/responses/PayloadTooLarge"
"415":
$ref: "#/components/responses/UnsupportedMediaType"
"431":
$ref: "#/components/responses/HeadersTooLarge"
"500":
$ref: "#/components/responses/InternalError"
"501":
$ref: "#/components/responses/NotImplemented"
/api/v1/games:
options:
operationId: preflightGames
summary: CORS preflight
tags: [Games]
responses:
"204":
$ref: "#/components/responses/Preflight"
post:
operationId: listGames
summary: Get the complete game snapshot
tags: [Games]
requestBody:
$ref: "#/components/requestBodies/EmptyRequest"
responses:
"200":
$ref: "#/components/responses/GamesSuccess"
"400":
$ref: "#/components/responses/BadRequest"
"411":
$ref: "#/components/responses/LengthRequired"
"413":
$ref: "#/components/responses/PayloadTooLarge"
"415":
$ref: "#/components/responses/UnsupportedMediaType"
"431":
$ref: "#/components/responses/HeadersTooLarge"
"500":
$ref: "#/components/responses/InternalError"
"501":
$ref: "#/components/responses/NotImplemented"
/api/v1/games/mount:
options:
operationId: preflightMountGame
summary: CORS preflight
tags: [Games]
responses:
"204":
$ref: "#/components/responses/Preflight"
post:
operationId: mountGame
summary: Mount a managed game
tags: [Games]
requestBody:
$ref: "#/components/requestBodies/TitleRequest"
responses:
"200":
$ref: "#/components/responses/MountSuccess"
"400":
$ref: "#/components/responses/BadRequest"
"404":
$ref: "#/components/responses/NotFound"
"409":
$ref: "#/components/responses/Busy"
"411":
$ref: "#/components/responses/LengthRequired"
"413":
$ref: "#/components/responses/PayloadTooLarge"
"415":
$ref: "#/components/responses/UnsupportedMediaType"
"431":
$ref: "#/components/responses/HeadersTooLarge"
"500":
$ref: "#/components/responses/InternalError"
"501":
$ref: "#/components/responses/NotImplemented"
/api/v1/games/unmount:
options:
operationId: preflightUnmountGame
summary: CORS preflight
tags: [Games]
responses:
"204":
$ref: "#/components/responses/Preflight"
post:
operationId: unmountGame
summary: Unmount a managed game
tags: [Games]
requestBody:
$ref: "#/components/requestBodies/TitleRequest"
responses:
"200":
$ref: "#/components/responses/UnmountSuccess"
"400":
$ref: "#/components/responses/BadRequest"
"404":
$ref: "#/components/responses/NotFound"
"409":
$ref: "#/components/responses/Busy"
"411":
$ref: "#/components/responses/LengthRequired"
"413":
$ref: "#/components/responses/PayloadTooLarge"
"415":
$ref: "#/components/responses/UnsupportedMediaType"
"431":
$ref: "#/components/responses/HeadersTooLarge"
"500":
$ref: "#/components/responses/InternalError"
"501":
$ref: "#/components/responses/NotImplemented"
components:
requestBodies:
EmptyRequest:
required: true
content:
application/json:
schema:
type: object
example: {}
TitleRequest:
required: true
content:
application/json:
schema:
$ref: "#/components/schemas/TitleRequest"
headers:
AllowOrigin:
description: Browser origins allowed to access the API
schema:
type: string
const: "*"
AllowMethods:
description: Methods allowed by CORS preflight
schema:
type: string
const: POST, OPTIONS
AllowHeaders:
description: Request headers allowed by CORS preflight
schema:
type: string
const: Content-Type
AllowPrivateNetwork:
description: Private Network Access permission
schema:
type: string
const: "true"
MaxAge:
description: Number of seconds for which the preflight may be cached
schema:
type: integer
const: 86400
responses:
Preflight:
description: CORS preflight accepted
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
Access-Control-Allow-Methods:
$ref: "#/components/headers/AllowMethods"
Access-Control-Allow-Headers:
$ref: "#/components/headers/AllowHeaders"
Access-Control-Allow-Private-Network:
$ref: "#/components/headers/AllowPrivateNetwork"
Access-Control-Max-Age:
$ref: "#/components/headers/MaxAge"
VersionSuccess:
description: API version and capabilities
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/VersionResponse"
ImagesSuccess:
description: Complete image snapshot
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ImagesResponse"
GamesSuccess:
description: Complete game snapshot
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/GamesResponse"
MountSuccess:
description: Game mounted
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/MountResponse"
UnmountSuccess:
description: Game unmounted
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/UnmountResponse"
BadRequest:
description: Invalid HTTP request, JSON body or title ID
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
NotFound:
description: Managed title tracker was not found
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
Busy:
description: Runtime state does not currently permit the operation
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
example:
status: 16
error: Device busy
LengthRequired:
description: Content-Length is required
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
PayloadTooLarge:
description: JSON request body exceeds 4096 bytes
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
UnsupportedMediaType:
description: Content-Type is not application/json
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
HeadersTooLarge:
description: HTTP headers exceed 8192 bytes
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
InternalError:
description: Internal failure
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
NotImplemented:
description: Unsupported transfer encoding or runtime operation
headers:
Access-Control-Allow-Origin:
$ref: "#/components/headers/AllowOrigin"
content:
application/json:
schema:
$ref: "#/components/schemas/ErrorResponse"
schemas:
TitleId:
type: string
pattern: "^(CUSA|PPSA)[0-9]{5}$"
examples: [PPSA12345]
TitleRequest:
type: object
required: [title_id]
properties:
title_id:
$ref: "#/components/schemas/TitleId"
VersionResponse:
type: object
additionalProperties: false
required: [status, api_version, shadowmount_version, capabilities]
properties:
status:
type: integer
const: 0
api_version:
type: integer
const: 1
shadowmount_version:
type: string
capabilities:
type: array
items:
type: string
enum: [list_images, list_games, mount_game, unmount_game]
example: [list_images, list_games, mount_game, unmount_game]
Image:
type: object
additionalProperties: false
required:
- path
- mount_point
- size
- mtime_sec
- mtime_nsec
- unit_id
- backend
- complete
- source_available
- mapped
- mounted
properties:
path:
type: string
mount_point:
type: string
size:
type: integer
format: int64
minimum: 0
mtime_sec:
type: integer
format: int64
mtime_nsec:
type: integer
minimum: 0
maximum: 999999999
unit_id:
type: integer
minimum: -1
backend:
type: string
enum: [LVD, MD, UNKNOWN]
complete:
type: boolean
source_available:
type: boolean
mapped:
type: boolean
mounted:
type: boolean
ImagesResponse:
type: object
additionalProperties: false
required: [status, count, images]
properties:
status:
type: integer
const: 0
count:
type: integer
minimum: 0
images:
type: array
items:
$ref: "#/components/schemas/Image"
Game:
type: object
additionalProperties: false
required:
- path
- image_path
- title_id
- title_name
- installed
- managed
- mounted
- image_backed
- source_available
properties:
path:
type: string
image_path:
type: string
title_id:
$ref: "#/components/schemas/TitleId"
title_name:
type: string
installed:
type: boolean
managed:
type: boolean
mounted:
type: boolean
image_backed:
type: boolean
source_available:
type: boolean
GamesResponse:
type: object
additionalProperties: false
required: [status, count, games]
properties:
status:
type: integer
const: 0
count:
type: integer
minimum: 0
games:
type: array
items:
$ref: "#/components/schemas/Game"
MountResponse:
type: object
additionalProperties: false
required: [status, title_id, mounted]
properties:
status:
type: integer
const: 0
title_id:
$ref: "#/components/schemas/TitleId"
mounted:
type: boolean
const: true
UnmountResponse:
type: object
additionalProperties: false
required: [status, title_id, mounted]
properties:
status:
type: integer
const: 0
title_id:
$ref: "#/components/schemas/TitleId"
mounted:
type: boolean
const: false
ErrorResponse:
type: object
additionalProperties: false
required: [status, error]
properties:
status:
type: integer
minimum: 1
description: Positive errno value
error:
type: string