@litmers/cursorflow-orchestrator 0.1.40 → 0.2.3
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/CHANGELOG.md +0 -2
- package/README.md +8 -3
- package/commands/cursorflow-init.md +0 -4
- package/dist/cli/index.js +0 -6
- package/dist/cli/index.js.map +1 -1
- package/dist/cli/logs.js +108 -9
- package/dist/cli/logs.js.map +1 -1
- package/dist/cli/models.js +20 -3
- package/dist/cli/models.js.map +1 -1
- package/dist/cli/monitor.d.ts +7 -10
- package/dist/cli/monitor.js +1103 -1239
- package/dist/cli/monitor.js.map +1 -1
- package/dist/cli/resume.js +21 -1
- package/dist/cli/resume.js.map +1 -1
- package/dist/cli/run.js +28 -9
- package/dist/cli/run.js.map +1 -1
- package/dist/cli/signal.d.ts +6 -1
- package/dist/cli/signal.js +99 -13
- package/dist/cli/signal.js.map +1 -1
- package/dist/cli/tasks.js +3 -46
- package/dist/cli/tasks.js.map +1 -1
- package/dist/core/agent-supervisor.d.ts +23 -0
- package/dist/core/agent-supervisor.js +42 -0
- package/dist/core/agent-supervisor.js.map +1 -0
- package/dist/core/auto-recovery.d.ts +3 -117
- package/dist/core/auto-recovery.js +4 -482
- package/dist/core/auto-recovery.js.map +1 -1
- package/dist/core/failure-policy.d.ts +0 -53
- package/dist/core/failure-policy.js +7 -175
- package/dist/core/failure-policy.js.map +1 -1
- package/dist/core/git-lifecycle-manager.d.ts +284 -0
- package/dist/core/git-lifecycle-manager.js +778 -0
- package/dist/core/git-lifecycle-manager.js.map +1 -0
- package/dist/core/git-pipeline-coordinator.d.ts +21 -0
- package/dist/core/git-pipeline-coordinator.js +205 -0
- package/dist/core/git-pipeline-coordinator.js.map +1 -0
- package/dist/core/intervention.d.ts +170 -0
- package/dist/core/intervention.js +408 -0
- package/dist/core/intervention.js.map +1 -0
- package/dist/core/lane-state-machine.d.ts +423 -0
- package/dist/core/lane-state-machine.js +890 -0
- package/dist/core/lane-state-machine.js.map +1 -0
- package/dist/core/orchestrator.d.ts +4 -1
- package/dist/core/orchestrator.js +39 -65
- package/dist/core/orchestrator.js.map +1 -1
- package/dist/core/runner/agent.d.ts +7 -1
- package/dist/core/runner/agent.js +54 -36
- package/dist/core/runner/agent.js.map +1 -1
- package/dist/core/runner/pipeline.js +283 -123
- package/dist/core/runner/pipeline.js.map +1 -1
- package/dist/core/runner/task.d.ts +4 -5
- package/dist/core/runner/task.js +6 -80
- package/dist/core/runner/task.js.map +1 -1
- package/dist/core/runner.js +8 -2
- package/dist/core/runner.js.map +1 -1
- package/dist/core/stall-detection.d.ts +11 -4
- package/dist/core/stall-detection.js +64 -27
- package/dist/core/stall-detection.js.map +1 -1
- package/dist/hooks/contexts/index.d.ts +104 -0
- package/dist/hooks/contexts/index.js +134 -0
- package/dist/hooks/contexts/index.js.map +1 -0
- package/dist/hooks/data-accessor.d.ts +86 -0
- package/dist/hooks/data-accessor.js +410 -0
- package/dist/hooks/data-accessor.js.map +1 -0
- package/dist/hooks/flow-controller.d.ts +136 -0
- package/dist/hooks/flow-controller.js +351 -0
- package/dist/hooks/flow-controller.js.map +1 -0
- package/dist/hooks/index.d.ts +68 -0
- package/dist/hooks/index.js +105 -0
- package/dist/hooks/index.js.map +1 -0
- package/dist/hooks/manager.d.ts +129 -0
- package/dist/hooks/manager.js +389 -0
- package/dist/hooks/manager.js.map +1 -0
- package/dist/hooks/types.d.ts +463 -0
- package/dist/hooks/types.js +45 -0
- package/dist/hooks/types.js.map +1 -0
- package/dist/services/logging/buffer.d.ts +2 -2
- package/dist/services/logging/buffer.js +95 -42
- package/dist/services/logging/buffer.js.map +1 -1
- package/dist/services/logging/console.js +6 -1
- package/dist/services/logging/console.js.map +1 -1
- package/dist/services/logging/formatter.d.ts +9 -4
- package/dist/services/logging/formatter.js +64 -18
- package/dist/services/logging/formatter.js.map +1 -1
- package/dist/services/logging/index.d.ts +0 -1
- package/dist/services/logging/index.js +0 -1
- package/dist/services/logging/index.js.map +1 -1
- package/dist/services/logging/paths.d.ts +8 -0
- package/dist/services/logging/paths.js +48 -0
- package/dist/services/logging/paths.js.map +1 -0
- package/dist/services/logging/raw-log.d.ts +6 -0
- package/dist/services/logging/raw-log.js +37 -0
- package/dist/services/logging/raw-log.js.map +1 -0
- package/dist/services/process/index.js +1 -1
- package/dist/services/process/index.js.map +1 -1
- package/dist/types/agent.d.ts +15 -0
- package/dist/types/config.d.ts +22 -1
- package/dist/types/event-categories.d.ts +601 -0
- package/dist/types/event-categories.js +233 -0
- package/dist/types/event-categories.js.map +1 -0
- package/dist/types/events.d.ts +0 -20
- package/dist/types/flow.d.ts +10 -6
- package/dist/types/index.d.ts +1 -1
- package/dist/types/index.js +17 -3
- package/dist/types/index.js.map +1 -1
- package/dist/types/lane.d.ts +1 -1
- package/dist/types/logging.d.ts +1 -1
- package/dist/types/task.d.ts +12 -1
- package/dist/ui/log-viewer.d.ts +3 -0
- package/dist/ui/log-viewer.js +3 -0
- package/dist/ui/log-viewer.js.map +1 -1
- package/dist/utils/config.js +10 -1
- package/dist/utils/config.js.map +1 -1
- package/dist/utils/cursor-agent.d.ts +11 -1
- package/dist/utils/cursor-agent.js +63 -16
- package/dist/utils/cursor-agent.js.map +1 -1
- package/dist/utils/enhanced-logger.d.ts +5 -1
- package/dist/utils/enhanced-logger.js +98 -19
- package/dist/utils/enhanced-logger.js.map +1 -1
- package/dist/utils/event-registry.d.ts +222 -0
- package/dist/utils/event-registry.js +463 -0
- package/dist/utils/event-registry.js.map +1 -0
- package/dist/utils/events.d.ts +1 -13
- package/dist/utils/events.js.map +1 -1
- package/dist/utils/flow.d.ts +10 -0
- package/dist/utils/flow.js +75 -0
- package/dist/utils/flow.js.map +1 -1
- package/dist/utils/log-constants.d.ts +1 -0
- package/dist/utils/log-constants.js +2 -1
- package/dist/utils/log-constants.js.map +1 -1
- package/dist/utils/log-formatter.d.ts +2 -1
- package/dist/utils/log-formatter.js +10 -10
- package/dist/utils/log-formatter.js.map +1 -1
- package/dist/utils/logger.d.ts +11 -0
- package/dist/utils/logger.js +82 -3
- package/dist/utils/logger.js.map +1 -1
- package/dist/utils/repro-thinking-logs.js +0 -13
- package/dist/utils/repro-thinking-logs.js.map +1 -1
- package/dist/utils/run-service.js +1 -1
- package/dist/utils/run-service.js.map +1 -1
- package/examples/README.md +0 -2
- package/examples/demo-project/README.md +1 -2
- package/package.json +13 -34
- package/scripts/setup-security.sh +0 -1
- package/scripts/test-log-parser.ts +171 -0
- package/scripts/verify-change.sh +272 -0
- package/src/cli/index.ts +0 -6
- package/src/cli/logs.ts +121 -10
- package/src/cli/models.ts +20 -3
- package/src/cli/monitor.ts +1273 -1342
- package/src/cli/resume.ts +27 -1
- package/src/cli/run.ts +29 -11
- package/src/cli/signal.ts +120 -18
- package/src/cli/tasks.ts +2 -59
- package/src/core/agent-supervisor.ts +64 -0
- package/src/core/auto-recovery.ts +14 -590
- package/src/core/failure-policy.ts +7 -229
- package/src/core/git-lifecycle-manager.ts +1011 -0
- package/src/core/git-pipeline-coordinator.ts +221 -0
- package/src/core/intervention.ts +463 -0
- package/src/core/lane-state-machine.ts +1097 -0
- package/src/core/orchestrator.ts +48 -64
- package/src/core/runner/agent.ts +77 -39
- package/src/core/runner/pipeline.ts +318 -138
- package/src/core/runner/task.ts +12 -97
- package/src/core/runner.ts +8 -2
- package/src/core/stall-detection.ts +74 -27
- package/src/hooks/contexts/index.ts +256 -0
- package/src/hooks/data-accessor.ts +488 -0
- package/src/hooks/flow-controller.ts +425 -0
- package/src/hooks/index.ts +154 -0
- package/src/hooks/manager.ts +434 -0
- package/src/hooks/types.ts +544 -0
- package/src/services/logging/buffer.ts +104 -43
- package/src/services/logging/console.ts +7 -1
- package/src/services/logging/formatter.ts +74 -18
- package/src/services/logging/index.ts +0 -2
- package/src/services/logging/paths.ts +14 -0
- package/src/services/logging/raw-log.ts +43 -0
- package/src/services/process/index.ts +1 -1
- package/src/types/agent.ts +15 -0
- package/src/types/config.ts +23 -1
- package/src/types/event-categories.ts +663 -0
- package/src/types/events.ts +0 -25
- package/src/types/flow.ts +10 -6
- package/src/types/index.ts +50 -4
- package/src/types/lane.ts +1 -2
- package/src/types/logging.ts +2 -1
- package/src/types/task.ts +12 -1
- package/src/ui/log-viewer.ts +3 -0
- package/src/utils/config.ts +11 -1
- package/src/utils/cursor-agent.ts +68 -16
- package/src/utils/enhanced-logger.ts +105 -19
- package/src/utils/event-registry.ts +595 -0
- package/src/utils/events.ts +0 -16
- package/src/utils/flow.ts +83 -0
- package/src/utils/log-constants.ts +2 -1
- package/src/utils/log-formatter.ts +10 -11
- package/src/utils/logger.ts +49 -3
- package/src/utils/repro-thinking-logs.ts +0 -15
- package/src/utils/run-service.ts +1 -1
- package/dist/cli/prepare.d.ts +0 -7
- package/dist/cli/prepare.js +0 -690
- package/dist/cli/prepare.js.map +0 -1
- package/dist/services/logging/file-writer.d.ts +0 -71
- package/dist/services/logging/file-writer.js +0 -516
- package/dist/services/logging/file-writer.js.map +0 -1
- package/dist/types/review.d.ts +0 -17
- package/dist/types/review.js +0 -6
- package/dist/types/review.js.map +0 -1
- package/scripts/ai-security-check.js +0 -233
- package/src/cli/prepare.ts +0 -777
- package/src/services/logging/file-writer.ts +0 -526
- package/src/types/review.ts +0 -20
package/src/types/index.ts
CHANGED
|
@@ -27,12 +27,58 @@ export {
|
|
|
27
27
|
// Agent
|
|
28
28
|
export * from './agent';
|
|
29
29
|
|
|
30
|
-
//
|
|
31
|
-
export * from './review';
|
|
32
|
-
|
|
33
|
-
// Events
|
|
30
|
+
// Events (기존 - 호환성 유지)
|
|
34
31
|
export * from './events';
|
|
35
32
|
|
|
33
|
+
// Event Categories (v2.1 - 카테고리별 분류, 새 아키텍처)
|
|
34
|
+
// 중복 이름은 명시적으로 제외하고 새 카테고리 관련 타입만 export
|
|
35
|
+
export {
|
|
36
|
+
// Event Categories
|
|
37
|
+
EventCategory,
|
|
38
|
+
|
|
39
|
+
// Event Type Enums
|
|
40
|
+
OrchestrationEventType,
|
|
41
|
+
LaneEventType,
|
|
42
|
+
TaskEventType,
|
|
43
|
+
GitEventType,
|
|
44
|
+
RecoveryEventType,
|
|
45
|
+
AgentEventType,
|
|
46
|
+
StateEventType,
|
|
47
|
+
SystemEventType,
|
|
48
|
+
AllEventTypes,
|
|
49
|
+
|
|
50
|
+
// Event Payload Map & Typed Event
|
|
51
|
+
EventPayloadMap,
|
|
52
|
+
TypedCursorFlowEvent,
|
|
53
|
+
TypedEventHandler,
|
|
54
|
+
GenericEventHandler,
|
|
55
|
+
getCategoryFromEventType,
|
|
56
|
+
|
|
57
|
+
// New Payload Types (이름 충돌 없는 것들)
|
|
58
|
+
CycleDetectedPayload,
|
|
59
|
+
LaneWaitingPayload,
|
|
60
|
+
LaneBlockedPayload,
|
|
61
|
+
TaskRetryPayload,
|
|
62
|
+
TaskWaitingDependencyPayload,
|
|
63
|
+
GitBranchCreatedPayload,
|
|
64
|
+
GitCommittedPayload,
|
|
65
|
+
GitPushedPayload,
|
|
66
|
+
GitMergeStartedPayload,
|
|
67
|
+
GitMergeCompletedPayload,
|
|
68
|
+
GitMergeConflictPayload,
|
|
69
|
+
GitPushRejectedPayload,
|
|
70
|
+
GitErrorPayload,
|
|
71
|
+
RecoveryStartedPayload,
|
|
72
|
+
RecoveryConflictResolvedPayload,
|
|
73
|
+
AgentConnectionErrorPayload,
|
|
74
|
+
StateTransitionPayload,
|
|
75
|
+
StateTransitionFailedPayload,
|
|
76
|
+
StateCorruptedPayload,
|
|
77
|
+
StateRepairedPayload,
|
|
78
|
+
SystemHealthCheckPayload,
|
|
79
|
+
SystemSignalReceivedPayload,
|
|
80
|
+
} from './event-categories';
|
|
81
|
+
|
|
36
82
|
// Logging
|
|
37
83
|
export * from './logging';
|
|
38
84
|
|
package/src/types/lane.ts
CHANGED
package/src/types/logging.ts
CHANGED
package/src/types/task.ts
CHANGED
|
@@ -13,6 +13,8 @@ export interface Task {
|
|
|
13
13
|
dependsOn?: string[];
|
|
14
14
|
/** Task execution timeout in milliseconds. Overrides lane-level timeout. */
|
|
15
15
|
timeout?: number;
|
|
16
|
+
/** Enable browser automation for this task. Required for web testing/scraping. */
|
|
17
|
+
browser?: boolean;
|
|
16
18
|
}
|
|
17
19
|
|
|
18
20
|
export interface RunnerConfig {
|
|
@@ -26,7 +28,7 @@ export interface RunnerConfig {
|
|
|
26
28
|
model?: string;
|
|
27
29
|
dependencyPolicy: DependencyPolicy;
|
|
28
30
|
/** Output format for cursor-agent (default: 'json') */
|
|
29
|
-
agentOutputFormat?: 'json' | '
|
|
31
|
+
agentOutputFormat?: 'json' | 'stream-json';
|
|
30
32
|
/** Task execution timeout in milliseconds. Default: 600000 (10 minutes) */
|
|
31
33
|
timeout?: number;
|
|
32
34
|
/**
|
|
@@ -40,6 +42,15 @@ export interface RunnerConfig {
|
|
|
40
42
|
* Default: false
|
|
41
43
|
*/
|
|
42
44
|
verboseGit?: boolean;
|
|
45
|
+
/**
|
|
46
|
+
* Enable browser automation for all tasks in this config.
|
|
47
|
+
* Required for web testing/scraping.
|
|
48
|
+
*/
|
|
49
|
+
browser?: boolean;
|
|
50
|
+
/** Auto-approve commands (--force flag). Default: true */
|
|
51
|
+
autoApproveCommands?: boolean;
|
|
52
|
+
/** Auto-approve MCP servers (--approve-mcps flag). Default: true */
|
|
53
|
+
autoApproveMcps?: boolean;
|
|
43
54
|
}
|
|
44
55
|
|
|
45
56
|
export interface TaskDirInfo {
|
package/src/ui/log-viewer.ts
CHANGED
|
@@ -8,6 +8,9 @@
|
|
|
8
8
|
* - Importance filtering
|
|
9
9
|
* - Text search
|
|
10
10
|
* - Readable format toggle
|
|
11
|
+
*
|
|
12
|
+
* Note: This viewer only reads lane/subprocess logs. Main process logs are
|
|
13
|
+
* written to the run-level main log file and shown by default in CLI logs.
|
|
11
14
|
*/
|
|
12
15
|
|
|
13
16
|
import * as readline from 'readline';
|
package/src/utils/config.ts
CHANGED
|
@@ -96,6 +96,11 @@ export function loadConfig(projectRoot: string | null = null): CursorFlowConfig
|
|
|
96
96
|
// Default AI model
|
|
97
97
|
defaultModel: 'gemini-3-flash',
|
|
98
98
|
|
|
99
|
+
// Agent execution flags (cursor-agent CLI options)
|
|
100
|
+
autoApproveCommands: true, // --force flag
|
|
101
|
+
autoApproveMcps: true, // --approve-mcps flag
|
|
102
|
+
browser: true, // --browser flag
|
|
103
|
+
|
|
99
104
|
// Internal
|
|
100
105
|
projectRoot,
|
|
101
106
|
};
|
|
@@ -212,7 +217,7 @@ export function createDefaultConfig(projectRoot: string, force = false): string
|
|
|
212
217
|
// Advanced
|
|
213
218
|
worktreePrefix: 'cursorflow-',
|
|
214
219
|
maxConcurrentLanes: 10,
|
|
215
|
-
agentOutputFormat: 'json', // 'json' | '
|
|
220
|
+
agentOutputFormat: 'stream-json', // 'json' | 'stream-json'
|
|
216
221
|
|
|
217
222
|
// Webhook configuration
|
|
218
223
|
// webhooks: [
|
|
@@ -234,6 +239,11 @@ export function createDefaultConfig(projectRoot: string, force = false): string
|
|
|
234
239
|
writeJsonLog: true, // Write structured JSON logs
|
|
235
240
|
timestampFormat: 'iso', // 'iso' | 'relative' | 'short'
|
|
236
241
|
},
|
|
242
|
+
|
|
243
|
+
// Agent execution flags (cursor-agent CLI options)
|
|
244
|
+
autoApproveCommands: true, // --force flag
|
|
245
|
+
autoApproveMcps: true, // --approve-mcps flag
|
|
246
|
+
browser: false, // --browser flag
|
|
237
247
|
};
|
|
238
248
|
`;
|
|
239
249
|
|
|
@@ -110,19 +110,45 @@ export function validateSetup(executor = 'cursor-agent'): { valid: boolean; erro
|
|
|
110
110
|
};
|
|
111
111
|
}
|
|
112
112
|
|
|
113
|
+
/**
|
|
114
|
+
* Known models in cursor-agent (2025.12 version)
|
|
115
|
+
* Reference: docs/CURSOR_AGENT_GUIDE.md
|
|
116
|
+
*/
|
|
117
|
+
export const KNOWN_MODELS = [
|
|
118
|
+
// Special modes
|
|
119
|
+
'composer-1',
|
|
120
|
+
'auto',
|
|
121
|
+
// Anthropic Claude models
|
|
122
|
+
'sonnet-4.5',
|
|
123
|
+
'sonnet-4.5-thinking',
|
|
124
|
+
'opus-4.5',
|
|
125
|
+
'opus-4.5-thinking',
|
|
126
|
+
'opus-4.1',
|
|
127
|
+
// Google Gemini models
|
|
128
|
+
'gemini-3-flash',
|
|
129
|
+
'gemini-3-pro',
|
|
130
|
+
// OpenAI GPT models
|
|
131
|
+
'gpt-5.2',
|
|
132
|
+
'gpt-5.2-high',
|
|
133
|
+
'gpt-5.1',
|
|
134
|
+
'gpt-5.1-high',
|
|
135
|
+
// OpenAI Codex models
|
|
136
|
+
'gpt-5.1-codex',
|
|
137
|
+
'gpt-5.1-codex-high',
|
|
138
|
+
'gpt-5.1-codex-max',
|
|
139
|
+
'gpt-5.1-codex-max-high',
|
|
140
|
+
// xAI
|
|
141
|
+
'grok',
|
|
142
|
+
] as const;
|
|
143
|
+
|
|
144
|
+
export type KnownModel = typeof KNOWN_MODELS[number];
|
|
145
|
+
|
|
113
146
|
/**
|
|
114
147
|
* Get available models (if cursor-agent supports it)
|
|
115
148
|
*/
|
|
116
149
|
export function getAvailableModels(): string[] {
|
|
117
|
-
//
|
|
118
|
-
const knownModels = [
|
|
119
|
-
'sonnet-4.5',
|
|
120
|
-
'sonnet-4.5-thinking',
|
|
121
|
-
'opus-4.5',
|
|
122
|
-
'opus-4.5-thinking',
|
|
123
|
-
'gpt-5.2',
|
|
124
|
-
'gpt-5.2-high',
|
|
125
|
-
];
|
|
150
|
+
// Use the known models list
|
|
151
|
+
const knownModels = [...KNOWN_MODELS];
|
|
126
152
|
|
|
127
153
|
try {
|
|
128
154
|
// Try to trigger a model list by using an invalid model with --print
|
|
@@ -236,34 +262,49 @@ export interface AuthCheckResult {
|
|
|
236
262
|
}
|
|
237
263
|
|
|
238
264
|
/**
|
|
239
|
-
* Check cursor-agent authentication
|
|
265
|
+
* Check cursor-agent authentication using status/whoami command
|
|
266
|
+
* This is faster and has no side effects (unlike create-chat which creates a session)
|
|
267
|
+
*
|
|
268
|
+
* Reference: docs/CURSOR_AGENT_GUIDE.md
|
|
269
|
+
* Expected output: " ✓ Logged in as user@email.com"
|
|
240
270
|
*/
|
|
241
271
|
export function checkCursorAuth(): AuthCheckResult {
|
|
242
272
|
try {
|
|
243
|
-
|
|
273
|
+
// Use 'status' command (or 'whoami' alias) - faster than create-chat
|
|
274
|
+
const result = spawnSync('cursor-agent', ['status'], {
|
|
244
275
|
encoding: 'utf8',
|
|
245
276
|
stdio: 'pipe',
|
|
246
277
|
timeout: 10000, // 10 second timeout
|
|
247
278
|
});
|
|
248
279
|
|
|
249
|
-
|
|
280
|
+
const output = (result.stdout?.trim() || '').toString();
|
|
281
|
+
const errorOutput = (result.stderr?.trim() || '').toString();
|
|
282
|
+
|
|
283
|
+
// Check for successful login (output contains "Logged in as")
|
|
284
|
+
if (result.status === 0 && output.includes('Logged in')) {
|
|
285
|
+
// Extract email if present
|
|
286
|
+
const emailMatch = output.match(/Logged in as\s+(\S+)/i);
|
|
287
|
+
const email = emailMatch ? emailMatch[1] : undefined;
|
|
288
|
+
|
|
250
289
|
return {
|
|
251
290
|
authenticated: true,
|
|
252
291
|
message: 'Cursor authentication OK',
|
|
292
|
+
details: email ? `Logged in as ${email}` : undefined,
|
|
253
293
|
};
|
|
254
294
|
}
|
|
255
295
|
|
|
256
|
-
const errorMsg =
|
|
296
|
+
const errorMsg = errorOutput || output;
|
|
257
297
|
|
|
258
298
|
// Check for authentication errors
|
|
259
299
|
if (errorMsg.includes('not authenticated') ||
|
|
300
|
+
errorMsg.includes('not logged') ||
|
|
260
301
|
errorMsg.includes('login') ||
|
|
261
302
|
errorMsg.includes('auth')) {
|
|
262
303
|
return {
|
|
263
304
|
authenticated: false,
|
|
264
305
|
message: 'Not authenticated with Cursor',
|
|
265
306
|
details: errorMsg,
|
|
266
|
-
help: '
|
|
307
|
+
help: 'Run: cursor-agent login',
|
|
267
308
|
};
|
|
268
309
|
}
|
|
269
310
|
|
|
@@ -279,13 +320,24 @@ export function checkCursorAuth(): AuthCheckResult {
|
|
|
279
320
|
};
|
|
280
321
|
}
|
|
281
322
|
|
|
323
|
+
// If status command failed but no specific error, might still be authenticated
|
|
324
|
+
// Fall back to checking if cursor-agent is responsive
|
|
325
|
+
if (result.status !== 0) {
|
|
326
|
+
return {
|
|
327
|
+
authenticated: false,
|
|
328
|
+
message: 'Authentication status check failed',
|
|
329
|
+
details: errorMsg || `Exit code: ${result.status}`,
|
|
330
|
+
help: 'Try running: cursor-agent status',
|
|
331
|
+
};
|
|
332
|
+
}
|
|
333
|
+
|
|
282
334
|
return {
|
|
283
335
|
authenticated: false,
|
|
284
|
-
message: 'Unknown
|
|
336
|
+
message: 'Unknown authentication status',
|
|
285
337
|
details: errorMsg,
|
|
286
338
|
};
|
|
287
339
|
} catch (error: any) {
|
|
288
|
-
if (error.code === 'ETIMEDOUT') {
|
|
340
|
+
if (error.code === 'ETIMEDOUT' || error.killed) {
|
|
289
341
|
return {
|
|
290
342
|
authenticated: false,
|
|
291
343
|
message: 'Connection timeout',
|
|
@@ -11,6 +11,7 @@ import * as path from 'path';
|
|
|
11
11
|
import { EnhancedLogConfig, ParsedMessage, LogSession } from '../types';
|
|
12
12
|
import { formatMessageForConsole } from './log-formatter';
|
|
13
13
|
import { safeJoin } from './path';
|
|
14
|
+
import { getLaneLogPath } from '../services/logging/paths';
|
|
14
15
|
|
|
15
16
|
export { EnhancedLogConfig, ParsedMessage, LogSession };
|
|
16
17
|
|
|
@@ -115,9 +116,11 @@ export class EnhancedLogManager {
|
|
|
115
116
|
// Ensure log directory exists
|
|
116
117
|
fs.mkdirSync(logDir, { recursive: true });
|
|
117
118
|
|
|
119
|
+
// Subprocess (lane) logs live in the lane run directory to avoid nesting with main logs.
|
|
120
|
+
// Main process logs are written separately to a run-level file (see utils/logger.ts).
|
|
118
121
|
// Set up log file paths (simplified)
|
|
119
|
-
this.rawLogPath =
|
|
120
|
-
this.readableLogPath =
|
|
122
|
+
this.rawLogPath = getLaneLogPath(logDir, 'raw');
|
|
123
|
+
this.readableLogPath = getLaneLogPath(logDir, 'readable');
|
|
121
124
|
|
|
122
125
|
// Initialize log files
|
|
123
126
|
this.initLogFiles();
|
|
@@ -131,13 +134,13 @@ export class EnhancedLogManager {
|
|
|
131
134
|
}
|
|
132
135
|
|
|
133
136
|
/**
|
|
134
|
-
* Get lane-task label like [1-1-
|
|
137
|
+
* Get lane-task label like [1-1-refactor]
|
|
135
138
|
*/
|
|
136
139
|
private getLaneTaskLabel(): string {
|
|
137
140
|
const laneNum = (this.session.laneIndex ?? 0) + 1;
|
|
138
141
|
const taskNum = (this.session.taskIndex ?? 0) + 1;
|
|
139
|
-
const shortLaneName = this.session.laneName.substring(0,
|
|
140
|
-
return `${laneNum}-${taskNum}-${shortLaneName}
|
|
142
|
+
const shortLaneName = this.session.laneName.substring(0, 8);
|
|
143
|
+
return `${laneNum}-${taskNum}-${shortLaneName}`;
|
|
141
144
|
}
|
|
142
145
|
|
|
143
146
|
/**
|
|
@@ -308,6 +311,17 @@ export class EnhancedLogManager {
|
|
|
308
311
|
this.writeReadableMessage(msg);
|
|
309
312
|
continue;
|
|
310
313
|
}
|
|
314
|
+
// parseJsonToMessage returned null - create fallback message for known JSON
|
|
315
|
+
if (json.type) {
|
|
316
|
+
const fallbackMsg: ParsedMessage = {
|
|
317
|
+
type: 'info',
|
|
318
|
+
role: 'system',
|
|
319
|
+
content: `[${json.type}] ${json.subtype || ''} ${JSON.stringify(json).substring(0, 150)}...`,
|
|
320
|
+
timestamp: json.timestamp_ms || Date.now(),
|
|
321
|
+
};
|
|
322
|
+
this.writeReadableMessage(fallbackMsg);
|
|
323
|
+
continue;
|
|
324
|
+
}
|
|
311
325
|
} catch {
|
|
312
326
|
// Not valid JSON, fall through
|
|
313
327
|
}
|
|
@@ -318,16 +332,38 @@ export class EnhancedLogManager {
|
|
|
318
332
|
if (cleanLine && !this.isNoiseLog(cleanLine)) {
|
|
319
333
|
const hasTimestamp = /^\[(\d{4}-\d{2}-\d{2}T|\d{2}:\d{2}:\d{2})\]/.test(cleanLine);
|
|
320
334
|
const label = this.getLaneTaskLabel();
|
|
335
|
+
const ts = this.getShortTime();
|
|
321
336
|
|
|
337
|
+
// For file output, use clean line (no ANSI codes)
|
|
338
|
+
let fileFormattedLine: string;
|
|
322
339
|
if (hasTimestamp) {
|
|
323
|
-
|
|
324
|
-
const formatted = cleanLine.includes(`[${label}]`)
|
|
340
|
+
fileFormattedLine = cleanLine.includes(`[${label}]`)
|
|
325
341
|
? cleanLine
|
|
326
342
|
: cleanLine.replace(/^(\[[^\]]+\])/, `$1 [${label}]`);
|
|
327
|
-
this.writeToReadableLog(`${formatted}\n`);
|
|
328
343
|
} else {
|
|
329
|
-
|
|
330
|
-
|
|
344
|
+
fileFormattedLine = `[${ts}] [${label}] ${cleanLine}`;
|
|
345
|
+
}
|
|
346
|
+
|
|
347
|
+
this.writeToReadableLog(`${fileFormattedLine}\n`);
|
|
348
|
+
|
|
349
|
+
// For console output, preserve ANSI colors from original line
|
|
350
|
+
if (this.onParsedMessage) {
|
|
351
|
+
let consoleFormattedLine: string;
|
|
352
|
+
if (hasTimestamp) {
|
|
353
|
+
consoleFormattedLine = trimmed.includes(`[${label}]`)
|
|
354
|
+
? trimmed
|
|
355
|
+
: trimmed.replace(/^(\[[^\]]+\])/, `$1 [${label}]`);
|
|
356
|
+
} else {
|
|
357
|
+
consoleFormattedLine = `[${ts}] [${label}] ${trimmed}`;
|
|
358
|
+
}
|
|
359
|
+
|
|
360
|
+
const rawMsg: ParsedMessage = {
|
|
361
|
+
type: 'raw',
|
|
362
|
+
role: 'system',
|
|
363
|
+
content: consoleFormattedLine,
|
|
364
|
+
timestamp: Date.now(),
|
|
365
|
+
};
|
|
366
|
+
this.onParsedMessage(rawMsg);
|
|
331
367
|
}
|
|
332
368
|
}
|
|
333
369
|
}
|
|
@@ -426,6 +462,15 @@ export class EnhancedLogManager {
|
|
|
426
462
|
return null;
|
|
427
463
|
|
|
428
464
|
default:
|
|
465
|
+
// Fallback: show unknown JSON types with basic formatting
|
|
466
|
+
if (type) {
|
|
467
|
+
return {
|
|
468
|
+
type: 'info',
|
|
469
|
+
role: 'system',
|
|
470
|
+
content: `[${type}] ${JSON.stringify(json).substring(0, 200)}`,
|
|
471
|
+
timestamp,
|
|
472
|
+
};
|
|
473
|
+
}
|
|
429
474
|
return null;
|
|
430
475
|
}
|
|
431
476
|
}
|
|
@@ -439,27 +484,68 @@ export class EnhancedLogManager {
|
|
|
439
484
|
// Write raw log
|
|
440
485
|
this.writeToRawLog(data);
|
|
441
486
|
|
|
442
|
-
// Write to readable log
|
|
487
|
+
// Write to readable log - treat stderr same as stdout
|
|
488
|
+
// Git and many tools use stderr for non-error output
|
|
443
489
|
const lines = text.split('\n');
|
|
444
490
|
for (const line of lines) {
|
|
445
491
|
const cleanLine = stripAnsi(line).trim();
|
|
446
492
|
if (cleanLine && !this.isNoiseLog(cleanLine)) {
|
|
447
493
|
const hasTimestamp = /^\[(\d{4}-\d{2}-\d{2}T|\d{2}:\d{2}:\d{2})\]/.test(cleanLine);
|
|
448
494
|
const label = this.getLaneTaskLabel();
|
|
495
|
+
const ts = this.getShortTime();
|
|
449
496
|
|
|
497
|
+
// Determine if this is actually an error message
|
|
498
|
+
const isError = this.isErrorLine(cleanLine);
|
|
499
|
+
const prefix = isError ? '❌ ERR' : '';
|
|
500
|
+
|
|
501
|
+
let formattedLine: string;
|
|
450
502
|
if (hasTimestamp) {
|
|
451
|
-
|
|
503
|
+
formattedLine = cleanLine.includes(`[${label}]`)
|
|
452
504
|
? cleanLine
|
|
453
|
-
: cleanLine.replace(/^(\[[^\]]+\])/, `$1 [${label}]
|
|
454
|
-
this.writeToReadableLog(`${formatted}\n`);
|
|
505
|
+
: cleanLine.replace(/^(\[[^\]]+\])/, `$1 [${label}]${prefix ? ' ' + prefix : ''}`);
|
|
455
506
|
} else {
|
|
456
|
-
|
|
457
|
-
|
|
507
|
+
formattedLine = prefix
|
|
508
|
+
? `[${ts}] [${label}] ${prefix} ${cleanLine}`
|
|
509
|
+
: `[${ts}] [${label}] ${cleanLine}`;
|
|
510
|
+
}
|
|
511
|
+
|
|
512
|
+
this.writeToReadableLog(`${formattedLine}\n`);
|
|
513
|
+
|
|
514
|
+
// Output to console
|
|
515
|
+
if (this.onParsedMessage) {
|
|
516
|
+
const rawMsg: ParsedMessage = {
|
|
517
|
+
type: 'raw',
|
|
518
|
+
role: 'system',
|
|
519
|
+
content: formattedLine,
|
|
520
|
+
timestamp: Date.now(),
|
|
521
|
+
};
|
|
522
|
+
this.onParsedMessage(rawMsg);
|
|
458
523
|
}
|
|
459
524
|
}
|
|
460
525
|
}
|
|
461
526
|
}
|
|
462
527
|
|
|
528
|
+
/**
|
|
529
|
+
* Check if a line is actually an error message
|
|
530
|
+
*/
|
|
531
|
+
private isErrorLine(text: string): boolean {
|
|
532
|
+
const errorPatterns = [
|
|
533
|
+
/^error:/i,
|
|
534
|
+
/^fatal:/i,
|
|
535
|
+
/^panic:/i,
|
|
536
|
+
/\berror\b.*:/i,
|
|
537
|
+
/\bfailed\b/i,
|
|
538
|
+
/\bexception\b/i,
|
|
539
|
+
/^ENOENT:/i,
|
|
540
|
+
/^EACCES:/i,
|
|
541
|
+
/^EPERM:/i,
|
|
542
|
+
/^ERR!/i,
|
|
543
|
+
/npm ERR!/i,
|
|
544
|
+
];
|
|
545
|
+
|
|
546
|
+
return errorPatterns.some(p => p.test(text));
|
|
547
|
+
}
|
|
548
|
+
|
|
463
549
|
/**
|
|
464
550
|
* Write a custom log entry
|
|
465
551
|
*/
|
|
@@ -644,12 +730,12 @@ export function exportLogs(
|
|
|
644
730
|
format: 'text' | 'json' | 'markdown' | 'html',
|
|
645
731
|
outputPath?: string
|
|
646
732
|
): string {
|
|
647
|
-
const
|
|
733
|
+
const logPath = getLaneLogPath(laneRunDir, 'raw');
|
|
648
734
|
|
|
649
735
|
let output = '';
|
|
650
736
|
|
|
651
|
-
if (fs.existsSync(
|
|
652
|
-
output = fs.readFileSync(
|
|
737
|
+
if (fs.existsSync(logPath)) {
|
|
738
|
+
output = fs.readFileSync(logPath, 'utf8');
|
|
653
739
|
}
|
|
654
740
|
|
|
655
741
|
if (outputPath) {
|