Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
100 commits
Select commit Hold shift + click to select a range
eb94e4d
feat: enhance CodexUsageService to fetch usage data from app-server J…
Shironex Jan 9, 2026
fc20dd5
refactor: remove AI profile functionality and related components
webdevcody Jan 10, 2026
a3ecc6f
Merge pull request #394 from AutoMaker-Org/remove-profiles
webdevcody Jan 10, 2026
99b05d3
feat: update Codex services and UI components for enhanced model mana…
Shironex Jan 10, 2026
c5009a0
refactor: remove Codex credits handling from services and UI components
Shironex Jan 10, 2026
604f98b
chore: ignore .codex/config.toml to prevent API key exposure
Shironex Jan 10, 2026
c99883e
fix: address PR review comments
Shironex Jan 10, 2026
36ddf05
Merge pull request #400 from AutoMaker-Org/feat/codex-usage
Shironex Jan 10, 2026
543aa7a
chore: update @modelcontextprotocol/sdk in server dep
Shironex Jan 10, 2026
fe433a8
Merge pull request #402 from AutoMaker-Org/fix/security-vulnerability…
Shironex Jan 10, 2026
887343d
Merge branch 'main' into v0.10.0rc
webdevcody Jan 10, 2026
134208d
Merge branch 'v0.10.0rc' of github.com:AutoMaker-Org/automaker into v…
webdevcody Jan 10, 2026
a67b8c6
feat: implement dashboard view and enhance sidebar navigation
webdevcody Jan 10, 2026
dd88213
refactor: streamline feature addition in BoardView and KanbanBoard
webdevcody Jan 10, 2026
555523d
refactor: remove kanbanCardDetailLevel from settings and UI components
webdevcody Jan 10, 2026
e64a850
feat: enhance feature dialogs with planning mode tooltips
Shironex Jan 10, 2026
4040bef
feat: Add OpenCode provider integration with official brand icons
DhanushSantosh Jan 10, 2026
1dc843d
Merge upstream/v0.10.0rc into feature/codex-cli
DhanushSantosh Jan 10, 2026
51cd715
test: Update OpenCode provider tests to use new event format
DhanushSantosh Jan 10, 2026
7cc092c
test: Fix remaining OpenCode provider test failures
DhanushSantosh Jan 10, 2026
e34e4a5
fix: Resolve TypeScript error assigning part.result to string field
DhanushSantosh Jan 10, 2026
0c19beb
fix: Set OpenCode icon to official brand color (#6366F1 indigo)
DhanushSantosh Jan 10, 2026
fa8ae14
feat: enhance worktree listing by scanning external directories
webdevcody Jan 10, 2026
27c6065
Merge branch 'v0.10.0rc' of github.com:AutoMaker-Org/automaker into v…
webdevcody Jan 10, 2026
427832e
fix: Display correct provider icons for all OpenCode/Bedrock models
DhanushSantosh Jan 10, 2026
360cddc
Merge upstream commits including worktree enhancement
DhanushSantosh Jan 10, 2026
41144ff
Merge recovered upstream commits including worktree enhancement
DhanushSantosh Jan 10, 2026
05d96a7
feat: Implement worktree initialization script functionality
Shironex Jan 10, 2026
89a9606
fix: Improve E2E test workflow for better backend debugging
DhanushSantosh Jan 10, 2026
6c412cd
feat: Add run init script functionality for worktrees
Shironex Jan 10, 2026
c24e620
feat: Enhance ShellSyntaxEditor and WorktreesSection with new features
Shironex Jan 10, 2026
a92457b
fix: Handle Claude CLI unavailability gracefully in CI
DhanushSantosh Jan 10, 2026
aeb5bd8
feat: Add Init Script Indicator visibility feature for worktrees
Shironex Jan 10, 2026
e902e8e
feat: Introduce default delete branch option for worktrees
Shironex Jan 10, 2026
d98ff16
feat: Enhance CreateWorktreeDialog with user-friendly error handling
Shironex Jan 10, 2026
09527b3
feat: Add auto-dismiss functionality for Init Script Indicator
Shironex Jan 10, 2026
861fff1
fix: broken lock file
Shironex Jan 10, 2026
385e7f5
fix: address pr comments
Shironex Jan 10, 2026
8ed2fa0
security: Fix critical vulnerabilities in worktree init script feature
Shironex Jan 11, 2026
4a59e90
chore: format
Shironex Jan 11, 2026
da682e3
feat: add memory management feature with UI components
webdevcody Jan 11, 2026
cf3ed1d
Merge branch 'v0.10.0rc' of github.com:AutoMaker-Org/automaker into v…
webdevcody Jan 11, 2026
0db8808
Merge branch 'memory-ui' into v0.10.0rc
webdevcody Jan 11, 2026
7115460
feat: add resume interrupted features endpoint and handler
webdevcody Jan 11, 2026
5f3db1f
feat: enhance spec regeneration management by project
webdevcody Jan 11, 2026
2d4ffc7
feat: add accept all functionality in ideation view
Shironex Jan 11, 2026
7f79d96
feat: Add official icons for MiniMax, GLM (Z.ai), and BigPickle models
DhanushSantosh Jan 11, 2026
9c5fe44
feat: add bulk delete functionality for features
Shironex Jan 11, 2026
317c21f
Merge pull request #413 from AutoMaker-Org/feat/bulk-delete-features-…
Shironex Jan 11, 2026
7522e58
Merge remote-tracking branch 'upstream/v0.10.0rc' into feature/codex-cli
DhanushSantosh Jan 11, 2026
6e4b611
refactor: optimize bulk delete handler and UI feedback
Shironex Jan 11, 2026
e171b6a
feat: add empty state card component and integrate AI suggestion func…
Shironex Jan 11, 2026
f60c18d
Update apps/ui/src/components/views/board-view/constants.ts
Shironex Jan 11, 2026
8321c06
refactor: extract Enhance with AI into shared components
Shironex Jan 11, 2026
7e5d915
fix: address PR review feedback from Gemini Code Assist
Shironex Jan 11, 2026
41a6c7f
fix: address second round of PR review feedback
Shironex Jan 11, 2026
785a4d2
fix: restore auth and auto-open last project
DhanushSantosh Jan 11, 2026
32656a9
feat: add default IDE setting and multi-editor support with icons
stefandevo Jan 11, 2026
ac87594
fix: address code review feedback from PR #423
stefandevo Jan 11, 2026
33dd9ae
fix: address nitpick feedback from PR #423
stefandevo Jan 11, 2026
fb3a849
fix: address CodeRabbitAI security and UX review comments
stefandevo Jan 11, 2026
2a98de8
fix: improve cache management and editor fallback handling
stefandevo Jan 11, 2026
a4a111f
feat: add pre-enhancement description tracking for feature updates
Shironex Jan 11, 2026
a266d85
Merge pull request #421 from AutoMaker-Org/refactor/extract-enhance-w…
Shironex Jan 11, 2026
d724e78
fix(ui): restore startup project context
DhanushSantosh Jan 11, 2026
a046d12
Merge remote-tracking branch 'upstream/v0.10.0rc' into feature/codex-cli
DhanushSantosh Jan 11, 2026
8b0b565
Merge remote-tracking branch 'origin/v0.10.0rc' into stefandevo/main
Shironex Jan 11, 2026
6d267ce
feat(platform): add cross-platform editor utilities and refresh funct…
Shironex Jan 11, 2026
01cf81a
fix(platform): detect Antigravity CLI aliases
DhanushSantosh Jan 11, 2026
1b9acb1
fix(platform): verify full Xcode installation for xed command
Shironex Jan 11, 2026
b9b3695
feat(platform): add VS Code Insiders and Kiro editor support
Shironex Jan 11, 2026
cbca9b6
fix: correct Kiro CLI command typo (kido -> kiro)
Shironex Jan 11, 2026
80081b6
fix(platform): remove logger import to avoid circular dependency
Shironex Jan 11, 2026
43fc3de
Merge pull request #423 from stefandevo/main
Shironex Jan 11, 2026
a48c67d
refactor: update EmptyStateCard component for improved layout and fun…
Shironex Jan 11, 2026
6e13cdd
Merge branch: resolve conflict in worktree-actions-dropdown.tsx
Shironex Jan 11, 2026
53f5c2b
feat(backlog): add branchName support to apply handler and UI components
Shironex Jan 11, 2026
6638c35
refactor(sidebar): enhance sidebar responsiveness and improve layout
webdevcody Jan 11, 2026
6842e4c
refactor: simplify EmptyStateCard and update empty state configurations
Shironex Jan 11, 2026
a4a792c
Merge pull request #416 from AutoMaker-Org/feat/emtpy-columns-enhancm…
Shironex Jan 11, 2026
a0669d4
feat(board-view): enhance feature and plan dialogs with worktree bran…
Shironex Jan 11, 2026
f41a420
fix: address pr comments
Shironex Jan 12, 2026
ed65f70
Merge pull request #409 from AutoMaker-Org/feat/worktrees-init-script
Shironex Jan 12, 2026
6c5206d
feat: add dynamic model discovery and routing for OpenCode provider
stefandevo Jan 11, 2026
5e4b422
fix: improve OpenCode error handling and message extraction
stefandevo Jan 11, 2026
e38325c
fix: improve dynamic model icons and fix React reference
stefandevo Jan 11, 2026
70204a2
fix: address code review feedback from gemini-code-assist
stefandevo Jan 11, 2026
20cc401
fix: update enhancement test to include ux-reviewer mode
stefandevo Jan 11, 2026
edcc4e7
fix: address CodeRabbitAI review feedback
stefandevo Jan 11, 2026
b8531cf
fix: add OpenCode settings to migration for persistence
stefandevo Jan 11, 2026
9f936c6
fix(opencode): parse api-key provider models
DhanushSantosh Jan 12, 2026
b152f11
fix(ui): refresh OpenCode models on new providers
DhanushSantosh Jan 12, 2026
0cff4cf
feat(ui): add OpenRouter icon
DhanushSantosh Jan 12, 2026
6184440
fix(ui): tie dynamic models to connected providers
DhanushSantosh Jan 12, 2026
9ce3cfe
feat(opencode): drop bedrock defaults
DhanushSantosh Jan 12, 2026
8094941
feat(opencode): persist dynamic model selection
DhanushSantosh Jan 12, 2026
6020219
fix(opencode): address review feedback
DhanushSantosh Jan 12, 2026
cebf57f
Merge pull request #426 from stefandevo/opencode-dynamic-providers
DhanushSantosh Jan 12, 2026
f50520c
feat(delete): enhance branch deletion handling and validation
Shironex Jan 12, 2026
fbab1d3
test: align app-spec and enhancement mode tests
DhanushSantosh Jan 12, 2026
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
88 changes: 83 additions & 5 deletions .github/workflows/e2e-tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,14 @@ jobs:
git config --global user.email "ci@example.com"

- name: Start backend server
run: npm run start --workspace=apps/server &
run: |
echo "Starting backend server..."
# Start server in background and save PID
npm run start --workspace=apps/server > backend.log 2>&1 &
SERVER_PID=$!
echo "Server started with PID: $SERVER_PID"
echo "SERVER_PID=$SERVER_PID" >> $GITHUB_ENV

Comment on lines +40 to +47
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

PID capture may not correspond to the actual server process (npm wrapper vs node) — consider process-group management.

Line 43–46: $! likely tracks the npm process; killing that PID later may leave the real server running, causing flakes/port conflicts.

Proposed hardening (capture process group + quote env file)
       - name: Start backend server
         run: |
           echo "Starting backend server..."
-          # Start server in background and save PID
-          npm run start --workspace=apps/server > backend.log 2>&1 &
-          SERVER_PID=$!
+          # Start server in its own process group so cleanup can terminate children too.
+          setsid npm run start --workspace=apps/server > backend.log 2>&1 &
+          SERVER_PID=$! # PID == PGID for setsid-launched command
           echo "Server started with PID: $SERVER_PID"
-          echo "SERVER_PID=$SERVER_PID" >> $GITHUB_ENV
+          echo "SERVER_PID=$SERVER_PID" >> "$GITHUB_ENV"
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
run: |
echo "Starting backend server..."
# Start server in background and save PID
npm run start --workspace=apps/server > backend.log 2>&1 &
SERVER_PID=$!
echo "Server started with PID: $SERVER_PID"
echo "SERVER_PID=$SERVER_PID" >> $GITHUB_ENV
run: |
echo "Starting backend server..."
# Start server in its own process group so cleanup can terminate children too.
setsid npm run start --workspace=apps/server > backend.log 2>&1 &
SERVER_PID=$! # PID == PGID for setsid-launched command
echo "Server started with PID: $SERVER_PID"
echo "SERVER_PID=$SERVER_PID" >> "$GITHUB_ENV"
🤖 Prompt for AI Agents
In @.github/workflows/e2e-tests.yml around lines 40 - 47, The current capture of
SERVER_PID via $! after running "npm run start --workspace=apps/server" may
record the npm wrapper PID instead of the actual node server; change the startup
to launch the server in its own process group or capture its process group and
export that instead (e.g., use setsid/nohup or derive PGID from the recorded PID
and save/kill the group with a negative PID) so later shutdown targets the real
server and avoids stray node processes, and ensure the "SERVER_PID" / env write
to $GITHUB_ENV is quoted/escaped when appended to avoid parsing issues.

env:
PORT: 3008
NODE_ENV: test
Expand All @@ -53,21 +60,70 @@ jobs:
- name: Wait for backend server
run: |
echo "Waiting for backend server to be ready..."

# Check if server process is running
if [ -z "$SERVER_PID" ]; then
echo "ERROR: Server PID not found in environment"
cat backend.log 2>/dev/null || echo "No backend log found"
exit 1
fi

# Check if process is actually running
if ! kill -0 $SERVER_PID 2>/dev/null; then
echo "ERROR: Server process $SERVER_PID is not running!"
echo "=== Backend logs ==="
cat backend.log
echo ""
echo "=== Recent system logs ==="
dmesg 2>/dev/null | tail -20 || echo "No dmesg available"
exit 1
fi

# Wait for health endpoint
for i in {1..60}; do
if curl -s -f http://localhost:3008/api/health > /dev/null 2>&1; then
echo "Backend server is ready!"
curl -s http://localhost:3008/api/health | jq . 2>/dev/null || echo "Health check response: $(curl -s http://localhost:3008/api/health 2>/dev/null || echo 'No response')"
echo "=== Backend logs ==="
cat backend.log
echo ""
echo "Health check response:"
curl -s http://localhost:3008/api/health | jq . 2>/dev/null || echo "Health check: $(curl -s http://localhost:3008/api/health 2>/dev/null || echo 'No response')"
exit 0
fi

# Check if server process is still running
if ! kill -0 $SERVER_PID 2>/dev/null; then
echo "ERROR: Server process died during wait!"
echo "=== Backend logs ==="
cat backend.log
exit 1
fi

echo "Waiting... ($i/60)"
sleep 1
done
echo "Backend server failed to start!"
echo "Checking server status..."

echo "ERROR: Backend server failed to start within 60 seconds!"
echo "=== Backend logs ==="
cat backend.log
echo ""
echo "=== Process status ==="
ps aux | grep -E "(node|tsx)" | grep -v grep || echo "No node processes found"
echo ""
echo "=== Port status ==="
netstat -tlnp 2>/dev/null | grep :3008 || echo "Port 3008 not listening"
echo "Testing health endpoint..."
lsof -i :3008 2>/dev/null || echo "lsof not available or port not in use"
echo ""
echo "=== Health endpoint test ==="
curl -v http://localhost:3008/api/health 2>&1 || echo "Health endpoint failed"

# Kill the server process if it's still hanging
if kill -0 $SERVER_PID 2>/dev/null; then
echo ""
echo "Killing stuck server process..."
kill -9 $SERVER_PID 2>/dev/null || true
fi

exit 1

- name: Run E2E tests
Expand All @@ -81,6 +137,18 @@ jobs:
# Keep UI-side login/defaults consistent
AUTOMAKER_API_KEY: test-api-key-for-e2e-tests

- name: Print backend logs on failure
if: failure()
run: |
echo "=== E2E Tests Failed - Backend Logs ==="
cat backend.log 2>/dev/null || echo "No backend log found"
echo ""
echo "=== Process status at failure ==="
ps aux | grep -E "(node|tsx)" | grep -v grep || echo "No node processes found"
echo ""
echo "=== Port status ==="
netstat -tlnp 2>/dev/null | grep :3008 || echo "Port 3008 not listening"

- name: Upload Playwright report
uses: actions/upload-artifact@v4
if: always()
Expand All @@ -98,3 +166,13 @@ jobs:
apps/ui/test-results/
retention-days: 7
if-no-files-found: ignore

- name: Cleanup - Kill backend server
if: always()
run: |
if [ -n "$SERVER_PID" ]; then
echo "Cleaning up backend server (PID: $SERVER_PID)..."
kill $SERVER_PID 2>/dev/null || true
kill -9 $SERVER_PID 2>/dev/null || true
echo "Backend server cleanup complete"
fi
Comment on lines +170 to +178
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major

Cleanup should terminate the whole server tree (TERM → wait → KILL), not just the captured PID.

Line 173–177: kill $SERVER_PID may not stop the actual Node server if it’s a child; also skipping a grace period can drop in-flight writes.

Proposed cleanup (kill process group, graceful first)
       - name: Cleanup - Kill backend server
         if: always()
         run: |
           if [ -n "$SERVER_PID" ]; then
             echo "Cleaning up backend server (PID: $SERVER_PID)..."
-            kill $SERVER_PID 2>/dev/null || true
-            kill -9 $SERVER_PID 2>/dev/null || true
+            # Kill the whole process group (covers child node/tsx processes).
+            kill -TERM "-$SERVER_PID" 2>/dev/null || true
+            sleep 2
+            kill -KILL "-$SERVER_PID" 2>/dev/null || true
             echo "Backend server cleanup complete"
           fi
🤖 Prompt for AI Agents
In @.github/workflows/e2e-tests.yml around lines 170 - 178, The cleanup step
"Cleanup - Kill backend server" currently kills only the captured PID and
immediately uses SIGKILL; update it to terminate the whole process group and
perform a graceful shutdown: send SIGTERM to the process group using the
negative PID (use -$SERVER_PID), wait up to a short timeout polling for process
exit (e.g., loop checking if the PID/group is gone and sleeping), then if still
alive send SIGKILL to the process group (-$SERVER_PID); ensure you still guard
with the existing if [ -n "$SERVER_PID" ] check and keep logging around the
TERM→wait→KILL sequence.

13 changes: 12 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -73,6 +73,9 @@ blob-report/
!.env.example
!.env.local.example

# Codex config (contains API keys)
.codex/config.toml

# TypeScript
*.tsbuildinfo

Expand All @@ -84,4 +87,12 @@ docker-compose.override.yml
.claude/hans/

pnpm-lock.yaml
yarn.lock
yarn.lock

# Fork-specific workflow files (should never be committed)
DEVELOPMENT_WORKFLOW.md
check-sync.sh
# API key files
data/.api-key
data/credentials.json
data/
35 changes: 32 additions & 3 deletions apps/server/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -55,6 +55,8 @@ import { createClaudeRoutes } from './routes/claude/index.js';
import { ClaudeUsageService } from './services/claude-usage-service.js';
import { createCodexRoutes } from './routes/codex/index.js';
import { CodexUsageService } from './services/codex-usage-service.js';
import { CodexAppServerService } from './services/codex-app-server-service.js';
import { CodexModelCacheService } from './services/codex-model-cache-service.js';
import { createGitHubRoutes } from './routes/github/index.js';
import { createContextRoutes } from './routes/context/index.js';
import { createBacklogPlanRoutes } from './routes/backlog-plan/index.js';
Expand Down Expand Up @@ -168,14 +170,21 @@ const agentService = new AgentService(DATA_DIR, events, settingsService);
const featureLoader = new FeatureLoader();
const autoModeService = new AutoModeService(events, settingsService);
const claudeUsageService = new ClaudeUsageService();
const codexUsageService = new CodexUsageService();
const codexAppServerService = new CodexAppServerService();
const codexModelCacheService = new CodexModelCacheService(DATA_DIR, codexAppServerService);
const codexUsageService = new CodexUsageService(codexAppServerService);
const mcpTestService = new MCPTestService(settingsService);
const ideationService = new IdeationService(events, settingsService, featureLoader);

// Initialize services
(async () => {
await agentService.initialize();
logger.info('Agent service initialized');

// Bootstrap Codex model cache in background (don't block server startup)
void codexModelCacheService.getModels().catch((err) => {
logger.error('Failed to bootstrap Codex model cache:', err);
});
})();

// Run stale validation cleanup every hour to prevent memory leaks from crashed validations
Expand Down Expand Up @@ -208,7 +217,7 @@ app.use('/api/sessions', createSessionsRoutes(agentService));
app.use('/api/features', createFeaturesRoutes(featureLoader));
app.use('/api/auto-mode', createAutoModeRoutes(autoModeService));
app.use('/api/enhance-prompt', createEnhancePromptRoutes(settingsService));
app.use('/api/worktree', createWorktreeRoutes());
app.use('/api/worktree', createWorktreeRoutes(events));
app.use('/api/git', createGitRoutes());
app.use('/api/suggestions', createSuggestionsRoutes(events, settingsService));
app.use('/api/models', createModelsRoutes());
Expand All @@ -219,7 +228,7 @@ app.use('/api/templates', createTemplatesRoutes());
app.use('/api/terminal', createTerminalRoutes());
app.use('/api/settings', createSettingsRoutes(settingsService));
app.use('/api/claude', createClaudeRoutes(claudeUsageService));
app.use('/api/codex', createCodexRoutes(codexUsageService));
app.use('/api/codex', createCodexRoutes(codexUsageService, codexModelCacheService));
app.use('/api/github', createGitHubRoutes(events, settingsService));
app.use('/api/context', createContextRoutes(settingsService));
app.use('/api/backlog-plan', createBacklogPlanRoutes(events, settingsService));
Expand Down Expand Up @@ -588,6 +597,26 @@ const startServer = (port: number) => {

startServer(PORT);

// Global error handlers to prevent crashes from uncaught errors
process.on('unhandledRejection', (reason: unknown, _promise: Promise<unknown>) => {
logger.error('Unhandled Promise Rejection:', {
reason: reason instanceof Error ? reason.message : String(reason),
stack: reason instanceof Error ? reason.stack : undefined,
});
// Don't exit - log the error and continue running
// This prevents the server from crashing due to unhandled rejections
});

process.on('uncaughtException', (error: Error) => {
logger.error('Uncaught Exception:', {
message: error.message,
stack: error.stack,
});
// Exit on uncaught exceptions to prevent undefined behavior
// The process is in an unknown state after an uncaught exception
process.exit(1);
});

// Graceful shutdown
process.on('SIGTERM', () => {
logger.info('SIGTERM received, shutting down...');
Expand Down
50 changes: 10 additions & 40 deletions apps/server/src/lib/codex-auth.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,11 @@
* Never assumes authenticated - only returns true if CLI confirms.
*/

import { spawnProcess, getCodexAuthPath } from '@automaker/platform';
import { spawnProcess } from '@automaker/platform';
import { findCodexCliPath } from '@automaker/platform';
import * as fs from 'fs';
import { createLogger } from '@automaker/utils';

const logger = createLogger('CodexAuth');

const CODEX_COMMAND = 'codex';
const OPENAI_API_KEY_ENV = 'OPENAI_API_KEY';
Expand All @@ -26,36 +28,16 @@ export interface CodexAuthCheckResult {
export async function checkCodexAuthentication(
cliPath?: string | null
): Promise<CodexAuthCheckResult> {
console.log('[CodexAuth] checkCodexAuthentication called with cliPath:', cliPath);

const resolvedCliPath = cliPath || (await findCodexCliPath());
const hasApiKey = !!process.env[OPENAI_API_KEY_ENV];

console.log('[CodexAuth] resolvedCliPath:', resolvedCliPath);
console.log('[CodexAuth] hasApiKey:', hasApiKey);

// Debug: Check auth file
const authFilePath = getCodexAuthPath();
console.log('[CodexAuth] Auth file path:', authFilePath);
try {
const authFileExists = fs.existsSync(authFilePath);
console.log('[CodexAuth] Auth file exists:', authFileExists);
if (authFileExists) {
const authContent = fs.readFileSync(authFilePath, 'utf-8');
console.log('[CodexAuth] Auth file content:', authContent.substring(0, 500)); // First 500 chars
}
} catch (error) {
console.log('[CodexAuth] Error reading auth file:', error);
}

// If CLI is not installed, cannot be authenticated
if (!resolvedCliPath) {
console.log('[CodexAuth] No CLI path found, returning not authenticated');
logger.info('CLI not found');
return { authenticated: false, method: 'none' };
}

try {
console.log('[CodexAuth] Running: ' + resolvedCliPath + ' login status');
const result = await spawnProcess({
command: resolvedCliPath || CODEX_COMMAND,
args: ['login', 'status'],
Expand All @@ -66,33 +48,21 @@ export async function checkCodexAuthentication(
},
});

console.log('[CodexAuth] Command result:');
console.log('[CodexAuth] exitCode:', result.exitCode);
console.log('[CodexAuth] stdout:', JSON.stringify(result.stdout));
console.log('[CodexAuth] stderr:', JSON.stringify(result.stderr));

// Check both stdout and stderr for "logged in" - Codex CLI outputs to stderr
const combinedOutput = (result.stdout + result.stderr).toLowerCase();
const isLoggedIn = combinedOutput.includes('logged in');
console.log('[CodexAuth] isLoggedIn (contains "logged in" in stdout or stderr):', isLoggedIn);

if (result.exitCode === 0 && isLoggedIn) {
// Determine auth method based on what we know
const method = hasApiKey ? 'api_key_env' : 'cli_authenticated';
console.log('[CodexAuth] Authenticated! method:', method);
logger.info(`✓ Authenticated (${method})`);
return { authenticated: true, method };
}

console.log(
'[CodexAuth] Not authenticated. exitCode:',
result.exitCode,
'isLoggedIn:',
isLoggedIn
);
logger.info('Not authenticated');
return { authenticated: false, method: 'none' };
} catch (error) {
console.log('[CodexAuth] Error running command:', error);
logger.error('Failed to check authentication:', error);
return { authenticated: false, method: 'none' };
}

console.log('[CodexAuth] Returning not authenticated');
return { authenticated: false, method: 'none' };
}
6 changes: 6 additions & 0 deletions apps/server/src/lib/worktree-metadata.ts
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,12 @@ export interface WorktreeMetadata {
branch: string;
createdAt: string;
pr?: WorktreePRInfo;
/** Whether the init script has been executed for this worktree */
initScriptRan?: boolean;
/** Status of the init script execution */
initScriptStatus?: 'running' | 'success' | 'failed';
/** Error message if init script failed */
initScriptError?: string;
}

/**
Expand Down
Loading
Loading