@naisys/supervisor 3.0.0-beta.10

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (57) hide show
  1. package/bin/naisys-supervisor +2 -0
  2. package/client-dist/android-chrome-192x192.png +0 -0
  3. package/client-dist/android-chrome-512x512.png +0 -0
  4. package/client-dist/apple-touch-icon.png +0 -0
  5. package/client-dist/assets/index-CKg0vgt5.css +1 -0
  6. package/client-dist/assets/index-WzoDF0aQ.js +177 -0
  7. package/client-dist/assets/naisys-logo-CzoPnn5I.webp +0 -0
  8. package/client-dist/favicon-16x16.png +0 -0
  9. package/client-dist/favicon-32x32.png +0 -0
  10. package/client-dist/favicon.ico +0 -0
  11. package/client-dist/index.html +49 -0
  12. package/client-dist/site.webmanifest +22 -0
  13. package/dist/api-reference.js +54 -0
  14. package/dist/auth-middleware.js +116 -0
  15. package/dist/database/hubDb.js +26 -0
  16. package/dist/database/supervisorDb.js +18 -0
  17. package/dist/error-helpers.js +13 -0
  18. package/dist/hateoas.js +61 -0
  19. package/dist/logger.js +11 -0
  20. package/dist/route-helpers.js +7 -0
  21. package/dist/routes/admin.js +209 -0
  22. package/dist/routes/agentChat.js +194 -0
  23. package/dist/routes/agentConfig.js +265 -0
  24. package/dist/routes/agentLifecycle.js +350 -0
  25. package/dist/routes/agentMail.js +171 -0
  26. package/dist/routes/agentRuns.js +90 -0
  27. package/dist/routes/agents.js +236 -0
  28. package/dist/routes/api.js +52 -0
  29. package/dist/routes/attachments.js +18 -0
  30. package/dist/routes/auth.js +103 -0
  31. package/dist/routes/costs.js +51 -0
  32. package/dist/routes/hosts.js +296 -0
  33. package/dist/routes/models.js +152 -0
  34. package/dist/routes/root.js +56 -0
  35. package/dist/routes/schemas.js +31 -0
  36. package/dist/routes/status.js +20 -0
  37. package/dist/routes/users.js +420 -0
  38. package/dist/routes/variables.js +103 -0
  39. package/dist/schema-registry.js +23 -0
  40. package/dist/services/agentConfigService.js +182 -0
  41. package/dist/services/agentHostStatusService.js +178 -0
  42. package/dist/services/agentService.js +291 -0
  43. package/dist/services/attachmentProxyService.js +131 -0
  44. package/dist/services/browserSocketService.js +78 -0
  45. package/dist/services/chatService.js +201 -0
  46. package/dist/services/configExportService.js +61 -0
  47. package/dist/services/costsService.js +127 -0
  48. package/dist/services/hostService.js +156 -0
  49. package/dist/services/hubConnectionService.js +320 -0
  50. package/dist/services/logFileService.js +11 -0
  51. package/dist/services/mailService.js +154 -0
  52. package/dist/services/modelService.js +92 -0
  53. package/dist/services/runsService.js +168 -0
  54. package/dist/services/userService.js +147 -0
  55. package/dist/services/variableService.js +23 -0
  56. package/dist/supervisorServer.js +221 -0
  57. package/package.json +79 -0
@@ -0,0 +1,296 @@
1
+ import { AgentActionResultSchema, AgentNameParamSchema, AssignAgentToHostRequestSchema, CreateHostRequestSchema, ErrorResponseSchema, HostDetailResponseSchema, HostListResponseSchema, HostNameParamsSchema, UpdateHostRequestSchema, } from "@naisys/supervisor-shared";
2
+ import { hasPermission, requirePermission } from "../auth-middleware.js";
3
+ import { badRequest, conflict, notFound } from "../error-helpers.js";
4
+ import { API_PREFIX, selfLink } from "../hateoas.js";
5
+ import { permGate, resolveActions } from "../route-helpers.js";
6
+ import { emitHostsListChanged, isHostConnected, } from "../services/agentHostStatusService.js";
7
+ import { assignAgentToHost, createHost, deleteHost, getHostDetail, getHosts, unassignAgentFromHost, updateHost, } from "../services/hostService.js";
8
+ import { sendHostsChanged, sendUserListChanged, } from "../services/hubConnectionService.js";
9
+ function hostActions(hostname, user, isOnline) {
10
+ const href = `${API_PREFIX}/hosts/${hostname}`;
11
+ return resolveActions([
12
+ {
13
+ rel: "update",
14
+ method: "PUT",
15
+ title: "Update Host",
16
+ permission: "manage_hosts",
17
+ },
18
+ {
19
+ rel: "assign-agent",
20
+ path: "/agents",
21
+ method: "POST",
22
+ title: "Assign Agent",
23
+ permission: "manage_hosts",
24
+ },
25
+ {
26
+ rel: "delete",
27
+ method: "DELETE",
28
+ title: "Delete Host",
29
+ permission: "manage_hosts",
30
+ disabledWhen: (ctx) => ctx.isOnline ? "Host must be offline before deletion" : null,
31
+ },
32
+ ], href, { user, isOnline });
33
+ }
34
+ function hostActionTemplates(hostname, hasManageHostsPermission) {
35
+ if (!hasManageHostsPermission)
36
+ return [];
37
+ return [
38
+ {
39
+ rel: "unassignAgent",
40
+ hrefTemplate: `${API_PREFIX}/hosts/${hostname}/agents/{agentName}`,
41
+ method: "DELETE",
42
+ title: "Unassign Agent",
43
+ },
44
+ ];
45
+ }
46
+ export default function hostsRoutes(fastify, _options) {
47
+ // GET / — List hosts
48
+ fastify.get("/", {
49
+ schema: {
50
+ description: "List hosts with status",
51
+ tags: ["Hosts"],
52
+ response: {
53
+ 200: HostListResponseSchema,
54
+ 500: ErrorResponseSchema,
55
+ },
56
+ },
57
+ }, async (request, _reply) => {
58
+ const hosts = await getHosts();
59
+ const user = request.supervisorUser;
60
+ const hasManageHostsPermission = hasPermission(user, "manage_hosts");
61
+ const items = hosts.map((host) => {
62
+ const online = isHostConnected(host.id);
63
+ return {
64
+ ...host,
65
+ online,
66
+ _actions: hostActions(host.name, user, online),
67
+ };
68
+ });
69
+ return {
70
+ items,
71
+ _links: [selfLink("/hosts")],
72
+ _linkTemplates: [
73
+ { rel: "item", hrefTemplate: `${API_PREFIX}/hosts/{name}` },
74
+ ],
75
+ _actions: [
76
+ {
77
+ rel: "create",
78
+ href: `${API_PREFIX}/hosts`,
79
+ method: "POST",
80
+ title: "Create Host",
81
+ ...permGate(hasManageHostsPermission, "manage_hosts"),
82
+ },
83
+ ],
84
+ };
85
+ });
86
+ // POST / — Create host
87
+ fastify.post("/", {
88
+ preHandler: [requirePermission("manage_hosts")],
89
+ schema: {
90
+ description: "Create a new host",
91
+ tags: ["Hosts"],
92
+ body: CreateHostRequestSchema,
93
+ response: {
94
+ 200: AgentActionResultSchema,
95
+ 400: ErrorResponseSchema,
96
+ 500: ErrorResponseSchema,
97
+ },
98
+ security: [{ cookieAuth: [] }],
99
+ },
100
+ }, async (request, reply) => {
101
+ try {
102
+ const { name } = request.body;
103
+ const { id } = await createHost(name);
104
+ sendHostsChanged();
105
+ return {
106
+ success: true,
107
+ message: `Host '${name}' created successfully`,
108
+ id,
109
+ };
110
+ }
111
+ catch (error) {
112
+ const errorMessage = error instanceof Error ? error.message : "Unknown error";
113
+ if (errorMessage.includes("already exists")) {
114
+ return conflict(reply, errorMessage);
115
+ }
116
+ if (errorMessage.includes("must contain only")) {
117
+ return badRequest(reply, errorMessage);
118
+ }
119
+ throw error;
120
+ }
121
+ });
122
+ // GET /:hostname — Host detail
123
+ fastify.get("/:hostname", {
124
+ schema: {
125
+ description: "Get host detail with assigned agents",
126
+ tags: ["Hosts"],
127
+ params: HostNameParamsSchema,
128
+ response: {
129
+ 200: HostDetailResponseSchema,
130
+ 404: ErrorResponseSchema,
131
+ 500: ErrorResponseSchema,
132
+ },
133
+ },
134
+ }, async (request, reply) => {
135
+ const { hostname } = request.params;
136
+ const host = await getHostDetail(hostname);
137
+ if (!host) {
138
+ return notFound(reply, `Host "${hostname}" not found`);
139
+ }
140
+ const user = request.supervisorUser;
141
+ const hasManageHostsPermission = hasPermission(user, "manage_hosts");
142
+ const online = isHostConnected(host.id);
143
+ return {
144
+ ...host,
145
+ online,
146
+ assignedAgents: host.assignedAgents,
147
+ _links: [selfLink(`/hosts/${hostname}`)],
148
+ _actions: hostActions(hostname, user, online),
149
+ _actionTemplates: hostActionTemplates(hostname, hasManageHostsPermission),
150
+ };
151
+ });
152
+ // PUT /:hostname — Update host
153
+ fastify.put("/:hostname", {
154
+ preHandler: [requirePermission("manage_hosts")],
155
+ schema: {
156
+ description: "Update host name and/or restricted flag",
157
+ tags: ["Hosts"],
158
+ params: HostNameParamsSchema,
159
+ body: UpdateHostRequestSchema,
160
+ response: {
161
+ 200: AgentActionResultSchema,
162
+ 400: ErrorResponseSchema,
163
+ 404: ErrorResponseSchema,
164
+ 500: ErrorResponseSchema,
165
+ },
166
+ security: [{ cookieAuth: [] }],
167
+ },
168
+ }, async (request, reply) => {
169
+ try {
170
+ const { hostname } = request.params;
171
+ const body = request.body;
172
+ // Look up host to get id for online check
173
+ const host = await getHostDetail(hostname);
174
+ if (!host) {
175
+ return notFound(reply, `Host "${hostname}" not found`);
176
+ }
177
+ // Name change only allowed when offline
178
+ if (body.name !== undefined && isHostConnected(host.id)) {
179
+ return badRequest(reply, "Cannot rename an online host. Disconnect it first.");
180
+ }
181
+ await updateHost(hostname, body);
182
+ sendHostsChanged();
183
+ return { success: true, message: "Host updated" };
184
+ }
185
+ catch (error) {
186
+ const errorMessage = error instanceof Error ? error.message : "Unknown error";
187
+ if (errorMessage.includes("not found")) {
188
+ return notFound(reply, errorMessage);
189
+ }
190
+ if (errorMessage.includes("already exists")) {
191
+ return conflict(reply, errorMessage);
192
+ }
193
+ if (errorMessage.includes("must contain only")) {
194
+ return badRequest(reply, errorMessage);
195
+ }
196
+ throw error;
197
+ }
198
+ });
199
+ // DELETE /:hostname — Permanently delete a host
200
+ fastify.delete("/:hostname", {
201
+ preHandler: [requirePermission("manage_hosts")],
202
+ schema: {
203
+ description: "Permanently delete an offline host",
204
+ tags: ["Hosts"],
205
+ params: HostNameParamsSchema,
206
+ response: {
207
+ 200: AgentActionResultSchema,
208
+ 400: ErrorResponseSchema,
209
+ 404: ErrorResponseSchema,
210
+ 500: ErrorResponseSchema,
211
+ },
212
+ security: [{ cookieAuth: [] }],
213
+ },
214
+ }, async (request, reply) => {
215
+ const { hostname } = request.params;
216
+ const hosts = await getHosts();
217
+ const host = hosts.find((h) => h.name === hostname);
218
+ if (!host) {
219
+ return notFound(reply, `Host "${hostname}" not found`);
220
+ }
221
+ if (isHostConnected(host.id)) {
222
+ return badRequest(reply, "Cannot delete an online host. Disconnect it first.");
223
+ }
224
+ await deleteHost(hostname);
225
+ sendHostsChanged();
226
+ return { success: true, message: "Host permanently deleted" };
227
+ });
228
+ // POST /:hostname/agents — Assign agent to host
229
+ fastify.post("/:hostname/agents", {
230
+ preHandler: [requirePermission("manage_hosts")],
231
+ schema: {
232
+ description: "Assign an agent to this host",
233
+ tags: ["Hosts"],
234
+ params: HostNameParamsSchema,
235
+ body: AssignAgentToHostRequestSchema,
236
+ response: {
237
+ 200: AgentActionResultSchema,
238
+ 400: ErrorResponseSchema,
239
+ 404: ErrorResponseSchema,
240
+ 500: ErrorResponseSchema,
241
+ },
242
+ security: [{ cookieAuth: [] }],
243
+ },
244
+ }, async (request, reply) => {
245
+ try {
246
+ const { hostname } = request.params;
247
+ const { agentId } = request.body;
248
+ await assignAgentToHost(hostname, agentId);
249
+ sendUserListChanged();
250
+ emitHostsListChanged();
251
+ return { success: true, message: "Agent assigned to host" };
252
+ }
253
+ catch (error) {
254
+ const errorMessage = error instanceof Error ? error.message : "Unknown error";
255
+ if (errorMessage.includes("not found")) {
256
+ return notFound(reply, errorMessage);
257
+ }
258
+ if (errorMessage.includes("already assigned")) {
259
+ return conflict(reply, errorMessage);
260
+ }
261
+ throw error;
262
+ }
263
+ });
264
+ // DELETE /:hostname/agents/:agentName — Unassign agent from host
265
+ fastify.delete("/:hostname/agents/:agentName", {
266
+ preHandler: [requirePermission("manage_hosts")],
267
+ schema: {
268
+ description: "Unassign an agent from this host",
269
+ tags: ["Hosts"],
270
+ params: HostNameParamsSchema.merge(AgentNameParamSchema),
271
+ response: {
272
+ 200: AgentActionResultSchema,
273
+ 400: ErrorResponseSchema,
274
+ 404: ErrorResponseSchema,
275
+ 500: ErrorResponseSchema,
276
+ },
277
+ security: [{ cookieAuth: [] }],
278
+ },
279
+ }, async (request, reply) => {
280
+ try {
281
+ const { hostname, agentName } = request.params;
282
+ await unassignAgentFromHost(hostname, agentName);
283
+ sendUserListChanged();
284
+ emitHostsListChanged();
285
+ return { success: true, message: "Agent unassigned from host" };
286
+ }
287
+ catch (error) {
288
+ const errorMessage = error instanceof Error ? error.message : "Unknown error";
289
+ if (errorMessage.includes("not assigned")) {
290
+ return badRequest(reply, errorMessage);
291
+ }
292
+ throw error;
293
+ }
294
+ });
295
+ }
296
+ //# sourceMappingURL=hosts.js.map
@@ -0,0 +1,152 @@
1
+ import { dbFieldsToImageModel, dbFieldsToLlmModel, ImageModelSchema, LlmModelSchema, } from "@naisys/common";
2
+ import { DeleteModelParamsSchema, DeleteModelResponseSchema, ErrorResponseSchema, ModelsResponseSchema, SaveImageModelRequestSchema, SaveLlmModelRequestSchema, SaveModelResponseSchema, } from "@naisys/supervisor-shared";
3
+ import { hasPermission, requirePermission } from "../auth-middleware.js";
4
+ import { badRequest } from "../error-helpers.js";
5
+ import { API_PREFIX } from "../hateoas.js";
6
+ import { sendModelsChanged } from "../services/hubConnectionService.js";
7
+ import { deleteImageModel, deleteLlmModel, getAllModelsFromDb, saveImageModel, saveLlmModel, } from "../services/modelService.js";
8
+ function modelActions(hasManagePermission) {
9
+ const actions = [];
10
+ if (hasManagePermission) {
11
+ actions.push({
12
+ rel: "save-llm",
13
+ href: `${API_PREFIX}/models/llm`,
14
+ method: "PUT",
15
+ title: "Save LLM Model",
16
+ schema: `${API_PREFIX}/schemas/SaveLlmModel`,
17
+ }, {
18
+ rel: "save-image",
19
+ href: `${API_PREFIX}/models/image`,
20
+ method: "PUT",
21
+ title: "Save Image Model",
22
+ schema: `${API_PREFIX}/schemas/SaveImageModel`,
23
+ }, {
24
+ rel: "delete",
25
+ href: `${API_PREFIX}/models/:type/:key`,
26
+ method: "DELETE",
27
+ title: "Delete Model",
28
+ });
29
+ }
30
+ return actions;
31
+ }
32
+ export default function modelsRoutes(fastify, _options) {
33
+ // GET /models — list all models with isCustom flag
34
+ fastify.get("/models", {
35
+ schema: {
36
+ description: "Get available LLM and image model options",
37
+ tags: ["Models"],
38
+ response: {
39
+ 200: ModelsResponseSchema,
40
+ 500: ErrorResponseSchema,
41
+ },
42
+ },
43
+ }, async (request, _reply) => {
44
+ const allModels = await getAllModelsFromDb();
45
+ const llmRows = allModels.filter((r) => r.type === "llm");
46
+ const imageRows = allModels.filter((r) => r.type === "image");
47
+ const hasManagePermission = hasPermission(request.supervisorUser, "manage_models");
48
+ const actions = modelActions(hasManagePermission);
49
+ return {
50
+ llmModels: llmRows.map((r) => ({ value: r.key, label: r.label })),
51
+ imageModels: imageRows.map((r) => ({
52
+ value: r.key,
53
+ label: r.label,
54
+ })),
55
+ llmModelDetails: llmRows.map((r) => ({
56
+ ...dbFieldsToLlmModel(r),
57
+ isCustom: r.is_custom,
58
+ })),
59
+ imageModelDetails: imageRows.map((r) => ({
60
+ ...dbFieldsToImageModel(r),
61
+ isCustom: r.is_custom,
62
+ })),
63
+ _actions: actions.length > 0 ? actions : undefined,
64
+ };
65
+ });
66
+ // PUT /models/llm — upsert custom LLM model
67
+ fastify.put("/models/llm", {
68
+ preHandler: [requirePermission("manage_models")],
69
+ schema: {
70
+ description: "Create or update a custom LLM model",
71
+ tags: ["Models"],
72
+ body: SaveLlmModelRequestSchema,
73
+ response: {
74
+ 200: SaveModelResponseSchema,
75
+ 400: ErrorResponseSchema,
76
+ 500: ErrorResponseSchema,
77
+ },
78
+ },
79
+ }, async (request, reply) => {
80
+ try {
81
+ // Validate with the full common schema (includes superRefine)
82
+ const parsed = LlmModelSchema.parse(request.body.model);
83
+ const result = await saveLlmModel(parsed);
84
+ sendModelsChanged();
85
+ return result;
86
+ }
87
+ catch (error) {
88
+ const message = error instanceof Error ? error.message : "Failed to save LLM model";
89
+ return badRequest(reply, message);
90
+ }
91
+ });
92
+ // PUT /models/image — upsert custom image model
93
+ fastify.put("/models/image", {
94
+ preHandler: [requirePermission("manage_models")],
95
+ schema: {
96
+ description: "Create or update a custom image model",
97
+ tags: ["Models"],
98
+ body: SaveImageModelRequestSchema,
99
+ response: {
100
+ 200: SaveModelResponseSchema,
101
+ 400: ErrorResponseSchema,
102
+ 500: ErrorResponseSchema,
103
+ },
104
+ },
105
+ }, async (request, reply) => {
106
+ try {
107
+ const parsed = ImageModelSchema.parse(request.body.model);
108
+ const result = await saveImageModel(parsed);
109
+ sendModelsChanged();
110
+ return result;
111
+ }
112
+ catch (error) {
113
+ const message = error instanceof Error ? error.message : "Failed to save image model";
114
+ return badRequest(reply, message);
115
+ }
116
+ });
117
+ // DELETE /models/:type/:key — delete a custom model
118
+ fastify.delete("/models/:type/:key", {
119
+ preHandler: [requirePermission("manage_models")],
120
+ schema: {
121
+ description: "Delete a custom model (reverts to built-in if one exists)",
122
+ tags: ["Models"],
123
+ params: DeleteModelParamsSchema,
124
+ response: {
125
+ 200: DeleteModelResponseSchema,
126
+ 400: ErrorResponseSchema,
127
+ 500: ErrorResponseSchema,
128
+ },
129
+ },
130
+ }, async (request, reply) => {
131
+ try {
132
+ const { type, key } = request.params;
133
+ let result;
134
+ if (type === "llm") {
135
+ result = await deleteLlmModel(key);
136
+ }
137
+ else if (type === "image") {
138
+ result = await deleteImageModel(key);
139
+ }
140
+ else {
141
+ return badRequest(reply, "Invalid model type");
142
+ }
143
+ sendModelsChanged();
144
+ return result;
145
+ }
146
+ catch (error) {
147
+ const message = error instanceof Error ? error.message : "Failed to delete model";
148
+ return reply.code(500).send({ success: false, message });
149
+ }
150
+ });
151
+ }
152
+ //# sourceMappingURL=models.js.map
@@ -0,0 +1,56 @@
1
+ import { PermissionEnum } from "@naisys/supervisor-shared";
2
+ const API_PREFIX = "/supervisor/api";
3
+ export default function rootRoutes(fastify, _options) {
4
+ fastify.get("/", {
5
+ schema: {
6
+ description: "API discovery root",
7
+ tags: ["Discovery"],
8
+ },
9
+ }, (request) => {
10
+ const links = [
11
+ { rel: "self", href: `${API_PREFIX}/` },
12
+ {
13
+ rel: "auth-me",
14
+ href: `${API_PREFIX}/auth/me`,
15
+ title: "Current User",
16
+ },
17
+ { rel: "schemas", href: `${API_PREFIX}/schemas/`, title: "Schemas" },
18
+ { rel: "agents", href: `${API_PREFIX}/agents`, title: "Agents" },
19
+ { rel: "hosts", href: `${API_PREFIX}/hosts`, title: "Hosts" },
20
+ { rel: "models", href: `${API_PREFIX}/models`, title: "Models" },
21
+ {
22
+ rel: "variables",
23
+ href: `${API_PREFIX}/variables`,
24
+ title: "Variables",
25
+ },
26
+ {
27
+ rel: "permissions",
28
+ href: `${API_PREFIX}/permissions`,
29
+ title: "Available Permissions",
30
+ },
31
+ ];
32
+ // Only show user management links if user has supervisor_admin permission
33
+ if (request.supervisorUser?.permissions.includes("supervisor_admin")) {
34
+ links.push({
35
+ rel: "users",
36
+ href: `${API_PREFIX}/users`,
37
+ title: "User Management",
38
+ });
39
+ links.push({
40
+ rel: "admin",
41
+ href: `${API_PREFIX}/admin`,
42
+ title: "Admin",
43
+ });
44
+ }
45
+ return { _links: links };
46
+ });
47
+ fastify.get("/permissions", {
48
+ schema: {
49
+ description: "List all available permissions",
50
+ tags: ["Discovery"],
51
+ },
52
+ }, () => {
53
+ return { permissions: PermissionEnum.options };
54
+ });
55
+ }
56
+ //# sourceMappingURL=root.js.map
@@ -0,0 +1,31 @@
1
+ import { z } from "zod/v4";
2
+ import { schemaRegistry } from "../schema-registry.js";
3
+ export default function schemaRoutes(fastify) {
4
+ // List all available schema names
5
+ fastify.get("/", {
6
+ schema: {
7
+ description: "List all available schema names",
8
+ tags: ["Discovery"],
9
+ },
10
+ handler: () => {
11
+ return { schemas: Object.keys(schemaRegistry) };
12
+ },
13
+ });
14
+ // Get a single schema by name
15
+ fastify.get("/:schemaName", {
16
+ schema: {
17
+ description: "Get a JSON Schema by name",
18
+ tags: ["Discovery"],
19
+ },
20
+ handler: (request, reply) => {
21
+ const { schemaName } = request.params;
22
+ const zodSchema = schemaRegistry[schemaName];
23
+ if (!zodSchema) {
24
+ reply.code(404);
25
+ return { error: "Schema not found", schemaName };
26
+ }
27
+ return z.toJSONSchema(zodSchema);
28
+ },
29
+ });
30
+ }
31
+ //# sourceMappingURL=schemas.js.map
@@ -0,0 +1,20 @@
1
+ import { ErrorResponseSchema, StatusResponseSchema, } from "@naisys/supervisor-shared";
2
+ import { isHubConnected } from "../services/hubConnectionService.js";
3
+ export default function statusRoutes(fastify, _options) {
4
+ fastify.get("/status", {
5
+ schema: {
6
+ description: "Get server status including hub connection",
7
+ tags: ["Status"],
8
+ response: {
9
+ 200: StatusResponseSchema,
10
+ 401: ErrorResponseSchema,
11
+ },
12
+ security: [{ cookieAuth: [] }],
13
+ },
14
+ }, () => {
15
+ return {
16
+ hubConnected: isHubConnected(),
17
+ };
18
+ });
19
+ }
20
+ //# sourceMappingURL=status.js.map