refactor(multiple): continue Phase 6 Optional[T] elimination (batch 3)

Phase 6: Eliminate Optional[T] returns - BATCH 3 of 7
Before: 4 more Optional[T] returns removed
After:  0 in app_controller.py (Pending MMA), project_manager.py
        (load_track_state), session_logger.py (log_tool_call),
        models.py (TrackState.metadata defaults)
Delta:  -4 sites (cumulative: -19 of 30)

Specific changes:
- src/app_controller.py:2781,2785: _pending_mma_spawn, _pending_mma_approval
  return Metadata() (zero-init sentinel) when no pending items
- src/project_manager.py:301: load_track_state returns EMPTY_TRACK_STATE
  sentinel (added to models.py) when no state file exists or load fails
- src/models.py:476: TrackState.metadata now has default_factory=dict;
  EMPTY_TRACK_STATE = TrackState() added as module-level sentinel
- src/session_logger.py:166: log_tool_call returns str (was Optional[str])

Test impact:
- test_track_state_persistence.py: 4 tests pass (existing tests)
- test_app_controller_result.py: 12 tests pass

Verification:
- audit_weak_types --strict: OK (107 <= 112 baseline)
- py_check_syntax: OK on all changed files
- 44 tests pass (test_track_state_persistence, test_track_state_schema,
  test_session_logger_optimization, test_app_controller_result)

REMAINING: ~11 Optional[T] returns in:
- src/external_editor.py (3 - get_editor, _find_vscode_common_paths,
  auto_detect_vscode)
- src/file_cache.py (7 - tree_sitter.Node walks + get_file_id)
- src/diff_viewer.py (1 - parse_hunk_header)
This commit is contained in:
ed
2026-06-26 05:11:09 -04:00
parent ba3eb0c090
commit 4ca95551c0
4 changed files with 15 additions and 10 deletions
+4 -4
View File
@@ -2778,12 +2778,12 @@ class AppController:
)]) )])
@property @property
def _pending_mma_spawn(self) -> Optional[Metadata]: def _pending_mma_spawn(self) -> Metadata:
return self._pending_mma_spawns[0] if self._pending_mma_spawns else None return self._pending_mma_spawns[0] if self._pending_mma_spawns else Metadata()
@property @property
def _pending_mma_approval(self) -> Optional[Metadata]: def _pending_mma_approval(self) -> Metadata:
return self._pending_mma_approvals[0] if self._pending_mma_approvals else None return self._pending_mma_approvals[0] if self._pending_mma_approvals else Metadata()
@property @property
def current_provider(self) -> str: def current_provider(self) -> str:
+5 -1
View File
@@ -474,7 +474,7 @@ class Metadata:
@dataclass @dataclass
class TrackState: class TrackState:
metadata: Metadata metadata: Metadata = field(default_factory=dict)
discussion: List[str] = field(default_factory=list) discussion: List[str] = field(default_factory=list)
tasks: List[Ticket] = field(default_factory=list) tasks: List[Ticket] = field(default_factory=list)
@@ -524,6 +524,10 @@ class TrackState:
tasks = [Ticket.from_dict(t) for t in data.get("tasks", [])], tasks = [Ticket.from_dict(t) for t in data.get("tasks", [])],
) )
EMPTY_TRACK_STATE: TrackState = TrackState()
@dataclass @dataclass
class FileItem: class FileItem:
path: str path: str
+5 -4
View File
@@ -298,18 +298,19 @@ def save_track_state(track_id: str, state: 'TrackState', base_dir: Union[str, Pa
data = clean_nones(state.to_dict()) data = clean_nones(state.to_dict())
with open(state_file, "wb") as f: tomli_w.dump(data, f) with open(state_file, "wb") as f: tomli_w.dump(data, f)
def load_track_state(track_id: str, base_dir: Union[str, Path] = ".") -> Optional['TrackState']: def load_track_state(track_id: str, base_dir: Union[str, Path] = ".") -> "TrackState":
""" """
Loads a TrackState object from conductor/tracks/<track_id>/state.toml. Loads a TrackState object from conductor/tracks/<track_id>/state.toml.
Returns empty TrackState (zero-init) if not found.
[C: tests/test_track_state_persistence.py:test_track_state_persistence] [C: tests/test_track_state_persistence.py:test_track_state_persistence]
""" """
from src.models import TrackState from src.models import TrackState, EMPTY_TRACK_STATE
state_file = paths.get_track_state_dir(track_id, project_path=str(base_dir)) / 'state.toml' state_file = paths.get_track_state_dir(track_id, project_path=str(base_dir)) / 'state.toml'
if not state_file.exists(): return None if not state_file.exists(): return EMPTY_TRACK_STATE
try: try:
with open(state_file, "rb") as f: data = tomllib.load(f) with open(state_file, "rb") as f: data = tomllib.load(f)
except (OSError, tomllib.TOMLDecodeError): except (OSError, tomllib.TOMLDecodeError):
return None return EMPTY_TRACK_STATE
return TrackState.from_dict(data) return TrackState.from_dict(data)
def load_track_history(track_id: str, base_dir: Union[str, Path] = ".") -> list[str]: def load_track_history(track_id: str, base_dir: Union[str, Path] = ".") -> list[str]:
+1 -1
View File
@@ -163,7 +163,7 @@ def log_comms(entry: dict[str, Any]) -> Result[bool]:
except (OSError, TypeError, ValueError) as e: except (OSError, TypeError, ValueError) as e:
return Result(data=False, errors=[ErrorInfo(kind=ErrorKind.INTERNAL, message=str(e), source="session_logger.log_comms", original=e)]) return Result(data=False, errors=[ErrorInfo(kind=ErrorKind.INTERNAL, message=str(e), source="session_logger.log_comms", original=e)])
def log_tool_call(script: str, result: str, script_path: Optional[str]) -> Optional[str]: def log_tool_call(script: str, result: str, script_path: Optional[str]) -> str:
""" """
Append a tool-call record to the toolcalls log and write the PS1 script to Append a tool-call record to the toolcalls log and write the PS1 script to
the session's scripts directory. Returns the path of the written script file. the session's scripts directory. Returns the path of the written script file.