Removed legacy interfaces and old documentation references to the previous on-disk layout

This commit is contained in:
2026-05-18 03:02:22 +00:00
parent 1054b64d9f
commit 2356688cb9
20 changed files with 150 additions and 759 deletions

View File

@@ -30,18 +30,13 @@ func NewLocalStore(workspaceRoot string) *LocalStore {
return &LocalStore{WorkspaceRoot: workspaceRoot}
}
// SessionPaths resolves legacy paths for a session workdir.
func (s *LocalStore) SessionPaths(sessionID string) SessionPaths {
return buildLegacySessionPaths(s.WorkspaceRoot, sessionID)
}
// SessionPathsFor resolves canonical campaign-aware paths for a session workdir.
func (s *LocalStore) SessionPathsFor(campaign, sessionID string) SessionPaths {
return buildSessionPaths(s.WorkspaceRoot, campaign, sessionID)
}
// ResolveSessionPathsFor resolves the active session path with legacy compatibility.
func (s *LocalStore) ResolveSessionPathsFor(campaign, sessionID string) (SessionPaths, error) {
// EnsureLayoutFor creates and verifies campaign-aware session layout.
func (s *LocalStore) EnsureLayoutFor(campaign, sessionID string) (SessionPaths, error) {
if strings.TrimSpace(s.WorkspaceRoot) == "" {
return SessionPaths{}, fmt.Errorf("workspace root is required")
}
@@ -51,50 +46,10 @@ func (s *LocalStore) ResolveSessionPathsFor(campaign, sessionID string) (Session
campaign = strings.TrimSpace(campaign)
if campaign == "" {
return s.SessionPaths(sessionID), nil
return SessionPaths{}, fmt.Errorf("campaign is required")
}
canonical := s.SessionPathsFor(campaign, sessionID)
legacy := s.SessionPaths(sessionID)
canonicalExists, err := dirExists(canonical.Root)
if err != nil {
return SessionPaths{}, fmt.Errorf("check canonical session root %q: %w", canonical.Root, err)
}
legacyExists, err := dirExists(legacy.Root)
if err != nil {
return SessionPaths{}, fmt.Errorf("check legacy session root %q: %w", legacy.Root, err)
}
switch {
case canonicalExists && legacyExists:
return SessionPaths{}, fmt.Errorf(
"ambiguous session workspace roots for campaign %q session %q: canonical=%q legacy=%q",
campaign,
sessionID,
canonical.Root,
legacy.Root,
)
case canonicalExists:
return canonical, nil
case legacyExists:
return legacy, nil
default:
return canonical, nil
}
}
// EnsureLayout creates and verifies the canonical session workdir directory layout.
func (s *LocalStore) EnsureLayout(sessionID string) (SessionPaths, error) {
return s.ensureLayout(s.SessionPaths(sessionID))
}
// EnsureLayoutFor creates and verifies campaign-aware session layout, with controlled legacy compatibility.
func (s *LocalStore) EnsureLayoutFor(campaign, sessionID string) (SessionPaths, error) {
paths, err := s.ResolveSessionPathsFor(campaign, sessionID)
if err != nil {
return SessionPaths{}, err
}
return s.ensureLayout(paths)
return s.ensureLayout(s.SessionPathsFor(campaign, sessionID))
}
func (s *LocalStore) ensureLayout(paths SessionPaths) (SessionPaths, error) {
@@ -129,15 +84,6 @@ func (s *LocalStore) ensureLayout(paths SessionPaths) (SessionPaths, error) {
return paths, nil
}
// CopyInput copies an input file into the session workdir under destRelativePath.
func (s *LocalStore) CopyInput(sessionID, srcPath, destRelativePath string) (Ref, error) {
paths, err := s.EnsureLayout(sessionID)
if err != nil {
return Ref{}, err
}
return s.copyInputWithPaths(paths, sessionID, srcPath, destRelativePath)
}
// CopyInputFor copies an input file into the campaign-aware session workdir under destRelativePath.
func (s *LocalStore) CopyInputFor(campaign, sessionID, srcPath, destRelativePath string) (Ref, error) {
paths, err := s.EnsureLayoutFor(campaign, sessionID)
@@ -248,15 +194,6 @@ func (s *LocalStore) Checksum(path string) (string, error) {
return digest, nil
}
// AcquireSessionLock acquires an exclusive lock file for a session workdir.
func (s *LocalStore) AcquireSessionLock(sessionID string) (*LockHandle, error) {
paths, err := s.EnsureLayout(sessionID)
if err != nil {
return nil, err
}
return s.acquireSessionLockForPaths(paths)
}
// AcquireSessionLockFor acquires an exclusive lock file for a campaign/session workdir.
func (s *LocalStore) AcquireSessionLockFor(campaign, sessionID string) (*LockHandle, error) {
paths, err := s.EnsureLayoutFor(campaign, sessionID)
@@ -290,17 +227,6 @@ func (s *LocalStore) acquireSessionLockForPaths(paths SessionPaths) (*LockHandle
return &LockHandle{path: paths.LockPath, file: f}, nil
}
func dirExists(path string) (bool, error) {
info, err := os.Stat(path)
if err == nil {
return info.IsDir(), nil
}
if errors.Is(err, os.ErrNotExist) {
return false, nil
}
return false, err
}
// ReleaseSessionLock releases a previously acquired session lock.
func (s *LocalStore) ReleaseSessionLock(lock *LockHandle) error {
if lock == nil {

View File

@@ -36,40 +36,14 @@ func TestEnsureLayoutCreatesExpectedDirectories(t *testing.T) {
}
}
func TestResolveSessionPathsForLegacyFallback(t *testing.T) {
root := t.TempDir()
store := NewLocalStore(root)
legacyRoot := SessionWorkDir(root, "session-1")
if err := os.MkdirAll(legacyRoot, 0o755); err != nil {
t.Fatalf("MkdirAll() error = %v", err)
}
paths, err := store.ResolveSessionPathsFor("sample-campaign", "session-1")
if err != nil {
t.Fatalf("ResolveSessionPathsFor() error = %v", err)
}
if paths.Root != legacyRoot {
t.Fatalf("paths.Root = %q, want legacy root %q", paths.Root, legacyRoot)
}
}
func TestResolveSessionPathsForAmbiguousRoots(t *testing.T) {
root := t.TempDir()
store := NewLocalStore(root)
legacyRoot := SessionWorkDir(root, "session-1")
canonicalRoot := SessionWorkDirForCampaign(root, "sample-campaign", "session-1")
for _, dir := range []string{legacyRoot, canonicalRoot} {
if err := os.MkdirAll(dir, 0o755); err != nil {
t.Fatalf("MkdirAll(%q) error = %v", dir, err)
}
}
_, err := store.ResolveSessionPathsFor("sample-campaign", "session-1")
func TestEnsureLayoutForRequiresCampaign(t *testing.T) {
store := NewLocalStore(t.TempDir())
_, err := store.EnsureLayoutFor("", "session-1")
if err == nil {
t.Fatal("expected ambiguity error, got nil")
t.Fatal("expected campaign-required error, got nil")
}
if !strings.Contains(err.Error(), "ambiguous session workspace roots") {
t.Fatalf("error = %v, want ambiguity message", err)
if !strings.Contains(err.Error(), "campaign is required") {
t.Fatalf("error = %v, want campaign-required error", err)
}
}

View File

@@ -27,11 +27,6 @@ type SessionPaths struct {
LockPath string
}
// SessionWorkDir returns the legacy work directory for one session.
func SessionWorkDir(rootDir, sessionID string) string {
return filepath.Join(rootDir, config.PathWorkDirSegment, sessionID)
}
// SessionWorkDirForCampaign returns the canonical campaign-aware work directory for one session.
func SessionWorkDirForCampaign(rootDir, campaign, sessionID string) string {
return filepath.Join(rootDir, config.PathWorkDirSegment, campaign, sessionID)
@@ -62,21 +57,11 @@ func SessionRunStageDirForCampaign(rootDir, campaign, sessionID, runID, stageNam
return filepath.Join(SessionRunRootForCampaign(rootDir, campaign, sessionID, runID), stageName)
}
// SessionRunWorkDir returns the legacy campaign/session/run scoped local work directory.
func SessionRunWorkDir(rootDir, campaign, sessionID, runID string) string {
return filepath.Join(rootDir, config.PathWorkDirSegment, campaign, sessionID, runID)
}
// SessionSpoolAudioDir returns the campaign/session/run scoped local spool audio path.
func SessionSpoolAudioDir(spoolRoot, campaign, sessionID, runID string) string {
return filepath.Join(spoolRoot, campaign, sessionID, runID, config.PathAudioDirSegment)
}
func buildLegacySessionPaths(workspaceRoot, sessionID string) SessionPaths {
root := SessionWorkDir(workspaceRoot, sessionID)
return buildSessionPathsFromRoot(workspaceRoot, "", sessionID, root)
}
func buildSessionPaths(workspaceRoot, campaign, sessionID string) SessionPaths {
root := SessionWorkDirForCampaign(workspaceRoot, campaign, sessionID)
return buildSessionPathsFromRoot(workspaceRoot, campaign, sessionID, root)

View File

@@ -5,15 +5,6 @@ import (
"testing"
)
func TestSessionRunWorkDir(t *testing.T) {
root := "/tmp/workspace"
got := SessionRunWorkDir(root, "forsaken", "2026-04-19", "20260515T031522Z-a1b2c3d4")
want := filepath.Join(root, "work", "forsaken", "2026-04-19", "20260515T031522Z-a1b2c3d4")
if got != want {
t.Fatalf("SessionRunWorkDir() = %q, want %q", got, want)
}
}
func TestSessionWorkDirForCampaign(t *testing.T) {
root := "/tmp/workspace"
got := SessionWorkDirForCampaign(root, "forsaken", "2026-04-19")

View File

@@ -11,36 +11,16 @@ type S3Store struct {
Prefix string
}
// SessionPaths is not implemented for S3-backed storage.
func (s *S3Store) SessionPaths(_ string) SessionPaths {
return SessionPaths{}
}
// SessionPathsFor is not implemented for S3-backed storage.
func (s *S3Store) SessionPathsFor(_, _ string) SessionPaths {
return SessionPaths{}
}
// ResolveSessionPathsFor is not implemented for S3-backed storage.
func (s *S3Store) ResolveSessionPathsFor(_, _ string) (SessionPaths, error) {
return SessionPaths{}, fmt.Errorf("artifacts s3 resolve session paths: not yet implemented")
}
// EnsureLayout returns a not-yet-implemented error in the scaffold.
func (s *S3Store) EnsureLayout(_ string) (SessionPaths, error) {
return SessionPaths{}, fmt.Errorf("artifacts s3 ensure layout: not yet implemented")
}
// EnsureLayoutFor returns a not-yet-implemented error in the scaffold.
func (s *S3Store) EnsureLayoutFor(_, _ string) (SessionPaths, error) {
return SessionPaths{}, fmt.Errorf("artifacts s3 ensure layout for campaign/session: not yet implemented")
}
// CopyInput returns a not-yet-implemented error in the scaffold.
func (s *S3Store) CopyInput(_, _, _ string) (Ref, error) {
return Ref{}, fmt.Errorf("artifacts s3 copy input: not yet implemented")
}
// CopyInputFor returns a not-yet-implemented error in the scaffold.
func (s *S3Store) CopyInputFor(_, _, _, _ string) (Ref, error) {
return Ref{}, fmt.Errorf("artifacts s3 copy input for campaign/session: not yet implemented")
@@ -66,11 +46,6 @@ func (s *S3Store) Checksum(_ string) (string, error) {
return "", fmt.Errorf("artifacts s3 checksum: not yet implemented")
}
// AcquireSessionLock returns a not-yet-implemented error in the scaffold.
func (s *S3Store) AcquireSessionLock(_ string) (*LockHandle, error) {
return nil, fmt.Errorf("artifacts s3 acquire lock: not yet implemented")
}
// AcquireSessionLockFor returns a not-yet-implemented error in the scaffold.
func (s *S3Store) AcquireSessionLockFor(_, _ string) (*LockHandle, error) {
return nil, fmt.Errorf("artifacts s3 acquire lock for campaign/session: not yet implemented")

View File

@@ -15,18 +15,13 @@ type Ref struct {
// Store is the local artifact/workdir abstraction used by orchestration code.
type Store interface {
SessionPaths(sessionID string) SessionPaths
SessionPathsFor(campaign, sessionID string) SessionPaths
ResolveSessionPathsFor(campaign, sessionID string) (SessionPaths, error)
EnsureLayout(sessionID string) (SessionPaths, error)
EnsureLayoutFor(campaign, sessionID string) (SessionPaths, error)
CopyInput(sessionID, srcPath, destRelativePath string) (Ref, error)
CopyInputFor(campaign, sessionID, srcPath, destRelativePath string) (Ref, error)
Exists(path string) (bool, error)
ExistsRef(ref Ref) (bool, error)
WriteFileAtomic(path string, data []byte, perm os.FileMode) error
Checksum(path string) (string, error)
AcquireSessionLock(sessionID string) (*LockHandle, error)
AcquireSessionLockFor(campaign, sessionID string) (*LockHandle, error)
ReleaseSessionLock(lock *LockHandle) error
}