@phaseo/devtools-viewer 0.2.1 → 0.2.2

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.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2024 Phaseo
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md CHANGED
@@ -1,5 +1,323 @@
1
- # Phaseo DevTools Viewer
1
+ # @phaseo/devtools-viewer
2
2
 
3
- Phaseo is the new name for AI Stats.
3
+ Web-based viewer for Phaseo DevTools telemetry data.
4
4
 
5
- This package reserves `@phaseo/devtools-viewer` and forwards to the current DevTools viewer from `@ai-stats/devtools-viewer` during the package migration.
5
+ ## Overview
6
+
7
+ The DevTools Viewer provides a beautiful, real-time web interface for inspecting API requests captured by Phaseo SDKs. It features:
8
+
9
+ - **Live telemetry updates** - Auto-refreshes every 2 seconds
10
+ - **Adaptive UI** - Different views for chat, images, audio, video, etc.
11
+ - **Analytics dashboard** - Aggregate stats by endpoint, model, cost, tokens
12
+ - **Export functionality** - Export telemetry as JSON or JSONL
13
+
14
+ ## Installation
15
+
16
+ ```bash
17
+ npm install @phaseo/sdk
18
+ # or
19
+ pnpm add @phaseo/sdk
20
+ ```
21
+
22
+ The DevTools CLI ships with the TypeScript SDK. You can also install it separately:
23
+
24
+ ```bash
25
+ npm install -g @phaseo/devtools-viewer
26
+ # or
27
+ pnpm add -g @phaseo/devtools-viewer
28
+ # or
29
+ npx @phaseo/devtools-viewer start
30
+ ```
31
+
32
+ ## Usage
33
+
34
+ ### Start the Viewer
35
+
36
+ ```bash
37
+ # Start with defaults (port 4983, directory .phaseo-devtools)
38
+ phaseo-devtools start
39
+
40
+ # Custom port
41
+ phaseo-devtools start -p 3000
42
+
43
+ # Custom directory
44
+ phaseo-devtools start -d /path/to/devtools
45
+
46
+ # Both
47
+ phaseo-devtools start -p 8080 -d ./my-devtools
48
+
49
+ # If installed locally (recommended)
50
+ pnpm exec phaseo-devtools start
51
+ ```
52
+
53
+ Then open http://localhost:4983 in your browser.
54
+
55
+ ### Environment Variables
56
+
57
+ ```bash
58
+ # Set devtools directory
59
+ export PHASEO_DEVTOOLS_DIR=/path/to/devtools
60
+
61
+ # Set port
62
+ export PORT=3000
63
+
64
+ # Start server
65
+ phaseo-devtools start
66
+ ```
67
+
68
+ ## Features
69
+
70
+ ### Generations View
71
+
72
+ - **Sidebar list** - All captured API requests sorted by timestamp
73
+ - **Adaptive detail view** - Specialized views for different endpoint types:
74
+ - **Chat Completions** - Messages, tool calls, reasoning blocks
75
+ - **Images** - Generated images, prompts, revised prompts
76
+ - **Audio** - Audio player, transcriptions, translations
77
+ - **Video** - Video player, generation parameters
78
+ - **Generic** - JSON view for all other endpoints
79
+ - **Error highlighting** - Failed requests clearly marked
80
+ - **Metadata display** - Model, provider, duration, cost, tokens
81
+
82
+ ### Stats Dashboard
83
+
84
+ - **Overview cards** - Total requests, cost, tokens, avg duration
85
+ - **By Endpoint table** - Breakdown by endpoint type
86
+ - **By Model table** - Breakdown by model
87
+ - **Error rate tracking** - Monitor API failures
88
+ - **Export buttons** - Download data as JSON or JSONL
89
+
90
+ ### Real-time Updates
91
+
92
+ The viewer automatically polls for new telemetry every 2 seconds, so you see API requests appear in real-time as your application makes them.
93
+
94
+ ## API Endpoints
95
+
96
+ The viewer exposes these HTTP endpoints:
97
+
98
+ - `GET /api/generations` - Get all generations (with filtering)
99
+ - `GET /api/generations/:id` - Get specific generation
100
+ - `GET /api/stats` - Get aggregate statistics
101
+ - `GET /api/metadata` - Get session metadata
102
+ - `GET /api/export?format=json|jsonl` - Export telemetry
103
+ - `GET /assets/*` - Serve binary assets (images, audio, video)
104
+
105
+ ### Query Parameters for `/api/generations`
106
+
107
+ ```bash
108
+ # Filter by endpoint type
109
+ /api/generations?type=chat.completions
110
+
111
+ # Filter by model
112
+ /api/generations?model=gpt-4
113
+
114
+ # Filter errors only
115
+ /api/generations?hasError=true
116
+
117
+ # Pagination
118
+ /api/generations?limit=50&offset=100
119
+ ```
120
+
121
+ ## Development
122
+
123
+ ### Build
124
+
125
+ ```bash
126
+ # Build server
127
+ pnpm run build:server
128
+
129
+ # Build UI
130
+ pnpm run build:ui
131
+
132
+ # Build both
133
+ pnpm run build
134
+ ```
135
+
136
+ ### Development Mode
137
+
138
+ ```bash
139
+ # Run both server and UI with hot reloading
140
+ pnpm run dev
141
+ ```
142
+
143
+ This will:
144
+ 1. Start the API server on port 4984 with auto-restart on changes
145
+ 2. Start the Vite dev server on port 4983 with HMR (Hot Module Replacement)
146
+ 3. Proxy all `/api` requests from the UI to the server
147
+
148
+ **How it works:**
149
+ - UI changes reload instantly in the browser (React Fast Refresh)
150
+ - Server changes trigger an automatic restart
151
+ - No need to rebuild or manually refresh
152
+
153
+ **Accessing the dev environment:**
154
+ - Open http://localhost:4983 in your browser
155
+ - Check the console for any errors
156
+ - Server logs appear in the terminal
157
+
158
+ **Troubleshooting:**
159
+ - If port 4984 is busy, the server won't start. Kill the process or change the port.
160
+ - If port 4983 is busy, the UI dev server won't start. Same solution.
161
+ - If you see `ENOENT` errors, make sure `.phaseo-devtools` directory exists with sample data
162
+ - Check browser DevTools console (F12) for client-side errors
163
+ - Check terminal output for server-side errors
164
+
165
+ ## Architecture
166
+
167
+ ### Tech Stack
168
+
169
+ - **Server**: Hono (fast web framework)
170
+ - **UI**: React + TanStack Query
171
+ - **Styling**: Tailwind CSS
172
+ - **Build**: Vite (UI) + TypeScript (server)
173
+
174
+ ### File Structure
175
+
176
+ ```
177
+ packages/devtools/devtools-viewer/
178
+ ├── src/
179
+ │ ├── server/ # Hono server
180
+ │ │ └── index.ts # API routes, static serving
181
+ │ ├── ui/ # React frontend
182
+ │ │ ├── components/ # UI components
183
+ │ │ │ ├── endpoints/ # Endpoint-specific views
184
+ │ │ │ ├── GenerationsList.tsx
185
+ │ │ │ ├── GenerationDetail.tsx
186
+ │ │ │ └── StatsOverview.tsx
187
+ │ │ ├── App.tsx # Main app
188
+ │ │ ├── main.tsx # Entry point
189
+ │ │ └── index.css # Tailwind styles
190
+ │ └── cli/ # CLI tool
191
+ │ └── index.ts # Command-line interface
192
+ ├── public/ # Built UI assets
193
+ └── dist/ # Compiled server code
194
+ ```
195
+
196
+ ## Telemetry Format
197
+
198
+ The viewer reads JSONL (JSON Lines) files from the devtools directory:
199
+
200
+ ```
201
+ .phaseo-devtools/
202
+ ├── generations.jsonl # Main telemetry log
203
+ ├── metadata.json # Session info
204
+ └── assets/ # Binary assets
205
+ ├── images/{uuid}.png
206
+ ├── audio/{uuid}.mp3
207
+ └── video/{uuid}.mp4
208
+ ```
209
+
210
+ Each line in `generations.jsonl` is a JSON object with this structure:
211
+
212
+ ```typescript
213
+ {
214
+ id: string;
215
+ type: "chat.completions" | "images.generations" | ...;
216
+ timestamp: number;
217
+ duration_ms: number;
218
+ request: { ... };
219
+ response: { ... } | null;
220
+ error: { message: string } | null;
221
+ metadata: {
222
+ sdk: "typescript" | "python" | ...;
223
+ sdk_version: string;
224
+ stream: boolean;
225
+ usage?: { ... };
226
+ cost?: { ... };
227
+ model?: string;
228
+ provider?: string;
229
+ };
230
+ }
231
+ ```
232
+
233
+ ## Troubleshooting
234
+
235
+ ### Blank Screen When Clicking on Generations
236
+
237
+ If the screen goes blank when you click on a generation:
238
+
239
+ 1. **Open Browser DevTools** (F12) and check the Console tab for errors
240
+ 2. **Check the Network tab** to see if the API call to `/api/generations/{id}` is failing
241
+ 3. **Look for component errors** - the ErrorBoundary will now show detailed error messages
242
+ 4. **Check data format** - ensure your generations.jsonl has valid JSON on each line
243
+ 5. **Try the "Try Again" button** that appears after errors
244
+
245
+ Recent fixes:
246
+ - Added comprehensive error boundaries with stack traces
247
+ - Improved null checking in all view components
248
+ - Added debug logging to identify rendering issues
249
+
250
+ ### Dev Server Issues
251
+
252
+ **Port conflicts:**
253
+ ```bash
254
+ # Find and kill processes on ports 4983/4984
255
+ # On Windows:
256
+ netstat -ano | findstr :4983
257
+ taskkill /PID <pid> /F
258
+
259
+ # On Linux/Mac:
260
+ lsof -ti:4983 | xargs kill -9
261
+ ```
262
+
263
+ **Missing dependencies:**
264
+ ```bash
265
+ cd packages/devtools/devtools-viewer
266
+ pnpm install
267
+ ```
268
+
269
+ **Stale build artifacts:**
270
+ ```bash
271
+ pnpm run clean
272
+ pnpm run build
273
+ ```
274
+
275
+ ### No Data Showing
276
+
277
+ 1. **Check devtools directory exists:**
278
+ ```bash
279
+ ls -la .phaseo-devtools/
280
+ ```
281
+
282
+ 2. **Verify files are present:**
283
+ - `generations.jsonl` should exist and have content
284
+ - `metadata.json` should exist
285
+
286
+ 3. **Test with sample data:**
287
+ ```bash
288
+ # Create test entry
289
+ echo '{"id":"test-1","type":"chat.completions","timestamp":1234567890,"duration_ms":100,"request":{"messages":[{"role":"user","content":"test"}]},"response":null,"error":null,"metadata":{"sdk":"test"}}' >> .phaseo-devtools/generations.jsonl
290
+ ```
291
+
292
+ ## Quick Development Workflow
293
+
294
+ ```bash
295
+ # 1. Navigate to devtools viewer
296
+ cd packages/devtools/devtools-viewer
297
+
298
+ # 2. Install dependencies (if needed)
299
+ pnpm install
300
+
301
+ # 3. Start dev servers
302
+ pnpm run dev
303
+
304
+ # 4. Open browser
305
+ # Navigate to http://localhost:4983
306
+
307
+ # 5. Make changes to components
308
+ # - Edit files in src/ui/components/
309
+ # - Changes reflect immediately (Hot Module Replacement)
310
+ # - No need to rebuild or refresh
311
+
312
+ # 6. Check for errors
313
+ # - Browser console (F12 → Console)
314
+ # - Terminal output (server logs)
315
+
316
+ # 7. Test with real data
317
+ # - Run your app with Phaseo SDK
318
+ # - Watch requests appear in real-time
319
+ ```
320
+
321
+ ## License
322
+
323
+ MIT
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+ export {};
3
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":""}
@@ -0,0 +1,82 @@
1
+ #!/usr/bin/env node
2
+ import { startServer } from "../server/index.js";
3
+ import * as process from "process";
4
+ const args = process.argv.slice(2);
5
+ const command = args[0] || "start";
6
+ function printHelp() {
7
+ console.log(`
8
+ Phaseo DevTools Viewer
9
+
10
+ Usage:
11
+ phaseo-devtools [command] [options]
12
+
13
+ Commands:
14
+ start Start the devtools viewer server (default)
15
+ help Show this help message
16
+
17
+ Options:
18
+ -p, --port <port> Port to run the server on (default: 4983)
19
+ -d, --dir <path> Path to devtools directory (default: .phaseo-devtools)
20
+ -h, --help Show this help message
21
+
22
+ Examples:
23
+ phaseo-devtools start
24
+ phaseo-devtools start -p 3000
25
+ phaseo-devtools start -d /path/to/devtools
26
+ phaseo-devtools --port 8080 --dir ./my-devtools
27
+
28
+ Environment Variables:
29
+ PHASEO_DEVTOOLS_DIR Path to devtools directory
30
+ PORT Port to run the server on
31
+ `);
32
+ }
33
+ function parseArgs() {
34
+ const config = {
35
+ port: parseInt(process.env.PORT || "4983", 10),
36
+ directory: process.env.PHASEO_DEVTOOLS_DIR || ".phaseo-devtools"
37
+ };
38
+ for (let i = 0; i < args.length; i++) {
39
+ const arg = args[i];
40
+ if (arg === "-h" || arg === "--help") {
41
+ printHelp();
42
+ process.exit(0);
43
+ }
44
+ if (arg === "-p" || arg === "--port") {
45
+ config.port = parseInt(args[++i], 10);
46
+ if (isNaN(config.port)) {
47
+ console.error("Error: Port must be a number");
48
+ process.exit(1);
49
+ }
50
+ }
51
+ if (arg === "-d" || arg === "--dir" || arg === "--directory") {
52
+ config.directory = args[++i];
53
+ if (!config.directory) {
54
+ console.error("Error: Directory path is required");
55
+ process.exit(1);
56
+ }
57
+ }
58
+ }
59
+ return config;
60
+ }
61
+ async function main() {
62
+ if (command === "help" || command === "--help" || command === "-h") {
63
+ printHelp();
64
+ return;
65
+ }
66
+ if (command === "start" || !command || command.startsWith("-")) {
67
+ const config = parseArgs();
68
+ // Set environment variables for the server
69
+ process.env.PHASEO_DEVTOOLS_DIR = config.directory;
70
+ process.env.PORT = config.port.toString();
71
+ startServer(config.port);
72
+ return;
73
+ }
74
+ console.error(`Unknown command: ${command}`);
75
+ console.error('Run "phaseo-devtools help" for usage information');
76
+ process.exit(1);
77
+ }
78
+ main().catch((error) => {
79
+ console.error("Error:", error);
80
+ process.exit(1);
81
+ });
82
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/cli/index.ts"],"names":[],"mappings":"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"}
package/dist/core.d.ts ADDED
@@ -0,0 +1,118 @@
1
+ export type EndpointType = "chat.completions" | "messages" | "images.generations" | "images.edits" | "audio.speech" | "audio.transcriptions" | "audio.translations" | "video.generations" | "video.list" | "video.retrieve" | "video.cancel" | "music.generations" | "music.retrieve" | "embeddings" | "ocr" | "rerank" | "moderations" | "responses" | "responses.websocket" | "batches.create" | "batches.retrieve" | "batches.cancel" | "files.list" | "files.retrieve" | "files.upload" | "endpoints.list" | "organisations.list" | "pricing.models" | "pricing.calculate" | "key.current" | "models.list" | "providers" | "providers.derank" | "credits" | "activity" | "health" | "analytics" | "generations.retrieve" | "provisioning.keys.list" | "provisioning.keys.create" | "provisioning.keys.get" | "provisioning.keys.update" | "provisioning.keys.delete" | "provisioning.workspaces.list" | "provisioning.workspaces.get" | "provisioning.workspaces.create" | "provisioning.workspaces.update" | "provisioning.workspaces.delete" | "agent.run" | "agent.continue";
2
+ export type SdkIdentifier = "typescript" | "python" | "go" | "csharp" | "ruby" | "php" | "java" | "rust" | "cpp";
3
+ export type ErrorInfo = {
4
+ message: string;
5
+ code?: string;
6
+ status?: number;
7
+ stack?: string;
8
+ };
9
+ export type UsageInfo = {
10
+ prompt_tokens?: number;
11
+ completion_tokens?: number;
12
+ total_tokens?: number;
13
+ images_generated?: number;
14
+ audio_seconds?: number;
15
+ video_seconds?: number;
16
+ cache_creation_input_tokens?: number;
17
+ cache_read_input_tokens?: number;
18
+ };
19
+ export type CostInfo = {
20
+ input_cost?: number;
21
+ output_cost?: number;
22
+ cache_creation_cost?: number;
23
+ cache_read_cost?: number;
24
+ total_cost: number;
25
+ };
26
+ export type ProviderAttempt = {
27
+ provider: string;
28
+ provider_label?: string;
29
+ request_id?: string;
30
+ status_code?: number;
31
+ status_text?: string;
32
+ outcome?: string;
33
+ duration_ms?: number;
34
+ latency_ms?: number;
35
+ generation_ms?: number;
36
+ throughput?: number;
37
+ started_at?: number;
38
+ completed_at?: number;
39
+ error_code?: string;
40
+ error_message?: string;
41
+ };
42
+ export type Metadata = {
43
+ sdk: SdkIdentifier;
44
+ sdk_version: string;
45
+ stream: boolean;
46
+ chunk_count?: number;
47
+ usage?: UsageInfo;
48
+ cost?: CostInfo;
49
+ model?: string;
50
+ provider?: string;
51
+ request_id?: string;
52
+ session_id?: string;
53
+ upstream_request_id?: string;
54
+ native_response_id?: string;
55
+ status_code?: number;
56
+ latency_ms?: number;
57
+ generation_ms?: number;
58
+ throughput?: number;
59
+ finish_reason?: string;
60
+ pricing_lines?: Array<Record<string, any> | string | number | boolean | null>;
61
+ provider_attempts?: ProviderAttempt[];
62
+ agent_id?: string;
63
+ run_id?: string;
64
+ run_status?: string;
65
+ step_count?: number;
66
+ tool_count?: number;
67
+ headers?: Record<string, string>;
68
+ };
69
+ export type DevToolsEntry = {
70
+ id: string;
71
+ type: EndpointType;
72
+ timestamp: number;
73
+ duration_ms: number;
74
+ request: Record<string, any>;
75
+ response: Record<string, any> | null;
76
+ error: ErrorInfo | null;
77
+ metadata: Metadata;
78
+ };
79
+ export type SessionMetadata = {
80
+ session_id: string;
81
+ started_at: number;
82
+ sdk: SdkIdentifier;
83
+ sdk_version: string;
84
+ platform?: string;
85
+ node_version?: string;
86
+ };
87
+ export type Stats = {
88
+ total_requests: number;
89
+ total_errors: number;
90
+ total_cost: number;
91
+ total_tokens: number;
92
+ total_duration_ms: number;
93
+ by_endpoint: Record<string, {
94
+ count: number;
95
+ errors: number;
96
+ avg_duration_ms: number;
97
+ total_cost: number;
98
+ }>;
99
+ by_model: Record<string, {
100
+ count: number;
101
+ tokens: number;
102
+ cost: number;
103
+ }>;
104
+ };
105
+ export declare class DevToolsWriter {
106
+ private readonly directory;
107
+ private readonly generationsFile;
108
+ private readonly metadataFile;
109
+ private readonly assetsDir;
110
+ constructor(directory?: string);
111
+ ensureDirectory(): void;
112
+ writeEntry(entry: DevToolsEntry): void;
113
+ writeEntries(entries: DevToolsEntry[]): void;
114
+ writeSessionMetadata(metadata: SessionMetadata): void;
115
+ readEntries(): DevToolsEntry[];
116
+ readSessionMetadata(): SessionMetadata | null;
117
+ }
118
+ //# sourceMappingURL=core.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"core.d.ts","sourceRoot":"","sources":["../src/core.ts"],"names":[],"mappings":"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"}
package/dist/core.js ADDED
@@ -0,0 +1,55 @@
1
+ import * as fs from "fs";
2
+ import * as path from "path";
3
+ export class DevToolsWriter {
4
+ directory;
5
+ generationsFile;
6
+ metadataFile;
7
+ assetsDir;
8
+ constructor(directory = ".phaseo-devtools") {
9
+ this.directory = directory;
10
+ this.generationsFile = path.join(directory, "generations.jsonl");
11
+ this.metadataFile = path.join(directory, "metadata.json");
12
+ this.assetsDir = path.join(directory, "assets");
13
+ }
14
+ ensureDirectory() {
15
+ if (!fs.existsSync(this.directory)) {
16
+ fs.mkdirSync(this.directory, { recursive: true });
17
+ }
18
+ if (!fs.existsSync(this.assetsDir)) {
19
+ fs.mkdirSync(path.join(this.assetsDir, "images"), { recursive: true });
20
+ fs.mkdirSync(path.join(this.assetsDir, "audio"), { recursive: true });
21
+ fs.mkdirSync(path.join(this.assetsDir, "video"), { recursive: true });
22
+ }
23
+ }
24
+ writeEntry(entry) {
25
+ this.ensureDirectory();
26
+ const line = JSON.stringify(entry) + "\n";
27
+ fs.appendFileSync(this.generationsFile, line, "utf-8");
28
+ }
29
+ writeEntries(entries) {
30
+ if (entries.length === 0)
31
+ return;
32
+ this.ensureDirectory();
33
+ const lines = entries.map((entry) => JSON.stringify(entry) + "\n").join("");
34
+ fs.appendFileSync(this.generationsFile, lines, "utf-8");
35
+ }
36
+ writeSessionMetadata(metadata) {
37
+ this.ensureDirectory();
38
+ fs.writeFileSync(this.metadataFile, JSON.stringify(metadata, null, 2), "utf-8");
39
+ }
40
+ readEntries() {
41
+ if (!fs.existsSync(this.generationsFile)) {
42
+ return [];
43
+ }
44
+ const content = fs.readFileSync(this.generationsFile, "utf-8");
45
+ const lines = content.split("\n").filter((line) => line.trim());
46
+ return lines.map((line) => JSON.parse(line));
47
+ }
48
+ readSessionMetadata() {
49
+ if (!fs.existsSync(this.metadataFile)) {
50
+ return null;
51
+ }
52
+ return JSON.parse(fs.readFileSync(this.metadataFile, "utf-8"));
53
+ }
54
+ }
55
+ //# sourceMappingURL=core.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"core.js","sourceRoot":"","sources":["../src/core.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,8 @@
1
+ import { Hono } from "hono";
2
+ declare const app: Hono<import("hono/types").BlankEnv, import("hono/types").BlankSchema, "/">;
3
+ /**
4
+ * Start server
5
+ */
6
+ export declare function startServer(port?: number): void;
7
+ export { app };
8
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/server/index.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,IAAI,EAAE,MAAM,MAAM,CAAC;AAQ5B,QAAA,MAAM,GAAG,4EAAa,CAAC;AAqQvB;;GAEG;AACH,wBAAgB,WAAW,CAAC,IAAI,GAAE,MAAqB,QAuBtD;AAsBD,OAAO,EAAE,GAAG,EAAE,CAAC"}