refactor: Restructure monorepo to apps/server/ and apps/web/ layout
Move src/ → apps/server/ and packages/web/ → apps/web/ to adopt standard monorepo conventions (apps/ for runnable apps, packages/ for reusable libraries). Update all config files, shared package imports, test fixtures, and documentation to reflect new paths. Key fixes: - Update workspace config to ["apps/*", "packages/*"] - Update tsconfig.json rootDir/include for apps/server/ - Add apps/web/** to vitest exclude list - Update drizzle.config.ts schema path - Fix ensure-schema.ts migration path detection (3 levels up in dev, 2 levels up in dist) - Fix tests/integration/cli-server.test.ts import paths - Update packages/shared imports to apps/server/ paths - Update all docs/ files with new paths
This commit is contained in:
266
apps/server/container.ts
Normal file
266
apps/server/container.ts
Normal file
@@ -0,0 +1,266 @@
|
||||
/**
|
||||
* Dependency Container
|
||||
*
|
||||
* Factory functions for creating the full dependency graph.
|
||||
* Keeps startServer() thin and makes repo wiring reusable by the test harness.
|
||||
*/
|
||||
|
||||
import type { DrizzleDatabase } from './db/index.js';
|
||||
import {
|
||||
createDatabase,
|
||||
ensureSchema,
|
||||
DrizzleInitiativeRepository,
|
||||
DrizzlePhaseRepository,
|
||||
DrizzleTaskRepository,
|
||||
DrizzleMessageRepository,
|
||||
DrizzleAgentRepository,
|
||||
DrizzlePageRepository,
|
||||
DrizzleProjectRepository,
|
||||
DrizzleAccountRepository,
|
||||
DrizzleChangeSetRepository,
|
||||
DrizzleLogChunkRepository,
|
||||
DrizzleConversationRepository,
|
||||
} from './db/index.js';
|
||||
import type { InitiativeRepository } from './db/repositories/initiative-repository.js';
|
||||
import type { PhaseRepository } from './db/repositories/phase-repository.js';
|
||||
import type { TaskRepository } from './db/repositories/task-repository.js';
|
||||
import type { MessageRepository } from './db/repositories/message-repository.js';
|
||||
import type { AgentRepository } from './db/repositories/agent-repository.js';
|
||||
import type { PageRepository } from './db/repositories/page-repository.js';
|
||||
import type { ProjectRepository } from './db/repositories/project-repository.js';
|
||||
import type { AccountRepository } from './db/repositories/account-repository.js';
|
||||
import type { ChangeSetRepository } from './db/repositories/change-set-repository.js';
|
||||
import type { LogChunkRepository } from './db/repositories/log-chunk-repository.js';
|
||||
import type { ConversationRepository } from './db/repositories/conversation-repository.js';
|
||||
import type { EventBus } from './events/index.js';
|
||||
import { createEventBus } from './events/index.js';
|
||||
import { ProcessManager, ProcessRegistry } from './process/index.js';
|
||||
import { LogManager } from './logging/index.js';
|
||||
import { MultiProviderAgentManager } from './agent/index.js';
|
||||
import { DefaultAccountCredentialManager } from './agent/credentials/index.js';
|
||||
import type { AccountCredentialManager } from './agent/credentials/types.js';
|
||||
import { DefaultDispatchManager } from './dispatch/manager.js';
|
||||
import { DefaultPhaseDispatchManager } from './dispatch/phase-manager.js';
|
||||
import type { DispatchManager, PhaseDispatchManager } from './dispatch/types.js';
|
||||
import { SimpleGitBranchManager } from './git/simple-git-branch-manager.js';
|
||||
import type { BranchManager } from './git/branch-manager.js';
|
||||
import { ExecutionOrchestrator } from './execution/orchestrator.js';
|
||||
import { DefaultConflictResolutionService } from './coordination/conflict-resolution-service.js';
|
||||
import { PreviewManager } from './preview/index.js';
|
||||
import { findWorkspaceRoot } from './config/index.js';
|
||||
import { createModuleLogger } from './logger/index.js';
|
||||
import type { ServerContextDeps } from './server/index.js';
|
||||
|
||||
// =============================================================================
|
||||
// Repositories
|
||||
// =============================================================================
|
||||
|
||||
/**
|
||||
* All 11 repository ports.
|
||||
*/
|
||||
export interface Repositories {
|
||||
initiativeRepository: InitiativeRepository;
|
||||
phaseRepository: PhaseRepository;
|
||||
taskRepository: TaskRepository;
|
||||
messageRepository: MessageRepository;
|
||||
agentRepository: AgentRepository;
|
||||
pageRepository: PageRepository;
|
||||
projectRepository: ProjectRepository;
|
||||
accountRepository: AccountRepository;
|
||||
changeSetRepository: ChangeSetRepository;
|
||||
logChunkRepository: LogChunkRepository;
|
||||
conversationRepository: ConversationRepository;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create all 11 Drizzle repository adapters from a database instance.
|
||||
* Reusable by both the production server and the test harness.
|
||||
*/
|
||||
export function createRepositories(db: DrizzleDatabase): Repositories {
|
||||
return {
|
||||
initiativeRepository: new DrizzleInitiativeRepository(db),
|
||||
phaseRepository: new DrizzlePhaseRepository(db),
|
||||
taskRepository: new DrizzleTaskRepository(db),
|
||||
messageRepository: new DrizzleMessageRepository(db),
|
||||
agentRepository: new DrizzleAgentRepository(db),
|
||||
pageRepository: new DrizzlePageRepository(db),
|
||||
projectRepository: new DrizzleProjectRepository(db),
|
||||
accountRepository: new DrizzleAccountRepository(db),
|
||||
changeSetRepository: new DrizzleChangeSetRepository(db),
|
||||
logChunkRepository: new DrizzleLogChunkRepository(db),
|
||||
conversationRepository: new DrizzleConversationRepository(db),
|
||||
};
|
||||
}
|
||||
|
||||
// =============================================================================
|
||||
// Container
|
||||
// =============================================================================
|
||||
|
||||
/**
|
||||
* Full dependency graph for the coordination server.
|
||||
*/
|
||||
export interface Container extends Repositories {
|
||||
db: DrizzleDatabase;
|
||||
eventBus: EventBus;
|
||||
processManager: ProcessManager;
|
||||
logManager: LogManager;
|
||||
workspaceRoot: string;
|
||||
credentialManager: AccountCredentialManager;
|
||||
agentManager: MultiProviderAgentManager;
|
||||
dispatchManager: DispatchManager;
|
||||
phaseDispatchManager: PhaseDispatchManager;
|
||||
branchManager: BranchManager;
|
||||
executionOrchestrator: ExecutionOrchestrator;
|
||||
previewManager: PreviewManager;
|
||||
|
||||
/** Extract the subset of deps that CoordinationServer needs. */
|
||||
toContextDeps(): ServerContextDeps;
|
||||
}
|
||||
|
||||
/**
|
||||
* Options for container creation.
|
||||
*/
|
||||
export interface ContainerOptions {
|
||||
debug?: boolean;
|
||||
}
|
||||
|
||||
/**
|
||||
* Create the full dependency container.
|
||||
*
|
||||
* Wires: ProcessRegistry → EventBus → ProcessManager → LogManager →
|
||||
* Database → Repositories → CredentialManager → AgentManager.
|
||||
* Runs ensureSchema() and reconcileAfterRestart() before returning.
|
||||
*/
|
||||
export async function createContainer(options?: ContainerOptions): Promise<Container> {
|
||||
const log = createModuleLogger('container');
|
||||
|
||||
// Infrastructure
|
||||
const registry = new ProcessRegistry();
|
||||
const eventBus = createEventBus();
|
||||
const processManager = new ProcessManager(registry, eventBus);
|
||||
const logManager = new LogManager();
|
||||
|
||||
// Database
|
||||
const db = createDatabase();
|
||||
ensureSchema(db);
|
||||
log.info('database initialized');
|
||||
|
||||
// Repositories
|
||||
const repos = createRepositories(db);
|
||||
log.info('repositories created');
|
||||
|
||||
// Workspace root
|
||||
const workspaceRoot = findWorkspaceRoot(process.cwd()) ?? process.cwd();
|
||||
log.info({ workspaceRoot }, 'workspace root resolved');
|
||||
|
||||
// Credential manager
|
||||
const credentialManager = new DefaultAccountCredentialManager(eventBus);
|
||||
log.info('credential manager created');
|
||||
|
||||
// Agent manager
|
||||
const agentManager = new MultiProviderAgentManager(
|
||||
repos.agentRepository,
|
||||
workspaceRoot,
|
||||
repos.projectRepository,
|
||||
repos.accountRepository,
|
||||
eventBus,
|
||||
credentialManager,
|
||||
repos.changeSetRepository,
|
||||
repos.phaseRepository,
|
||||
repos.taskRepository,
|
||||
repos.pageRepository,
|
||||
repos.logChunkRepository,
|
||||
options?.debug ?? false,
|
||||
);
|
||||
log.info('agent manager created');
|
||||
|
||||
// Reconcile agent state from any previous server session
|
||||
await agentManager.reconcileAfterRestart();
|
||||
log.info('agent reconciliation complete');
|
||||
|
||||
// Branch manager
|
||||
const branchManager = new SimpleGitBranchManager();
|
||||
log.info('branch manager created');
|
||||
|
||||
// Dispatch managers
|
||||
const dispatchManager = new DefaultDispatchManager(
|
||||
repos.taskRepository,
|
||||
repos.messageRepository,
|
||||
agentManager,
|
||||
eventBus,
|
||||
repos.initiativeRepository,
|
||||
repos.phaseRepository,
|
||||
);
|
||||
const phaseDispatchManager = new DefaultPhaseDispatchManager(
|
||||
repos.phaseRepository,
|
||||
repos.taskRepository,
|
||||
dispatchManager,
|
||||
eventBus,
|
||||
repos.initiativeRepository,
|
||||
repos.projectRepository,
|
||||
branchManager,
|
||||
workspaceRoot,
|
||||
);
|
||||
log.info('dispatch managers created');
|
||||
|
||||
// Conflict resolution service (for orchestrator)
|
||||
const conflictResolutionService = new DefaultConflictResolutionService(
|
||||
repos.taskRepository,
|
||||
repos.agentRepository,
|
||||
repos.messageRepository,
|
||||
eventBus,
|
||||
);
|
||||
|
||||
// Execution orchestrator
|
||||
const executionOrchestrator = new ExecutionOrchestrator(
|
||||
branchManager,
|
||||
repos.phaseRepository,
|
||||
repos.taskRepository,
|
||||
repos.initiativeRepository,
|
||||
repos.projectRepository,
|
||||
phaseDispatchManager,
|
||||
conflictResolutionService,
|
||||
eventBus,
|
||||
workspaceRoot,
|
||||
);
|
||||
executionOrchestrator.start();
|
||||
log.info('execution orchestrator started');
|
||||
|
||||
// Preview manager
|
||||
const previewManager = new PreviewManager(
|
||||
repos.projectRepository,
|
||||
eventBus,
|
||||
workspaceRoot,
|
||||
);
|
||||
log.info('preview manager created');
|
||||
|
||||
return {
|
||||
db,
|
||||
eventBus,
|
||||
processManager,
|
||||
logManager,
|
||||
workspaceRoot,
|
||||
credentialManager,
|
||||
agentManager,
|
||||
dispatchManager,
|
||||
phaseDispatchManager,
|
||||
branchManager,
|
||||
executionOrchestrator,
|
||||
previewManager,
|
||||
...repos,
|
||||
|
||||
toContextDeps(): ServerContextDeps {
|
||||
return {
|
||||
agentManager,
|
||||
credentialManager,
|
||||
dispatchManager,
|
||||
phaseDispatchManager,
|
||||
branchManager,
|
||||
executionOrchestrator,
|
||||
previewManager,
|
||||
workspaceRoot,
|
||||
...repos,
|
||||
};
|
||||
},
|
||||
};
|
||||
}
|
||||
Reference in New Issue
Block a user