detectAndLoadWorkspaceWithRootfs is the unified core of workspace detection and module gathering. It detects the current workspace root, applies legacy dagger.json compat, and gathers all modules to be loaded later by ensureModulesLoaded. It works for both local and remote workspaces, parameterized
( ctx context.Context, client *daggerClient, statFS core.StatFS, readFile func(context.Context, string) ([]byte, error), cwd string, resolveLocalRef func(ws *workspace.Workspace, relPath string) string, workspaceAddress func(ws *workspace.Workspace) string, isLocal bool, prebuiltRootfs dagql.ObjectResult[*core.Directory], )
| 441 | // abstraction (statFS/readFile) and reference resolution (resolveLocalRef). |
| 442 | // For remote workspaces, prebuiltRootfs provides the already-cloned git tree. |
| 443 | func (srv *Server) detectAndLoadWorkspaceWithRootfs( |
| 444 | ctx context.Context, |
| 445 | client *daggerClient, |
| 446 | statFS core.StatFS, |
| 447 | readFile func(context.Context, string) ([]byte, error), |
| 448 | cwd string, |
| 449 | resolveLocalRef func(ws *workspace.Workspace, relPath string) string, |
| 450 | workspaceAddress func(ws *workspace.Workspace) string, |
| 451 | isLocal bool, |
| 452 | prebuiltRootfs dagql.ObjectResult[*core.Directory], |
| 453 | ) error { |
| 454 | clientMD := client.clientMetadata |
| 455 | loadModules := client.pendingWorkspaceLoad && clientMD != nil && clientMD.LoadWorkspaceModules |
| 456 | |
| 457 | // --- Detect workspace (pure — no dagger.json knowledge) --- |
| 458 | ws, err := workspace.Detect(ctx, func(ctx context.Context, path string) (string, bool, error) { |
| 459 | return core.StatFSExists(ctx, statFS, path) |
| 460 | }, readFile, cwd) |
| 461 | if err != nil { |
| 462 | return err |
| 463 | } |
| 464 | |
| 465 | // --- Compat mode: extract toolchains/blueprints from legacy dagger.json --- |
| 466 | // In the foundation split, initialized workspace config is deferred, so a |
| 467 | // nearby dagger.json is the only source of workspace-level enrichment. |
| 468 | var legacyToolchains []workspace.LegacyToolchain |
| 469 | var legacyBlueprint *workspace.LegacyBlueprint |
| 470 | moduleDir, hasModuleConfig, _ := core.Host{}.FindUp(ctx, statFS, cwd, workspace.ModuleConfigFileName) |
| 471 | legacyCallerDir := legacyCallerModuleDir(isLocal, moduleDir) |
| 472 | if hasModuleConfig { |
| 473 | cfgPath := filepath.Join(moduleDir, workspace.ModuleConfigFileName) |
| 474 | if data, readErr := readFile(ctx, cfgPath); readErr == nil { |
| 475 | legacyToolchains, _ = workspace.ParseLegacyToolchains(data) |
| 476 | legacyBlueprint, _ = workspace.ParseLegacyBlueprint(data) |
| 477 | } |
| 478 | if len(legacyToolchains) > 0 || legacyBlueprint != nil { |
| 479 | slog.Warn("Inferring workspace behavior from legacy module config.", |
| 480 | "config", cfgPath) |
| 481 | } |
| 482 | } else { |
| 483 | wsDir := filepath.Join(ws.Root, ws.Path) |
| 484 | slog.Info("No workspace modules detected.", "path", wsDir) |
| 485 | } |
| 486 | |
| 487 | // Build + cache core.Workspace. |
| 488 | address := "" |
| 489 | if workspaceAddress != nil { |
| 490 | address = workspaceAddress(ws) |
| 491 | } |
| 492 | coreWS, err := srv.buildCoreWorkspace(ctx, client, ws, isLocal, prebuiltRootfs, address) |
| 493 | if err != nil { |
| 494 | return fmt.Errorf("building workspace: %w", err) |
| 495 | } |
| 496 | client.workspace = coreWS |
| 497 | |
| 498 | if !loadModules { |
| 499 | return nil |
| 500 | } |
no test coverage detected