OpenAPI spec at /api/docs with a Scalar viewer, opt-in via FEAT_API_DOCS

This commit is contained in:
jarek committed 2026-08-17 09:50:34 +02:00
1 parent ba8670af66
commit da26f7f764
251 files changed
+32497 -66

No files matched your search

@@ -215,6 +215,12 @@ function parseScannerDnsStorage(raw: string | null | undefined): string[] {
return trimmed.split(',').map((s) => s.trim()).filter(Boolean);
}
/**
* @openapi
* summary: Get global (instance-wide) general settings
* resp-401: Not authenticated
* resp-500: Failed to load settings
*/
export const GET: RequestHandler = async ({ cookies }) => {
const auth = await authorize(cookies);
// UI preferences (time format, date format) should be available to all authenticated users
@@ -391,6 +397,14 @@ export const GET: RequestHandler = async ({ cookies }) => {
}
};
/**
* @openapi
* summary: Update global general settings (all fields optional; only supplied keys are written)
* description: A large flat settings bag - theme/fonts, scanner defaults, cleanup schedules, event/metrics collection, editor options (e.g. editorIndentGuides), and more.
* body: {animateIcons:boolean, editorIndentGuides:boolean, coloredActionButtons:boolean, lightTheme:string, darkTheme:string, defaultTimezone:string, logBufferSizeKb:integer, externalStackPaths:string}
* resp-403: Permission denied (needs settings:edit)
* resp-500: Failed to save settings
*/
export const POST: RequestHandler = async ({ request, cookies }) => {
const auth = await authorize(cookies);
if (auth.authEnabled && !await auth.can('settings', 'edit')) {
@@ -12,6 +12,12 @@ import { authorize } from '$lib/server/authorize';
// GET /api/settings/navigation — returns effective prefs (for redirect/env-click), plus the raw
// global + per-user values so the UI can show what's inherited. Auth off => global only.
/**
* @openapi
* summary: Get the effective navigation preferences (landing page, env-click target) plus the raw global and per-user values
* resp-200: {effective:{landingPage:string!, envClickPage:string!}, global:{landingPage:string, envClickPage:string}, user:{landingPage:string, envClickPage:string}}
* resp-200-example: {"effective":{"landingPage":"dashboard","envClickPage":"containers"},"global":{"landingPage":null,"envClickPage":null},"user":null}
*/
export const GET: RequestHandler = async ({ cookies }) => {
const authEnabled = await isAuthEnabled();
const user = authEnabled ? await validateSession(cookies) : null;
@@ -22,6 +28,17 @@ export const GET: RequestHandler = async ({ cookies }) => {
};
// PUT /api/settings/navigation?scope=global|user
/**
* @openapi
* summary: Update navigation preferences (landing page, env-click target) at global or per-user scope
* query: scope:string Preference scope to update — "global" (default) or "user"
* body: {landingPage:string, envClickPage:string}
* body-example: {"landingPage":"containers","envClickPage":"logs"}
* resp-200: The updated preferences ({success:true, global:{...}} for scope=global, or {success:true, user:{...}} for scope=user)
* resp-400: Invalid input — invalid landingPage/envClickPage value, or scope=user requested while authentication is disabled
* resp-401: Not authenticated (scope=user, authentication is enabled but no valid session)
* resp-403: Permission denied (scope=global, requires settings:edit)
*/
export const PUT: RequestHandler = async ({ request, url, cookies }) => {
const scope = url.searchParams.get('scope') ?? 'global';
let patch: Partial<NavPreferences>;
@@ -19,6 +19,16 @@ export interface ScannerSettings {
trivyImage: string;
}
/**
* @openapi
* summary: Get the vulnerability-scanner settings for an environment, plus (unless settingsOnly) scanner availability, versions and optional update info
* query: env:integer Environment id to read scanner settings for (falls back to global defaults) (from GET /api/environments)
* query: checkUpdates:boolean When true, also check the scanner images for available updates (slower)
* query: settingsOnly:boolean When true, return only settings + defaults and skip the Docker availability/version checks
* resp-200: Scanner settings and (unless settingsOnly) availability, versions, updates and defaults
* resp-403: Permission denied (missing settings:view for the environment)
* resp-500: Failed to read the scanner settings
*/
export const GET: RequestHandler = async ({ url, cookies }) => {
const auth = await authorize(cookies);
@@ -79,6 +89,16 @@ export const GET: RequestHandler = async ({ url, cookies }) => {
}
};
/**
* @openapi
* summary: Save the vulnerability-scanner settings for an environment
* body: {scanner:string, grypeArgs:string, trivyArgs:string, envId:integer}
* body-example: {"scanner":"grype","grypeArgs":"-o json -v {image}","trivyArgs":"image --format json {image}","envId":1}
* resp-200: {success:boolean!, settings:{scanner:string!, grypeArgs:string!, trivyArgs:string!}}
* resp-400: Invalid scanner type (must be none, grype, trivy or both)
* resp-403: Permission denied (missing settings:edit for the environment)
* resp-500: Failed to save the scanner settings
*/
export const POST: RequestHandler = async ({ request, url, cookies }) => {
const auth = await authorize(cookies);
@@ -134,6 +154,18 @@ export const POST: RequestHandler = async ({ request, url, cookies }) => {
}
};
/**
* @openapi
* summary: Remove the scanner images (grype/trivy) and clean up scanner database volumes for an environment
* query: removeImages:boolean Must be true to actually perform the removal (required)
* query: scanner:string Which scanner image to remove (grype or trivy); omit to remove both
* query: env:integer Environment id whose scanner images should be removed (required) (from GET /api/environments)
* resp-200: {success:boolean!, removed:array<string>, errors:array<string>}
* resp-400: The removeImages parameter is required, or the environment id is missing
* resp-403: Permission denied (missing settings:edit for the environment)
* resp-404: Environment not found
* resp-500: Failed to remove the scanner images
*/
export const DELETE: RequestHandler = async ({ url, cookies }) => {
const auth = await authorize(cookies);
+7
View File
@@ -3,6 +3,13 @@ import { cleanupScannerCache } from '$lib/server/scanner';
import { authorize } from '$lib/server/authorize';
import { getEnvironments } from '$lib/server/db';
/**
* @openapi
* summary: Clear the vulnerability-scanner cache (local volumes/bind-mount dirs plus each remote environment's scanner volume)
* resp-200: {success:boolean!, removedVolumes:array<string>!, removedDirs:array<string>!, skippedEnvironments:array<string>!}
* resp-403: Permission denied
* resp-500: Failed to clear scanner cache
*/
export const DELETE: RequestHandler = async ({ cookies }) => {
const auth = await authorize(cookies);
+6
View File
@@ -20,6 +20,12 @@ const DEFAULT_THEME_SETTINGS = {
editorIndentGuides: false
};
/**
* @openapi
* summary: Public theme + editor display settings (used by the login page before auth)
* resp-200: object
* resp-200-desc: Light/dark theme, fonts, and editor display flags (e.g. editorIndentGuides)
*/
export const GET: RequestHandler = async () => {
try {
const [