@west10tech/notion-mcp 1.0.0
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 +120 -0
- package/dist/clients/notion-client.d.ts +53 -0
- package/dist/clients/notion-client.d.ts.map +1 -0
- package/dist/clients/notion-client.js +2950 -0
- package/dist/clients/notion-client.js.map +1 -0
- package/dist/config.d.ts +21 -0
- package/dist/config.d.ts.map +1 -0
- package/dist/config.js +58 -0
- package/dist/config.js.map +1 -0
- package/dist/index.d.ts +3 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +163 -0
- package/dist/index.js.map +1 -0
- package/dist/services/log-batcher.d.ts +44 -0
- package/dist/services/log-batcher.d.ts.map +1 -0
- package/dist/services/log-batcher.js +81 -0
- package/dist/services/log-batcher.js.map +1 -0
- package/dist/services/log-shipper.d.ts +104 -0
- package/dist/services/log-shipper.d.ts.map +1 -0
- package/dist/services/log-shipper.js +384 -0
- package/dist/services/log-shipper.js.map +1 -0
- package/dist/services/logger.d.ts +92 -0
- package/dist/services/logger.d.ts.map +1 -0
- package/dist/services/logger.js +224 -0
- package/dist/services/logger.js.map +1 -0
- package/dist/services/progress-reporter.d.ts +64 -0
- package/dist/services/progress-reporter.d.ts.map +1 -0
- package/dist/services/progress-reporter.js +192 -0
- package/dist/services/progress-reporter.js.map +1 -0
- package/dist/services/request-tracker.d.ts +55 -0
- package/dist/services/request-tracker.d.ts.map +1 -0
- package/dist/services/request-tracker.js +184 -0
- package/dist/services/request-tracker.js.map +1 -0
- package/dist/tools/notion-tools.d.ts +21 -0
- package/dist/tools/notion-tools.d.ts.map +1 -0
- package/dist/tools/notion-tools.js +1146 -0
- package/dist/tools/notion-tools.js.map +1 -0
- package/dist/types.d.ts +25 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +2 -0
- package/dist/types.js.map +1 -0
- package/package.json +57 -0
|
@@ -0,0 +1,81 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* LogBatcher - Implements the exact batching logic as specified in requirements
|
|
3
|
+
* Batches logs and sends them to the centralized logging endpoint
|
|
4
|
+
*/
|
|
5
|
+
export class LogBatcher {
|
|
6
|
+
constructor(logShipper, maxBatchSize = 500, flushInterval = 5000) {
|
|
7
|
+
this.logs = [];
|
|
8
|
+
this.flushTimer = null;
|
|
9
|
+
this.logShipper = logShipper;
|
|
10
|
+
this.maxBatchSize = maxBatchSize;
|
|
11
|
+
this.flushInterval = flushInterval;
|
|
12
|
+
this.sessionId = this.generateSessionId();
|
|
13
|
+
// Start the flush timer
|
|
14
|
+
this.flushTimer = setInterval(() => this.flush(), this.flushInterval);
|
|
15
|
+
}
|
|
16
|
+
/**
|
|
17
|
+
* Add a structured log entry to the batch
|
|
18
|
+
*/
|
|
19
|
+
addStructuredLog(logEntry) {
|
|
20
|
+
this.logs.push(logEntry);
|
|
21
|
+
// Flush immediately if batch size reached
|
|
22
|
+
if (this.logs.length >= this.maxBatchSize) {
|
|
23
|
+
this.flush();
|
|
24
|
+
}
|
|
25
|
+
}
|
|
26
|
+
/**
|
|
27
|
+
* Flush all batched logs
|
|
28
|
+
*/
|
|
29
|
+
async flush() {
|
|
30
|
+
if (this.logs.length === 0)
|
|
31
|
+
return;
|
|
32
|
+
const batch = this.logs.splice(0, this.maxBatchSize);
|
|
33
|
+
try {
|
|
34
|
+
// Send each structured log through the LogShipper
|
|
35
|
+
for (const logEntry of batch) {
|
|
36
|
+
this.logShipper.addLog(logEntry);
|
|
37
|
+
}
|
|
38
|
+
// Trigger immediate flush in LogShipper
|
|
39
|
+
await this.logShipper.flush();
|
|
40
|
+
}
|
|
41
|
+
catch (error) {
|
|
42
|
+
console.error('Failed to send logs:', error);
|
|
43
|
+
// Could implement retry logic here
|
|
44
|
+
}
|
|
45
|
+
}
|
|
46
|
+
/**
|
|
47
|
+
* Get the session ID for this batcher instance
|
|
48
|
+
*/
|
|
49
|
+
getSessionId() {
|
|
50
|
+
return this.sessionId;
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Generate a unique session ID
|
|
54
|
+
*/
|
|
55
|
+
generateSessionId() {
|
|
56
|
+
return `notion-mcp-${Date.now()}-${Math.random().toString(36).substring(2, 9)}`;
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Get current batch status
|
|
60
|
+
*/
|
|
61
|
+
getBatchStatus() {
|
|
62
|
+
return {
|
|
63
|
+
queueSize: this.logs.length,
|
|
64
|
+
maxBatchSize: this.maxBatchSize,
|
|
65
|
+
flushInterval: this.flushInterval,
|
|
66
|
+
sessionId: this.sessionId
|
|
67
|
+
};
|
|
68
|
+
}
|
|
69
|
+
/**
|
|
70
|
+
* Shutdown the batcher and flush remaining logs
|
|
71
|
+
*/
|
|
72
|
+
async shutdown() {
|
|
73
|
+
if (this.flushTimer) {
|
|
74
|
+
clearInterval(this.flushTimer);
|
|
75
|
+
this.flushTimer = null;
|
|
76
|
+
}
|
|
77
|
+
// Flush any remaining logs
|
|
78
|
+
await this.flush();
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
//# sourceMappingURL=log-batcher.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log-batcher.js","sourceRoot":"","sources":["../../src/services/log-batcher.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAIH,MAAM,OAAO,UAAU;IAQrB,YAAY,UAAsB,EAAE,eAAuB,GAAG,EAAE,gBAAwB,IAAI;QAPpF,SAAI,GAAe,EAAE,CAAC;QAKtB,eAAU,GAA0B,IAAI,CAAC;QAG/C,IAAI,CAAC,UAAU,GAAG,UAAU,CAAC;QAC7B,IAAI,CAAC,YAAY,GAAG,YAAY,CAAC;QACjC,IAAI,CAAC,aAAa,GAAG,aAAa,CAAC;QACnC,IAAI,CAAC,SAAS,GAAG,IAAI,CAAC,iBAAiB,EAAE,CAAC;QAE1C,wBAAwB;QACxB,IAAI,CAAC,UAAU,GAAG,WAAW,CAAC,GAAG,EAAE,CAAC,IAAI,CAAC,KAAK,EAAE,EAAE,IAAI,CAAC,aAAa,CAAC,CAAC;IACxE,CAAC;IAED;;OAEG;IACH,gBAAgB,CAAC,QAAkB;QACjC,IAAI,CAAC,IAAI,CAAC,IAAI,CAAC,QAAQ,CAAC,CAAC;QAEzB,0CAA0C;QAC1C,IAAI,IAAI,CAAC,IAAI,CAAC,MAAM,IAAI,IAAI,CAAC,YAAY,EAAE,CAAC;YAC1C,IAAI,CAAC,KAAK,EAAE,CAAC;QACf,CAAC;IACH,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,KAAK;QACT,IAAI,IAAI,CAAC,IAAI,CAAC,MAAM,KAAK,CAAC;YAAE,OAAO;QAEnC,MAAM,KAAK,GAAG,IAAI,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,EAAE,IAAI,CAAC,YAAY,CAAC,CAAC;QACrD,IAAI,CAAC;YACH,kDAAkD;YAClD,KAAK,MAAM,QAAQ,IAAI,KAAK,EAAE,CAAC;gBAC7B,IAAI,CAAC,UAAU,CAAC,MAAM,CAAC,QAAQ,CAAC,CAAC;YACnC,CAAC;YAED,wCAAwC;YACxC,MAAM,IAAI,CAAC,UAAU,CAAC,KAAK,EAAE,CAAC;QAChC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,OAAO,CAAC,KAAK,CAAC,sBAAsB,EAAE,KAAK,CAAC,CAAC;YAC7C,mCAAmC;QACrC,CAAC;IACH,CAAC;IAED;;OAEG;IACH,YAAY;QACV,OAAO,IAAI,CAAC,SAAS,CAAC;IACxB,CAAC;IAED;;OAEG;IACK,iBAAiB;QACvB,OAAO,cAAc,IAAI,CAAC,GAAG,EAAE,IAAI,IAAI,CAAC,MAAM,EAAE,CAAC,QAAQ,CAAC,EAAE,CAAC,CAAC,SAAS,CAAC,CAAC,EAAE,CAAC,CAAC,EAAE,CAAC;IAClF,CAAC;IAED;;OAEG;IACH,cAAc;QACZ,OAAO;YACL,SAAS,EAAE,IAAI,CAAC,IAAI,CAAC,MAAM;YAC3B,YAAY,EAAE,IAAI,CAAC,YAAY;YAC/B,aAAa,EAAE,IAAI,CAAC,aAAa;YACjC,SAAS,EAAE,IAAI,CAAC,SAAS;SAC1B,CAAC;IACJ,CAAC;IAED;;OAEG;IACH,KAAK,CAAC,QAAQ;QACZ,IAAI,IAAI,CAAC,UAAU,EAAE,CAAC;YACpB,aAAa,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;YAC/B,IAAI,CAAC,UAAU,GAAG,IAAI,CAAC;QACzB,CAAC;QAED,2BAA2B;QAC3B,MAAM,IAAI,CAAC,KAAK,EAAE,CAAC;IACrB,CAAC;CACF"}
|
|
@@ -0,0 +1,104 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* LogShipper - Centralized log shipping service for notion-mcp
|
|
3
|
+
* Sends logs to the centralized logging API endpoint with batching and retry logic
|
|
4
|
+
*/
|
|
5
|
+
export interface LogEntry {
|
|
6
|
+
timestamp: string;
|
|
7
|
+
level: string;
|
|
8
|
+
sessionId: string;
|
|
9
|
+
user: string;
|
|
10
|
+
integration: string;
|
|
11
|
+
component: string;
|
|
12
|
+
action: string;
|
|
13
|
+
message: string;
|
|
14
|
+
serverName: string;
|
|
15
|
+
projectId?: string;
|
|
16
|
+
organizationId?: string;
|
|
17
|
+
metadata?: {
|
|
18
|
+
toolParams?: any;
|
|
19
|
+
responseData?: any;
|
|
20
|
+
errorDetails?: any;
|
|
21
|
+
duration_ms?: number;
|
|
22
|
+
httpStatus?: number;
|
|
23
|
+
responseSize?: number;
|
|
24
|
+
requestId?: string;
|
|
25
|
+
executionId?: string;
|
|
26
|
+
[key: string]: any;
|
|
27
|
+
};
|
|
28
|
+
}
|
|
29
|
+
export interface LogBatch {
|
|
30
|
+
logs: LogEntry[];
|
|
31
|
+
}
|
|
32
|
+
export interface LogShipperConfig {
|
|
33
|
+
endpoint: string;
|
|
34
|
+
apiKey?: string;
|
|
35
|
+
requireApiKey?: boolean;
|
|
36
|
+
batchSize: number;
|
|
37
|
+
flushInterval: number;
|
|
38
|
+
maxRetries: number;
|
|
39
|
+
enabled: boolean;
|
|
40
|
+
}
|
|
41
|
+
export declare class LogShipper {
|
|
42
|
+
private config;
|
|
43
|
+
private logQueue;
|
|
44
|
+
private flushTimer;
|
|
45
|
+
private isShuttingDown;
|
|
46
|
+
private lastSuccessfulFlush;
|
|
47
|
+
constructor(config: LogShipperConfig);
|
|
48
|
+
private validateConfig;
|
|
49
|
+
private startFlushTimer;
|
|
50
|
+
/**
|
|
51
|
+
* Add a log entry to the queue
|
|
52
|
+
*/
|
|
53
|
+
addLog(logEntry: LogEntry): void;
|
|
54
|
+
/**
|
|
55
|
+
* Flush all queued logs to the endpoint
|
|
56
|
+
*/
|
|
57
|
+
flush(): Promise<void>;
|
|
58
|
+
/**
|
|
59
|
+
* Send logs with retry logic
|
|
60
|
+
*/
|
|
61
|
+
private sendLogsWithRetry;
|
|
62
|
+
/**
|
|
63
|
+
* Map component values to API-accepted enum values
|
|
64
|
+
*/
|
|
65
|
+
private mapComponentToValidEnum;
|
|
66
|
+
/**
|
|
67
|
+
* Map log level to API-accepted enum values (lowercase)
|
|
68
|
+
*/
|
|
69
|
+
private mapLogLevelToValidEnum;
|
|
70
|
+
/**
|
|
71
|
+
* Validate and clean log entries to ensure API compatibility
|
|
72
|
+
*/
|
|
73
|
+
private validateAndCleanLogs;
|
|
74
|
+
/**
|
|
75
|
+
* Clean metadata object to ensure JSON serialization compatibility
|
|
76
|
+
*/
|
|
77
|
+
private cleanMetadata;
|
|
78
|
+
/**
|
|
79
|
+
* Send logs to the API endpoint
|
|
80
|
+
*/
|
|
81
|
+
private sendLogs;
|
|
82
|
+
/**
|
|
83
|
+
* Generate a unique session ID
|
|
84
|
+
*/
|
|
85
|
+
private generateSessionId;
|
|
86
|
+
/**
|
|
87
|
+
* Log locally to stderr (for debugging the log shipper itself)
|
|
88
|
+
*/
|
|
89
|
+
private logLocally;
|
|
90
|
+
/**
|
|
91
|
+
* Get health status of the log shipper
|
|
92
|
+
*/
|
|
93
|
+
getHealthStatus(): {
|
|
94
|
+
healthy: boolean;
|
|
95
|
+
lastFlush?: string;
|
|
96
|
+
queueSize: number;
|
|
97
|
+
config: Partial<LogShipperConfig>;
|
|
98
|
+
};
|
|
99
|
+
/**
|
|
100
|
+
* Graceful shutdown - flush remaining logs
|
|
101
|
+
*/
|
|
102
|
+
shutdown(): Promise<void>;
|
|
103
|
+
}
|
|
104
|
+
//# sourceMappingURL=log-shipper.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log-shipper.d.ts","sourceRoot":"","sources":["../../src/services/log-shipper.ts"],"names":[],"mappings":"AAAA;;;GAGG;AAEH,MAAM,WAAW,QAAQ;IACvB,SAAS,EAAE,MAAM,CAAC;IAClB,KAAK,EAAE,MAAM,CAAC;IACd,SAAS,EAAE,MAAM,CAAC;IAClB,IAAI,EAAE,MAAM,CAAC;IACb,WAAW,EAAE,MAAM,CAAC;IACpB,SAAS,EAAE,MAAM,CAAC;IAClB,MAAM,EAAE,MAAM,CAAC;IACf,OAAO,EAAE,MAAM,CAAC;IAChB,UAAU,EAAE,MAAM,CAAC;IACnB,SAAS,CAAC,EAAE,MAAM,CAAC;IACnB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,EAAE;QAET,UAAU,CAAC,EAAE,GAAG,CAAC;QACjB,YAAY,CAAC,EAAE,GAAG,CAAC;QACnB,YAAY,CAAC,EAAE,GAAG,CAAC;QAEnB,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,UAAU,CAAC,EAAE,MAAM,CAAC;QACpB,YAAY,CAAC,EAAE,MAAM,CAAC;QAEtB,SAAS,CAAC,EAAE,MAAM,CAAC;QACnB,WAAW,CAAC,EAAE,MAAM,CAAC;QACrB,CAAC,GAAG,EAAE,MAAM,GAAG,GAAG,CAAC;KACpB,CAAC;CACH;AAED,MAAM,WAAW,QAAQ;IACvB,IAAI,EAAE,QAAQ,EAAE,CAAC;CAClB;AAED,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,EAAE,MAAM,CAAC;IACjB,MAAM,CAAC,EAAE,MAAM,CAAC;IAChB,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,SAAS,EAAE,MAAM,CAAC;IAClB,aAAa,EAAE,MAAM,CAAC;IACtB,UAAU,EAAE,MAAM,CAAC;IACnB,OAAO,EAAE,OAAO,CAAC;CAClB;AAED,qBAAa,UAAU;IACrB,OAAO,CAAC,MAAM,CAAmB;IACjC,OAAO,CAAC,QAAQ,CAAkB;IAClC,OAAO,CAAC,UAAU,CAA+B;IACjD,OAAO,CAAC,cAAc,CAAS;IAC/B,OAAO,CAAC,mBAAmB,CAAK;gBAEpB,MAAM,EAAE,gBAAgB;IAmBpC,OAAO,CAAC,cAAc;IAsBtB,OAAO,CAAC,eAAe;IAevB;;OAEG;IACH,MAAM,CAAC,QAAQ,EAAE,QAAQ,GAAG,IAAI;IAkBhC;;OAEG;IACG,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;IA8B5B;;OAEG;YACW,iBAAiB;IA6C/B;;OAEG;IACH,OAAO,CAAC,uBAAuB;IAc/B;;OAEG;IACH,OAAO,CAAC,sBAAsB;IAgB9B;;OAEG;IACH,OAAO,CAAC,oBAAoB;IA6B5B;;OAEG;IACH,OAAO,CAAC,aAAa;IA6CrB;;OAEG;YACW,QAAQ;IA6EtB;;OAEG;IACH,OAAO,CAAC,iBAAiB;IAIzB;;OAEG;IACH,OAAO,CAAC,UAAU;IAgBlB;;OAEG;IACH,eAAe,IAAI;QAAE,OAAO,EAAE,OAAO,CAAC;QAAC,SAAS,CAAC,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,OAAO,CAAC,gBAAgB,CAAC,CAAA;KAAE;IAkBjH;;OAEG;IACG,QAAQ,IAAI,OAAO,CAAC,IAAI,CAAC;CAwBhC"}
|
|
@@ -0,0 +1,384 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* LogShipper - Centralized log shipping service for notion-mcp
|
|
3
|
+
* Sends logs to the centralized logging API endpoint with batching and retry logic
|
|
4
|
+
*/
|
|
5
|
+
export class LogShipper {
|
|
6
|
+
constructor(config) {
|
|
7
|
+
this.logQueue = [];
|
|
8
|
+
this.flushTimer = null;
|
|
9
|
+
this.isShuttingDown = false;
|
|
10
|
+
this.lastSuccessfulFlush = 0;
|
|
11
|
+
this.config = config;
|
|
12
|
+
if (!this.config.enabled) {
|
|
13
|
+
return;
|
|
14
|
+
}
|
|
15
|
+
this.validateConfig();
|
|
16
|
+
this.startFlushTimer();
|
|
17
|
+
// Log initialization
|
|
18
|
+
this.logLocally('INFO', 'LogShipper initialized', {
|
|
19
|
+
endpoint: this.config.endpoint,
|
|
20
|
+
batchSize: this.config.batchSize,
|
|
21
|
+
flushInterval: this.config.flushInterval,
|
|
22
|
+
maxRetries: this.config.maxRetries
|
|
23
|
+
});
|
|
24
|
+
}
|
|
25
|
+
validateConfig() {
|
|
26
|
+
if (!this.config.endpoint) {
|
|
27
|
+
throw new Error('LogShipper: endpoint is required');
|
|
28
|
+
}
|
|
29
|
+
// API key validation based on requireApiKey flag
|
|
30
|
+
if (this.config.requireApiKey && !this.config.apiKey) {
|
|
31
|
+
throw new Error('LogShipper: apiKey is required when requireApiKey is true');
|
|
32
|
+
}
|
|
33
|
+
// Warning for missing API key during transition period
|
|
34
|
+
if (!this.config.apiKey && !this.config.requireApiKey) {
|
|
35
|
+
this.logLocally('WARN', 'API key not configured. Log shipping will work now but will require an API key in the future.', {
|
|
36
|
+
help: 'Set LOG_INGESTION_API_KEY environment variable to prepare for future requirements'
|
|
37
|
+
});
|
|
38
|
+
}
|
|
39
|
+
if (!this.config.endpoint.startsWith('https://')) {
|
|
40
|
+
throw new Error('LogShipper: endpoint must use HTTPS');
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
startFlushTimer() {
|
|
44
|
+
if (this.flushTimer) {
|
|
45
|
+
clearInterval(this.flushTimer);
|
|
46
|
+
}
|
|
47
|
+
this.flushTimer = setInterval(() => {
|
|
48
|
+
this.flush().catch(error => {
|
|
49
|
+
this.logLocally('ERROR', 'Scheduled flush failed', {
|
|
50
|
+
error: error.message,
|
|
51
|
+
queueSize: this.logQueue.length
|
|
52
|
+
});
|
|
53
|
+
});
|
|
54
|
+
}, this.config.flushInterval);
|
|
55
|
+
}
|
|
56
|
+
/**
|
|
57
|
+
* Add a log entry to the queue
|
|
58
|
+
*/
|
|
59
|
+
addLog(logEntry) {
|
|
60
|
+
if (!this.config.enabled || this.isShuttingDown) {
|
|
61
|
+
return;
|
|
62
|
+
}
|
|
63
|
+
this.logQueue.push(logEntry);
|
|
64
|
+
// Trigger immediate flush if batch size reached
|
|
65
|
+
if (this.logQueue.length >= this.config.batchSize) {
|
|
66
|
+
this.flush().catch(error => {
|
|
67
|
+
this.logLocally('ERROR', 'Immediate flush failed', {
|
|
68
|
+
error: error.message,
|
|
69
|
+
queueSize: this.logQueue.length
|
|
70
|
+
});
|
|
71
|
+
});
|
|
72
|
+
}
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* Flush all queued logs to the endpoint
|
|
76
|
+
*/
|
|
77
|
+
async flush() {
|
|
78
|
+
if (!this.config.enabled || this.logQueue.length === 0) {
|
|
79
|
+
return;
|
|
80
|
+
}
|
|
81
|
+
const batch = this.logQueue.splice(0, this.config.batchSize);
|
|
82
|
+
try {
|
|
83
|
+
await this.sendLogsWithRetry(batch);
|
|
84
|
+
this.lastSuccessfulFlush = Date.now();
|
|
85
|
+
this.logLocally('DEBUG', 'Logs shipped successfully', {
|
|
86
|
+
batchSize: batch.length,
|
|
87
|
+
queueRemaining: this.logQueue.length,
|
|
88
|
+
lastFlush: new Date(this.lastSuccessfulFlush).toISOString()
|
|
89
|
+
});
|
|
90
|
+
}
|
|
91
|
+
catch (error) {
|
|
92
|
+
// Return logs to queue on failure
|
|
93
|
+
this.logQueue.unshift(...batch);
|
|
94
|
+
this.logLocally('ERROR', 'Failed to ship logs after retries', {
|
|
95
|
+
error: error instanceof Error ? error.message : String(error),
|
|
96
|
+
batchSize: batch.length,
|
|
97
|
+
queueSize: this.logQueue.length
|
|
98
|
+
});
|
|
99
|
+
throw error;
|
|
100
|
+
}
|
|
101
|
+
}
|
|
102
|
+
/**
|
|
103
|
+
* Send logs with retry logic
|
|
104
|
+
*/
|
|
105
|
+
async sendLogsWithRetry(logs) {
|
|
106
|
+
for (let attempt = 1; attempt <= this.config.maxRetries; attempt++) {
|
|
107
|
+
try {
|
|
108
|
+
await this.sendLogs(logs);
|
|
109
|
+
return; // Success
|
|
110
|
+
}
|
|
111
|
+
catch (error) {
|
|
112
|
+
const status = error.status || error.response?.status;
|
|
113
|
+
// Don't retry on client errors (4xx except 429)
|
|
114
|
+
if (status >= 400 && status < 500 && status !== 429) {
|
|
115
|
+
this.logLocally('ERROR', 'Client error - not retrying', {
|
|
116
|
+
status,
|
|
117
|
+
error: error.message,
|
|
118
|
+
attempt
|
|
119
|
+
});
|
|
120
|
+
throw error;
|
|
121
|
+
}
|
|
122
|
+
// On last attempt, throw the error
|
|
123
|
+
if (attempt === this.config.maxRetries) {
|
|
124
|
+
this.logLocally('ERROR', 'Max retries exceeded', {
|
|
125
|
+
status,
|
|
126
|
+
error: error.message,
|
|
127
|
+
attempts: attempt
|
|
128
|
+
});
|
|
129
|
+
throw error;
|
|
130
|
+
}
|
|
131
|
+
// Calculate delay with exponential backoff
|
|
132
|
+
const baseDelay = status === 429 ? 1000 : 500; // Longer delay for rate limits
|
|
133
|
+
const delay = baseDelay * Math.pow(2, attempt - 1);
|
|
134
|
+
this.logLocally('WARN', 'Retrying log shipment', {
|
|
135
|
+
status,
|
|
136
|
+
error: error.message,
|
|
137
|
+
attempt,
|
|
138
|
+
nextAttemptIn: delay,
|
|
139
|
+
maxRetries: this.config.maxRetries
|
|
140
|
+
});
|
|
141
|
+
await new Promise(resolve => setTimeout(resolve, delay));
|
|
142
|
+
}
|
|
143
|
+
}
|
|
144
|
+
}
|
|
145
|
+
/**
|
|
146
|
+
* Map component values to API-accepted enum values
|
|
147
|
+
*/
|
|
148
|
+
mapComponentToValidEnum(component) {
|
|
149
|
+
const validComponents = ['client', 'tools', 'oauth-client'];
|
|
150
|
+
const componentMap = {
|
|
151
|
+
'server': 'client',
|
|
152
|
+
'client': 'client',
|
|
153
|
+
'tools': 'tools',
|
|
154
|
+
'oauth-client': 'oauth-client'
|
|
155
|
+
};
|
|
156
|
+
const componentStr = String(component || 'client');
|
|
157
|
+
const mapped = componentMap[componentStr.toLowerCase()];
|
|
158
|
+
return mapped || 'client'; // Default to 'client' for any unmapped components
|
|
159
|
+
}
|
|
160
|
+
/**
|
|
161
|
+
* Map log level to API-accepted enum values (lowercase)
|
|
162
|
+
*/
|
|
163
|
+
mapLogLevelToValidEnum(level) {
|
|
164
|
+
const validLevels = ['info', 'error', 'warn', 'debug'];
|
|
165
|
+
const levelMap = {
|
|
166
|
+
'info': 'info',
|
|
167
|
+
'error': 'error',
|
|
168
|
+
'warn': 'warn',
|
|
169
|
+
'warning': 'warn',
|
|
170
|
+
'debug': 'debug',
|
|
171
|
+
'fatal': 'error' // Map fatal to error as API doesn't support fatal
|
|
172
|
+
};
|
|
173
|
+
const levelStr = String(level || 'info');
|
|
174
|
+
const mapped = levelMap[levelStr.toLowerCase()];
|
|
175
|
+
return mapped || 'info'; // Default to 'info' for any unmapped levels
|
|
176
|
+
}
|
|
177
|
+
/**
|
|
178
|
+
* Validate and clean log entries to ensure API compatibility
|
|
179
|
+
*/
|
|
180
|
+
validateAndCleanLogs(logs) {
|
|
181
|
+
return logs.map(log => {
|
|
182
|
+
// Ensure all required fields are present and valid
|
|
183
|
+
const cleanedLog = {
|
|
184
|
+
timestamp: log.timestamp || new Date().toISOString(),
|
|
185
|
+
level: this.mapLogLevelToValidEnum(log.level || 'info'),
|
|
186
|
+
sessionId: log.sessionId || this.generateSessionId(),
|
|
187
|
+
user: log.user || process.env.CORETEXT_USER || 'unknown',
|
|
188
|
+
integration: log.integration || 'unknown',
|
|
189
|
+
component: this.mapComponentToValidEnum(log.component || 'client'),
|
|
190
|
+
action: log.action || 'unknown',
|
|
191
|
+
message: String(log.message || 'No message'),
|
|
192
|
+
serverName: log.serverName || 'notion-mcp',
|
|
193
|
+
projectId: log.projectId || process.env.PROJECT_ID || '',
|
|
194
|
+
organizationId: log.organizationId || process.env.ORGANIZATION_ID || ''
|
|
195
|
+
};
|
|
196
|
+
// Clean and validate metadata
|
|
197
|
+
if (log.metadata && typeof log.metadata === 'object') {
|
|
198
|
+
cleanedLog.metadata = this.cleanMetadata(log.metadata);
|
|
199
|
+
}
|
|
200
|
+
return cleanedLog;
|
|
201
|
+
}).filter(log => {
|
|
202
|
+
// Filter out any logs that still have invalid data
|
|
203
|
+
return log.timestamp && log.level && log.user && log.message;
|
|
204
|
+
});
|
|
205
|
+
}
|
|
206
|
+
/**
|
|
207
|
+
* Clean metadata object to ensure JSON serialization compatibility
|
|
208
|
+
*/
|
|
209
|
+
cleanMetadata(metadata) {
|
|
210
|
+
if (!metadata || typeof metadata !== 'object') {
|
|
211
|
+
return {};
|
|
212
|
+
}
|
|
213
|
+
const cleaned = {};
|
|
214
|
+
for (const [key, value] of Object.entries(metadata)) {
|
|
215
|
+
try {
|
|
216
|
+
// Skip undefined values
|
|
217
|
+
if (value === undefined) {
|
|
218
|
+
continue;
|
|
219
|
+
}
|
|
220
|
+
// Convert functions to string representation
|
|
221
|
+
if (typeof value === 'function') {
|
|
222
|
+
cleaned[key] = '[Function]';
|
|
223
|
+
continue;
|
|
224
|
+
}
|
|
225
|
+
// Handle circular references and complex objects
|
|
226
|
+
if (typeof value === 'object' && value !== null) {
|
|
227
|
+
try {
|
|
228
|
+
// Test if the object can be serialized
|
|
229
|
+
JSON.stringify(value);
|
|
230
|
+
cleaned[key] = value;
|
|
231
|
+
}
|
|
232
|
+
catch (e) {
|
|
233
|
+
// If serialization fails, convert to string
|
|
234
|
+
cleaned[key] = String(value);
|
|
235
|
+
}
|
|
236
|
+
}
|
|
237
|
+
else {
|
|
238
|
+
cleaned[key] = value;
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
catch (error) {
|
|
242
|
+
// If any error occurs with this field, skip it
|
|
243
|
+
this.logLocally('WARN', 'Skipping problematic metadata field', {
|
|
244
|
+
field: key,
|
|
245
|
+
error: error instanceof Error ? error.message : String(error)
|
|
246
|
+
});
|
|
247
|
+
}
|
|
248
|
+
}
|
|
249
|
+
return cleaned;
|
|
250
|
+
}
|
|
251
|
+
/**
|
|
252
|
+
* Send logs to the API endpoint
|
|
253
|
+
*/
|
|
254
|
+
async sendLogs(logs) {
|
|
255
|
+
const headers = {
|
|
256
|
+
'Content-Type': 'application/json'
|
|
257
|
+
};
|
|
258
|
+
// Only include API key header if provided
|
|
259
|
+
if (this.config.apiKey) {
|
|
260
|
+
headers['X-API-Key'] = this.config.apiKey;
|
|
261
|
+
}
|
|
262
|
+
// Validate and clean logs before sending
|
|
263
|
+
const cleanedLogs = this.validateAndCleanLogs(logs);
|
|
264
|
+
const payload = { logs: cleanedLogs };
|
|
265
|
+
// Debug logging - log the exact payload being sent
|
|
266
|
+
this.logLocally('DEBUG', 'Sending log payload', {
|
|
267
|
+
payloadSize: JSON.stringify(payload).length,
|
|
268
|
+
logCount: cleanedLogs.length,
|
|
269
|
+
endpoint: this.config.endpoint,
|
|
270
|
+
hasApiKey: !!this.config.apiKey,
|
|
271
|
+
payload: JSON.stringify(payload, null, 2)
|
|
272
|
+
});
|
|
273
|
+
const response = await fetch(this.config.endpoint, {
|
|
274
|
+
method: 'POST',
|
|
275
|
+
headers,
|
|
276
|
+
body: JSON.stringify(payload)
|
|
277
|
+
});
|
|
278
|
+
if (!response.ok) {
|
|
279
|
+
// Get response body for debugging
|
|
280
|
+
let responseBody = '';
|
|
281
|
+
try {
|
|
282
|
+
responseBody = await response.text();
|
|
283
|
+
}
|
|
284
|
+
catch (e) {
|
|
285
|
+
responseBody = 'Unable to read response body';
|
|
286
|
+
}
|
|
287
|
+
// Log detailed error information
|
|
288
|
+
this.logLocally('ERROR', 'HTTP error response from log ingestion API', {
|
|
289
|
+
status: response.status,
|
|
290
|
+
statusText: response.statusText,
|
|
291
|
+
responseBody,
|
|
292
|
+
requestPayloadSize: JSON.stringify({ logs: cleanedLogs }).length,
|
|
293
|
+
endpoint: this.config.endpoint,
|
|
294
|
+
headers: Object.keys(headers)
|
|
295
|
+
});
|
|
296
|
+
// Provide helpful message for authentication errors
|
|
297
|
+
if ((response.status === 401 || response.status === 403) && !this.config.apiKey) {
|
|
298
|
+
const error = new Error(`Authentication required (${response.status}). The log ingestion API now requires an API key. ` +
|
|
299
|
+
'Please set LOG_INGESTION_API_KEY environment variable and restart the server.');
|
|
300
|
+
error.status = response.status;
|
|
301
|
+
throw error;
|
|
302
|
+
}
|
|
303
|
+
// Provide specific error message for 400 Bad Request
|
|
304
|
+
if (response.status === 400) {
|
|
305
|
+
const error = new Error(`Bad Request (400): The log payload format is invalid. ` +
|
|
306
|
+
`Response: ${responseBody}. ` +
|
|
307
|
+
'Check the payload structure and field formats.');
|
|
308
|
+
error.status = response.status;
|
|
309
|
+
throw error;
|
|
310
|
+
}
|
|
311
|
+
const error = new Error(`HTTP ${response.status}: ${response.statusText}. Response: ${responseBody}`);
|
|
312
|
+
error.status = response.status;
|
|
313
|
+
throw error;
|
|
314
|
+
}
|
|
315
|
+
return response.json();
|
|
316
|
+
}
|
|
317
|
+
/**
|
|
318
|
+
* Generate a unique session ID
|
|
319
|
+
*/
|
|
320
|
+
generateSessionId() {
|
|
321
|
+
return `notion-mcp-${Date.now()}-${Math.random().toString(36).substring(2, 9)}`;
|
|
322
|
+
}
|
|
323
|
+
/**
|
|
324
|
+
* Log locally to stderr (for debugging the log shipper itself)
|
|
325
|
+
*/
|
|
326
|
+
logLocally(level, message, metadata) {
|
|
327
|
+
const timestamp = new Date().toISOString();
|
|
328
|
+
const user = process.env.CORETEXT_USER || 'unknown';
|
|
329
|
+
const logEntry = {
|
|
330
|
+
timestamp,
|
|
331
|
+
user,
|
|
332
|
+
component: 'log-shipper',
|
|
333
|
+
level,
|
|
334
|
+
message,
|
|
335
|
+
...(metadata && { metadata })
|
|
336
|
+
};
|
|
337
|
+
console.error(`[NOTION-MCP-LOG-SHIPPER] ${JSON.stringify(logEntry)}`);
|
|
338
|
+
}
|
|
339
|
+
/**
|
|
340
|
+
* Get health status of the log shipper
|
|
341
|
+
*/
|
|
342
|
+
getHealthStatus() {
|
|
343
|
+
const now = Date.now();
|
|
344
|
+
const timeSinceLastFlush = now - this.lastSuccessfulFlush;
|
|
345
|
+
const isHealthy = this.config.enabled && (this.lastSuccessfulFlush === 0 || timeSinceLastFlush < this.config.flushInterval * 3);
|
|
346
|
+
return {
|
|
347
|
+
healthy: isHealthy,
|
|
348
|
+
lastFlush: this.lastSuccessfulFlush > 0 ? new Date(this.lastSuccessfulFlush).toISOString() : undefined,
|
|
349
|
+
queueSize: this.logQueue.length,
|
|
350
|
+
config: {
|
|
351
|
+
enabled: this.config.enabled,
|
|
352
|
+
endpoint: this.config.endpoint,
|
|
353
|
+
batchSize: this.config.batchSize,
|
|
354
|
+
flushInterval: this.config.flushInterval
|
|
355
|
+
}
|
|
356
|
+
};
|
|
357
|
+
}
|
|
358
|
+
/**
|
|
359
|
+
* Graceful shutdown - flush remaining logs
|
|
360
|
+
*/
|
|
361
|
+
async shutdown() {
|
|
362
|
+
this.isShuttingDown = true;
|
|
363
|
+
if (this.flushTimer) {
|
|
364
|
+
clearInterval(this.flushTimer);
|
|
365
|
+
this.flushTimer = null;
|
|
366
|
+
}
|
|
367
|
+
this.logLocally('INFO', 'LogShipper shutting down', {
|
|
368
|
+
queueSize: this.logQueue.length
|
|
369
|
+
});
|
|
370
|
+
if (this.logQueue.length > 0) {
|
|
371
|
+
try {
|
|
372
|
+
await this.flush();
|
|
373
|
+
this.logLocally('INFO', 'Final flush completed successfully');
|
|
374
|
+
}
|
|
375
|
+
catch (error) {
|
|
376
|
+
this.logLocally('ERROR', 'Final flush failed', {
|
|
377
|
+
error: error instanceof Error ? error.message : String(error),
|
|
378
|
+
lostLogs: this.logQueue.length
|
|
379
|
+
});
|
|
380
|
+
}
|
|
381
|
+
}
|
|
382
|
+
}
|
|
383
|
+
}
|
|
384
|
+
//# sourceMappingURL=log-shipper.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"log-shipper.js","sourceRoot":"","sources":["../../src/services/log-shipper.ts"],"names":[],"mappings":"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"}
|