@lanonasis/cli 1.5.0 → 1.5.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/README.md +284 -586
- package/dist/commands/api-keys.d.ts +3 -0
- package/dist/commands/api-keys.js +812 -0
- package/dist/commands/auth.d.ts +2 -0
- package/dist/commands/auth.js +127 -138
- package/dist/commands/completion.d.ts +33 -0
- package/dist/commands/completion.js +378 -0
- package/dist/commands/guide.d.ts +19 -0
- package/dist/commands/guide.js +446 -0
- package/dist/commands/mcp.js +30 -37
- package/dist/commands/memory.js +53 -78
- package/dist/completions/bash-completion.sh +88 -0
- package/dist/completions/fish-completion.fish +132 -0
- package/dist/completions/zsh-completion.zsh +196 -0
- package/dist/index-simple.js +633 -183
- package/dist/index.js +327 -221
- package/dist/mcp-server.d.ts +38 -0
- package/dist/mcp-server.js +154 -0
- package/dist/utils/api.d.ts +12 -2
- package/dist/utils/api.js +38 -4
- package/dist/utils/config.d.ts +5 -2
- package/dist/utils/config.js +39 -15
- package/dist/utils/formatting.d.ts +2 -0
- package/dist/utils/formatting.js +13 -0
- package/dist/utils/mcp-client.d.ts +49 -6
- package/dist/utils/mcp-client.js +159 -82
- package/package.json +22 -12
- package/dist/utils/completions.d.ts +0 -28
- package/dist/utils/completions.js +0 -276
- package/dist/utils/mcp-client.test.d.ts +0 -1
- package/dist/utils/mcp-client.test.js +0 -125
- package/dist/utils/output.d.ts +0 -23
- package/dist/utils/output.js +0 -97
- package/dist/utils/websocket-mcp-client.d.ts +0 -60
- package/dist/utils/websocket-mcp-client.js +0 -182
- package/dist/utils/websocket-mcp-client.test.d.ts +0 -1
- package/dist/utils/websocket-mcp-client.test.js +0 -126
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* CLI-Embedded MCP Server
|
|
4
|
+
* Uses the same configuration and authentication as @lanonasis/cli v1.5.2+
|
|
5
|
+
* Can run standalone or be invoked by CLI commands
|
|
6
|
+
*/
|
|
7
|
+
interface MCPServerOptions {
|
|
8
|
+
mode?: 'stdio' | 'http';
|
|
9
|
+
port?: number;
|
|
10
|
+
verbose?: boolean;
|
|
11
|
+
useRemote?: boolean;
|
|
12
|
+
}
|
|
13
|
+
export declare class CLIMCPServer {
|
|
14
|
+
private config;
|
|
15
|
+
constructor();
|
|
16
|
+
/**
|
|
17
|
+
* Start MCP server using CLI configuration
|
|
18
|
+
*/
|
|
19
|
+
start(options?: MCPServerOptions): Promise<void>;
|
|
20
|
+
/**
|
|
21
|
+
* Start local MCP server using CLI auth config
|
|
22
|
+
*/
|
|
23
|
+
private startLocalMCP;
|
|
24
|
+
/**
|
|
25
|
+
* Connect to remote MCP server
|
|
26
|
+
*/
|
|
27
|
+
private startRemoteMCP;
|
|
28
|
+
/**
|
|
29
|
+
* Check if MCP server is available and configured
|
|
30
|
+
*/
|
|
31
|
+
checkStatus(): Promise<{
|
|
32
|
+
available: boolean;
|
|
33
|
+
configured: boolean;
|
|
34
|
+
authMethod: string;
|
|
35
|
+
mode: 'local' | 'remote' | 'auto';
|
|
36
|
+
}>;
|
|
37
|
+
}
|
|
38
|
+
export default CLIMCPServer;
|
|
@@ -0,0 +1,154 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
/**
|
|
3
|
+
* CLI-Embedded MCP Server
|
|
4
|
+
* Uses the same configuration and authentication as @lanonasis/cli v1.5.2+
|
|
5
|
+
* Can run standalone or be invoked by CLI commands
|
|
6
|
+
*/
|
|
7
|
+
import { fileURLToPath } from 'url';
|
|
8
|
+
import { dirname, join } from 'path';
|
|
9
|
+
import { spawn } from 'child_process';
|
|
10
|
+
import { CLIConfig } from './utils/config.js';
|
|
11
|
+
const __filename = fileURLToPath(import.meta.url);
|
|
12
|
+
const __dirname = dirname(__filename);
|
|
13
|
+
export class CLIMCPServer {
|
|
14
|
+
config;
|
|
15
|
+
constructor() {
|
|
16
|
+
this.config = new CLIConfig();
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Start MCP server using CLI configuration
|
|
20
|
+
*/
|
|
21
|
+
async start(options = {}) {
|
|
22
|
+
await this.config.init();
|
|
23
|
+
const { mode = 'stdio', port = 3001, verbose = false, useRemote = this.config.shouldUseRemoteMCP() } = options;
|
|
24
|
+
if (useRemote) {
|
|
25
|
+
await this.startRemoteMCP(options);
|
|
26
|
+
}
|
|
27
|
+
else {
|
|
28
|
+
await this.startLocalMCP(options);
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Start local MCP server using CLI auth config
|
|
33
|
+
*/
|
|
34
|
+
async startLocalMCP(options) {
|
|
35
|
+
const { mode, port, verbose } = options;
|
|
36
|
+
// Path to CLI-aligned MCP server in submodule
|
|
37
|
+
const mcpServerPath = join(__dirname, '../../../mcp-server/dist/cli-aligned-mcp-server.js');
|
|
38
|
+
const args = mode === 'http' ? ['--http'] : ['--stdio'];
|
|
39
|
+
if (verbose) {
|
|
40
|
+
console.error('🚀 Starting CLI-aligned MCP Server...');
|
|
41
|
+
console.error(`Mode: ${mode}`);
|
|
42
|
+
console.error(`Config: ~/.maas/config.json`);
|
|
43
|
+
console.error(`Auth: ${this.config.hasVendorKey() ? 'Vendor Key' : 'JWT Token'}`);
|
|
44
|
+
}
|
|
45
|
+
// Set environment variables from CLI config
|
|
46
|
+
const env = {
|
|
47
|
+
...process.env,
|
|
48
|
+
PORT: port?.toString(),
|
|
49
|
+
MEMORY_API_URL: this.config.getApiUrl(),
|
|
50
|
+
LANONASIS_VENDOR_KEY: this.config.getVendorKey(),
|
|
51
|
+
LANONASIS_TOKEN: this.config.getToken(),
|
|
52
|
+
MCP_VERBOSE: verbose ? 'true' : 'false',
|
|
53
|
+
CLI_ALIGNED: 'true'
|
|
54
|
+
};
|
|
55
|
+
const child = spawn('node', [mcpServerPath, ...args], {
|
|
56
|
+
env,
|
|
57
|
+
stdio: mode === 'stdio' ? ['pipe', 'pipe', 'inherit'] : 'inherit'
|
|
58
|
+
});
|
|
59
|
+
if (mode === 'stdio') {
|
|
60
|
+
// For stdio mode, pipe stdin/stdout for MCP protocol
|
|
61
|
+
process.stdin.pipe(child.stdin);
|
|
62
|
+
child.stdout.pipe(process.stdout);
|
|
63
|
+
}
|
|
64
|
+
child.on('error', (error) => {
|
|
65
|
+
console.error('❌ MCP Server failed to start:', error.message);
|
|
66
|
+
process.exit(1);
|
|
67
|
+
});
|
|
68
|
+
child.on('exit', (code) => {
|
|
69
|
+
if (code !== 0) {
|
|
70
|
+
console.error(`❌ MCP Server exited with code ${code}`);
|
|
71
|
+
process.exit(code || 1);
|
|
72
|
+
}
|
|
73
|
+
});
|
|
74
|
+
// Handle graceful shutdown
|
|
75
|
+
process.on('SIGINT', () => {
|
|
76
|
+
child.kill('SIGINT');
|
|
77
|
+
});
|
|
78
|
+
process.on('SIGTERM', () => {
|
|
79
|
+
child.kill('SIGTERM');
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
/**
|
|
83
|
+
* Connect to remote MCP server
|
|
84
|
+
*/
|
|
85
|
+
async startRemoteMCP(options) {
|
|
86
|
+
const { verbose } = options;
|
|
87
|
+
if (verbose) {
|
|
88
|
+
console.error('🌐 Connecting to remote MCP server...');
|
|
89
|
+
console.error(`URL: ${this.config.getMCPServerUrl()}`);
|
|
90
|
+
}
|
|
91
|
+
// For remote MCP, we'd need to implement a proxy or client
|
|
92
|
+
// For now, fall back to local mode
|
|
93
|
+
console.error('⚠️ Remote MCP not yet implemented, falling back to local mode');
|
|
94
|
+
await this.startLocalMCP({ ...options, useRemote: false });
|
|
95
|
+
}
|
|
96
|
+
/**
|
|
97
|
+
* Check if MCP server is available and configured
|
|
98
|
+
*/
|
|
99
|
+
async checkStatus() {
|
|
100
|
+
await this.config.init();
|
|
101
|
+
return {
|
|
102
|
+
available: true, // CLI always has MCP server available
|
|
103
|
+
configured: this.config.hasVendorKey() || !!this.config.getToken(),
|
|
104
|
+
authMethod: this.config.hasVendorKey() ? 'vendor_key' :
|
|
105
|
+
this.config.getToken() ? 'jwt' : 'none',
|
|
106
|
+
mode: this.config.shouldUseRemoteMCP() ? 'remote' : 'local'
|
|
107
|
+
};
|
|
108
|
+
}
|
|
109
|
+
}
|
|
110
|
+
// Main execution when run as standalone script
|
|
111
|
+
async function main() {
|
|
112
|
+
const args = process.argv.slice(2);
|
|
113
|
+
const server = new CLIMCPServer();
|
|
114
|
+
// Parse command line arguments
|
|
115
|
+
const options = {
|
|
116
|
+
mode: args.includes('--http') ? 'http' : 'stdio',
|
|
117
|
+
port: parseInt(args.find(arg => arg.startsWith('--port='))?.split('=')[1] || '3001'),
|
|
118
|
+
verbose: args.includes('--verbose') || args.includes('-v'),
|
|
119
|
+
useRemote: args.includes('--remote')
|
|
120
|
+
};
|
|
121
|
+
if (args.includes('--status')) {
|
|
122
|
+
const status = await server.checkStatus();
|
|
123
|
+
console.log(JSON.stringify(status, null, 2));
|
|
124
|
+
return;
|
|
125
|
+
}
|
|
126
|
+
if (args.includes('--help')) {
|
|
127
|
+
console.log(`
|
|
128
|
+
CLI MCP Server - CLI-aligned Model Context Protocol server
|
|
129
|
+
|
|
130
|
+
Usage:
|
|
131
|
+
lanonasis-mcp-server [options]
|
|
132
|
+
|
|
133
|
+
Options:
|
|
134
|
+
--stdio Use stdio transport (default)
|
|
135
|
+
--http Use HTTP transport
|
|
136
|
+
--port=3001 HTTP port (default: 3001)
|
|
137
|
+
--remote Use remote MCP server
|
|
138
|
+
--verbose, -v Verbose logging
|
|
139
|
+
--status Check server status
|
|
140
|
+
--help Show this help
|
|
141
|
+
|
|
142
|
+
Examples:
|
|
143
|
+
lanonasis-mcp-server # Start stdio server
|
|
144
|
+
lanonasis-mcp-server --http --port=3002 # Start HTTP server
|
|
145
|
+
lanonasis-mcp-server --status # Check status
|
|
146
|
+
`);
|
|
147
|
+
return;
|
|
148
|
+
}
|
|
149
|
+
await server.start(options);
|
|
150
|
+
}
|
|
151
|
+
if (import.meta.url === `file://${process.argv[1]}`) {
|
|
152
|
+
main().catch(console.error);
|
|
153
|
+
}
|
|
154
|
+
export default CLIMCPServer;
|
package/dist/utils/api.d.ts
CHANGED
|
@@ -57,7 +57,7 @@ export interface GetMemoriesParams {
|
|
|
57
57
|
limit?: number;
|
|
58
58
|
offset?: number;
|
|
59
59
|
memory_type?: MemoryType;
|
|
60
|
-
tags?: string[];
|
|
60
|
+
tags?: string[] | string;
|
|
61
61
|
topic_id?: string;
|
|
62
62
|
sort_by?: 'created_at' | 'updated_at' | 'last_accessed' | 'access_count';
|
|
63
63
|
sort_order?: 'asc' | 'desc';
|
|
@@ -125,13 +125,19 @@ export interface HealthStatus {
|
|
|
125
125
|
}>;
|
|
126
126
|
}
|
|
127
127
|
export interface PaginatedResponse<T> {
|
|
128
|
-
data
|
|
128
|
+
data?: T[];
|
|
129
|
+
memories?: T[];
|
|
130
|
+
results?: T[];
|
|
129
131
|
pagination: {
|
|
130
132
|
total: number;
|
|
131
133
|
limit: number;
|
|
132
134
|
offset: number;
|
|
133
135
|
has_more: boolean;
|
|
136
|
+
page?: number;
|
|
137
|
+
pages?: number;
|
|
134
138
|
};
|
|
139
|
+
total_results?: number;
|
|
140
|
+
search_time_ms?: number;
|
|
135
141
|
}
|
|
136
142
|
export interface ApiErrorResponse {
|
|
137
143
|
error: string;
|
|
@@ -159,6 +165,10 @@ export declare class APIClient {
|
|
|
159
165
|
updateTopic(id: string, data: UpdateTopicRequest): Promise<MemoryTopic>;
|
|
160
166
|
deleteTopic(id: string): Promise<void>;
|
|
161
167
|
getHealth(): Promise<HealthStatus>;
|
|
168
|
+
get<T = any>(url: string, config?: AxiosRequestConfig): Promise<T>;
|
|
169
|
+
post<T = any>(url: string, data?: any, config?: AxiosRequestConfig): Promise<T>;
|
|
170
|
+
put<T = any>(url: string, data?: any, config?: AxiosRequestConfig): Promise<T>;
|
|
171
|
+
delete<T = any>(url: string, config?: AxiosRequestConfig): Promise<T>;
|
|
162
172
|
request<T = Record<string, unknown>>(config: AxiosRequestConfig): Promise<T>;
|
|
163
173
|
}
|
|
164
174
|
export declare const apiClient: APIClient;
|
package/dist/utils/api.js
CHANGED
|
@@ -1,5 +1,6 @@
|
|
|
1
1
|
import axios from 'axios';
|
|
2
2
|
import chalk from 'chalk';
|
|
3
|
+
import { randomUUID } from 'crypto';
|
|
3
4
|
import { CLIConfig } from './config.js';
|
|
4
5
|
export class APIClient {
|
|
5
6
|
client;
|
|
@@ -7,16 +8,32 @@ export class APIClient {
|
|
|
7
8
|
constructor() {
|
|
8
9
|
this.config = new CLIConfig();
|
|
9
10
|
this.client = axios.create();
|
|
10
|
-
// Setup request interceptor to add auth token
|
|
11
|
+
// Setup request interceptor to add auth token and headers
|
|
11
12
|
this.client.interceptors.request.use(async (config) => {
|
|
12
13
|
await this.config.init();
|
|
14
|
+
// Service Discovery
|
|
15
|
+
await this.config.discoverServices();
|
|
16
|
+
config.baseURL = this.config.getDiscoveredApiUrl();
|
|
17
|
+
// Enhanced Authentication Support
|
|
13
18
|
const token = this.config.getToken();
|
|
14
|
-
|
|
19
|
+
const vendorKey = this.config.getVendorKey();
|
|
20
|
+
if (vendorKey) {
|
|
21
|
+
// Vendor key authentication (pk_*.sk_* format)
|
|
22
|
+
config.headers['X-API-Key'] = vendorKey;
|
|
23
|
+
config.headers['X-Auth-Method'] = 'vendor_key';
|
|
24
|
+
}
|
|
25
|
+
else if (token) {
|
|
26
|
+
// JWT token authentication
|
|
15
27
|
config.headers.Authorization = `Bearer ${token}`;
|
|
28
|
+
config.headers['X-Auth-Method'] = 'jwt';
|
|
16
29
|
}
|
|
17
|
-
|
|
30
|
+
// Add request ID for correlation
|
|
31
|
+
const requestId = randomUUID();
|
|
32
|
+
config.headers['X-Request-ID'] = requestId;
|
|
33
|
+
// Add project scope for Golden Contract compliance
|
|
34
|
+
config.headers['X-Project-Scope'] = 'lanonasis-maas';
|
|
18
35
|
if (process.env.CLI_VERBOSE === 'true') {
|
|
19
|
-
console.log(chalk.dim(`→ ${config.method?.toUpperCase()} ${config.url}`));
|
|
36
|
+
console.log(chalk.dim(`→ ${config.method?.toUpperCase()} ${config.url} [${requestId}]`));
|
|
20
37
|
}
|
|
21
38
|
return config;
|
|
22
39
|
});
|
|
@@ -132,6 +149,23 @@ export class APIClient {
|
|
|
132
149
|
const response = await this.client.get('/api/v1/health');
|
|
133
150
|
return response.data;
|
|
134
151
|
}
|
|
152
|
+
// Generic HTTP methods
|
|
153
|
+
async get(url, config) {
|
|
154
|
+
const response = await this.client.get(url, config);
|
|
155
|
+
return response.data;
|
|
156
|
+
}
|
|
157
|
+
async post(url, data, config) {
|
|
158
|
+
const response = await this.client.post(url, data, config);
|
|
159
|
+
return response.data;
|
|
160
|
+
}
|
|
161
|
+
async put(url, data, config) {
|
|
162
|
+
const response = await this.client.put(url, data, config);
|
|
163
|
+
return response.data;
|
|
164
|
+
}
|
|
165
|
+
async delete(url, config) {
|
|
166
|
+
const response = await this.client.delete(url, config);
|
|
167
|
+
return response.data;
|
|
168
|
+
}
|
|
135
169
|
// Generic request method
|
|
136
170
|
async request(config) {
|
|
137
171
|
const response = await this.client.request(config);
|
package/dist/utils/config.d.ts
CHANGED
|
@@ -13,11 +13,14 @@ export declare class CLIConfig {
|
|
|
13
13
|
load(): Promise<void>;
|
|
14
14
|
save(): Promise<void>;
|
|
15
15
|
getApiUrl(): string;
|
|
16
|
+
discoverServices(): Promise<void>;
|
|
17
|
+
getDiscoveredApiUrl(): string;
|
|
18
|
+
setVendorKey(vendorKey: string): Promise<void>;
|
|
19
|
+
getVendorKey(): string | undefined;
|
|
20
|
+
hasVendorKey(): boolean;
|
|
16
21
|
setApiUrl(url: string): Promise<void>;
|
|
17
22
|
setToken(token: string): Promise<void>;
|
|
18
23
|
getToken(): string | undefined;
|
|
19
|
-
setApiKey(apiKey: string): Promise<void>;
|
|
20
|
-
getApiKey(): string | undefined;
|
|
21
24
|
getCurrentUser(): Promise<UserProfile | undefined>;
|
|
22
25
|
isAuthenticated(): Promise<boolean>;
|
|
23
26
|
logout(): Promise<void>;
|
package/dist/utils/config.js
CHANGED
|
@@ -39,7 +39,42 @@ export class CLIConfig {
|
|
|
39
39
|
getApiUrl() {
|
|
40
40
|
return process.env.MEMORY_API_URL ||
|
|
41
41
|
this.config.apiUrl ||
|
|
42
|
-
'
|
|
42
|
+
'https://api.lanonasis.com/api/v1';
|
|
43
|
+
}
|
|
44
|
+
// Service Discovery Integration
|
|
45
|
+
async discoverServices() {
|
|
46
|
+
try {
|
|
47
|
+
// Use axios instead of fetch for consistency
|
|
48
|
+
const axios = (await import('axios')).default;
|
|
49
|
+
const discoveryUrl = 'https://api.lanonasis.com/.well-known/onasis.json';
|
|
50
|
+
const response = await axios.get(discoveryUrl);
|
|
51
|
+
this.config.discoveredServices = response.data;
|
|
52
|
+
await this.save();
|
|
53
|
+
}
|
|
54
|
+
catch (error) {
|
|
55
|
+
// Service discovery failed, use defaults
|
|
56
|
+
if (process.env.CLI_VERBOSE === 'true') {
|
|
57
|
+
console.log('Service discovery failed, using defaults');
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
}
|
|
61
|
+
getDiscoveredApiUrl() {
|
|
62
|
+
return this.config.discoveredServices?.auth_base || this.getApiUrl();
|
|
63
|
+
}
|
|
64
|
+
// Enhanced authentication support
|
|
65
|
+
async setVendorKey(vendorKey) {
|
|
66
|
+
// Validate vendor key format (pk_*.sk_*)
|
|
67
|
+
if (!vendorKey.match(/^pk_[a-zA-Z0-9]+\.sk_[a-zA-Z0-9]+$/)) {
|
|
68
|
+
throw new Error('Invalid vendor key format. Expected: pk_xxx.sk_xxx');
|
|
69
|
+
}
|
|
70
|
+
this.config.vendorKey = vendorKey;
|
|
71
|
+
await this.save();
|
|
72
|
+
}
|
|
73
|
+
getVendorKey() {
|
|
74
|
+
return this.config.vendorKey;
|
|
75
|
+
}
|
|
76
|
+
hasVendorKey() {
|
|
77
|
+
return !!this.config.vendorKey;
|
|
43
78
|
}
|
|
44
79
|
async setApiUrl(url) {
|
|
45
80
|
this.config.apiUrl = url;
|
|
@@ -67,22 +102,10 @@ export class CLIConfig {
|
|
|
67
102
|
getToken() {
|
|
68
103
|
return this.config.token;
|
|
69
104
|
}
|
|
70
|
-
async setApiKey(apiKey) {
|
|
71
|
-
this.config.apiKey = apiKey;
|
|
72
|
-
await this.save();
|
|
73
|
-
}
|
|
74
|
-
getApiKey() {
|
|
75
|
-
return this.config.apiKey || process.env.LANONASIS_API_KEY;
|
|
76
|
-
}
|
|
77
105
|
async getCurrentUser() {
|
|
78
106
|
return this.config.user;
|
|
79
107
|
}
|
|
80
108
|
async isAuthenticated() {
|
|
81
|
-
// Check for API key first
|
|
82
|
-
const apiKey = this.getApiKey();
|
|
83
|
-
if (apiKey)
|
|
84
|
-
return true;
|
|
85
|
-
// Then check for valid JWT token
|
|
86
109
|
const token = this.getToken();
|
|
87
110
|
if (!token)
|
|
88
111
|
return false;
|
|
@@ -97,7 +120,6 @@ export class CLIConfig {
|
|
|
97
120
|
}
|
|
98
121
|
async logout() {
|
|
99
122
|
this.config.token = undefined;
|
|
100
|
-
this.config.apiKey = undefined;
|
|
101
123
|
this.config.user = undefined;
|
|
102
124
|
await this.save();
|
|
103
125
|
}
|
|
@@ -133,7 +155,9 @@ export class CLIConfig {
|
|
|
133
155
|
return this.config.mcpServerPath || path.join(__dirname, '../../../../onasis-gateway/mcp-server/server.js');
|
|
134
156
|
}
|
|
135
157
|
getMCPServerUrl() {
|
|
136
|
-
return this.config.
|
|
158
|
+
return this.config.discoveredServices?.mcp_ws_base ||
|
|
159
|
+
this.config.mcpServerUrl ||
|
|
160
|
+
'https://api.lanonasis.com';
|
|
137
161
|
}
|
|
138
162
|
shouldUseRemoteMCP() {
|
|
139
163
|
const preference = this.config.mcpPreference || 'auto';
|
|
@@ -2,3 +2,5 @@ export declare function formatOutput(data: unknown, format?: string): void;
|
|
|
2
2
|
export declare function formatBytes(bytes: number): string;
|
|
3
3
|
export declare function truncateText(text: string, maxLength: number): string;
|
|
4
4
|
export declare function formatDuration(ms: number): string;
|
|
5
|
+
export declare function formatDate(date: string | Date): string;
|
|
6
|
+
export declare function formatTableData(data: unknown[]): string[][];
|
package/dist/utils/formatting.js
CHANGED
|
@@ -32,3 +32,16 @@ export function formatDuration(ms) {
|
|
|
32
32
|
return `${(ms / 1000).toFixed(1)}s`;
|
|
33
33
|
return `${(ms / 60000).toFixed(1)}m`;
|
|
34
34
|
}
|
|
35
|
+
export function formatDate(date) {
|
|
36
|
+
const d = new Date(date);
|
|
37
|
+
return d.toLocaleString();
|
|
38
|
+
}
|
|
39
|
+
export function formatTableData(data) {
|
|
40
|
+
return data.map(item => {
|
|
41
|
+
if (Array.isArray(item))
|
|
42
|
+
return item.map(String);
|
|
43
|
+
if (typeof item === 'object' && item !== null)
|
|
44
|
+
return Object.values(item).map(String);
|
|
45
|
+
return [String(item)];
|
|
46
|
+
});
|
|
47
|
+
}
|
|
@@ -2,27 +2,70 @@ interface MCPConnectionOptions {
|
|
|
2
2
|
serverPath?: string;
|
|
3
3
|
serverUrl?: string;
|
|
4
4
|
useRemote?: boolean;
|
|
5
|
-
|
|
5
|
+
useWebSocket?: boolean;
|
|
6
|
+
connectionMode?: 'local' | 'remote' | 'websocket';
|
|
7
|
+
}
|
|
8
|
+
/**
|
|
9
|
+
* Interface for MCP tool arguments
|
|
10
|
+
*/
|
|
11
|
+
interface MCPToolArgs {
|
|
12
|
+
[key: string]: unknown;
|
|
13
|
+
}
|
|
14
|
+
/**
|
|
15
|
+
* Interface for MCP tool response
|
|
16
|
+
*/
|
|
17
|
+
export interface MCPToolResponse {
|
|
18
|
+
result?: unknown;
|
|
19
|
+
error?: {
|
|
20
|
+
code: number;
|
|
21
|
+
message: string;
|
|
22
|
+
};
|
|
23
|
+
id?: string;
|
|
24
|
+
title?: string;
|
|
25
|
+
memory_type?: string;
|
|
26
|
+
length?: number;
|
|
27
|
+
forEach?: (callback: (item: any, index: number) => void) => void;
|
|
28
|
+
code?: number;
|
|
29
|
+
message?: string;
|
|
30
|
+
response?: any;
|
|
31
|
+
}
|
|
32
|
+
/**
|
|
33
|
+
* Interface for MCP WebSocket messages
|
|
34
|
+
*/
|
|
35
|
+
export interface MCPWebSocketMessage {
|
|
36
|
+
id: number;
|
|
37
|
+
method?: string;
|
|
38
|
+
params?: Record<string, unknown>;
|
|
39
|
+
result?: Record<string, unknown>;
|
|
40
|
+
error?: {
|
|
41
|
+
code: number;
|
|
42
|
+
message: string;
|
|
43
|
+
data?: unknown;
|
|
44
|
+
};
|
|
6
45
|
}
|
|
7
46
|
export declare class MCPClient {
|
|
8
47
|
private client;
|
|
9
48
|
private config;
|
|
10
49
|
private isConnected;
|
|
11
50
|
private sseConnection;
|
|
12
|
-
private
|
|
51
|
+
private wsConnection;
|
|
13
52
|
constructor();
|
|
14
53
|
/**
|
|
15
54
|
* Connect to MCP server (local or remote)
|
|
16
55
|
*/
|
|
17
56
|
connect(options?: MCPConnectionOptions): Promise<boolean>;
|
|
18
57
|
/**
|
|
19
|
-
* Initialize
|
|
58
|
+
* Initialize SSE connection for real-time updates
|
|
59
|
+
*/
|
|
60
|
+
private initializeSSE;
|
|
61
|
+
/**
|
|
62
|
+
* Initialize WebSocket connection for enterprise MCP server
|
|
20
63
|
*/
|
|
21
64
|
private initializeWebSocket;
|
|
22
65
|
/**
|
|
23
|
-
*
|
|
66
|
+
* Send a message over the WebSocket connection
|
|
24
67
|
*/
|
|
25
|
-
private
|
|
68
|
+
private sendWebSocketMessage;
|
|
26
69
|
/**
|
|
27
70
|
* Disconnect from MCP server
|
|
28
71
|
*/
|
|
@@ -30,7 +73,7 @@ export declare class MCPClient {
|
|
|
30
73
|
/**
|
|
31
74
|
* Call an MCP tool
|
|
32
75
|
*/
|
|
33
|
-
callTool(toolName: string, args:
|
|
76
|
+
callTool(toolName: string, args: MCPToolArgs): Promise<MCPToolResponse>;
|
|
34
77
|
/**
|
|
35
78
|
* Call remote tool via REST API with MCP interface
|
|
36
79
|
*/
|