Files
objectstorage/ts/opsserver/classes.opsserver.ts
T

94 lines
3.5 KiB
TypeScript

import * as plugins from '../plugins.ts';
import type { ObjectStorageContainer } from '../classes/objectstoragecontainer.ts';
import * as handlers from './handlers/index.ts';
import { files as bundledFiles } from '../../ts_bundled/bundle.ts';
export class OpsServer {
public objectStorageRef: ObjectStorageContainer;
public typedrouter = new plugins.typedrequest.TypedRouter();
public server!: plugins.typedserver.utilityservers.UtilityWebsiteServer;
// Handler instances
public adminHandler!: handlers.AdminHandler;
public statusHandler!: handlers.StatusHandler;
public bucketsHandler!: handlers.BucketsHandler;
public objectsHandler!: handlers.ObjectsHandler;
public configHandler!: handlers.ConfigHandler;
public credentialsHandler!: handlers.CredentialsHandler;
public policiesHandler!: handlers.PoliciesHandler;
public auditHandler!: handlers.AuditHandler;
constructor(objectStorageRef: ObjectStorageContainer) {
this.objectStorageRef = objectStorageRef;
}
public async start(port = 3000) {
this.server = new plugins.typedserver.utilityservers.UtilityWebsiteServer({
domain: 'localhost',
feedMetadata: undefined,
bundledContent: bundledFiles,
addCustomRoutes: async (typedserver) => {
typedserver.addRoute('/livez', 'GET', async () => {
return this.jsonResponse({ ok: true, status: 'alive' });
});
typedserver.addRoute('/readyz', 'GET', async () => {
const ready = await this.objectStorageRef.isReady();
return this.jsonResponse(
{ ok: ready, status: ready ? 'ready' : 'starting' },
ready ? 200 : 503,
);
});
typedserver.addRoute('/healthz', 'GET', async () => {
return this.jsonResponse(await this.objectStorageRef.getOperationalHealth());
});
typedserver.addRoute('/metrics', 'GET', async () => {
const metrics = await this.objectStorageRef.getOperationalMetrics();
return new Response(metrics, {
headers: { 'content-type': 'text/plain; version=0.0.4' },
});
});
},
});
// Chain typedrouters: server -> opsServer -> individual handlers
this.server.typedrouter.addTypedRouter(this.typedrouter);
// Set up all handlers
await this.setupHandlers();
await this.server.start(port);
console.log(`OpsServer started on http://localhost:${port}`);
}
private async setupHandlers(): Promise<void> {
// AdminHandler requires async initialization for JWT key generation
this.adminHandler = new handlers.AdminHandler(this);
await this.adminHandler.initialize();
// All other handlers self-register in their constructors
this.statusHandler = new handlers.StatusHandler(this);
this.bucketsHandler = new handlers.BucketsHandler(this);
this.objectsHandler = new handlers.ObjectsHandler(this);
this.configHandler = new handlers.ConfigHandler(this);
this.credentialsHandler = new handlers.CredentialsHandler(this);
this.policiesHandler = new handlers.PoliciesHandler(this);
this.auditHandler = new handlers.AuditHandler(this);
console.log('OpsServer TypedRequest handlers initialized');
}
public async stop() {
if (this.server) {
await this.server.stop();
console.log('OpsServer stopped');
}
}
private jsonResponse(data: unknown, status = 200): Response {
return new Response(JSON.stringify(data), {
status,
headers: { 'content-type': 'application/json' },
});
}
}