Skip to content

Strengthen nullable type discipline with true-myth and safety tests#315

Draft
jhodapp wants to merge 2 commits intomainfrom
improve-nullable-types
Draft

Strengthen nullable type discipline with true-myth and safety tests#315
jhodapp wants to merge 2 commits intomainfrom
improve-nullable-types

Conversation

@jhodapp
Copy link
Copy Markdown
Member

@jhodapp jhodapp commented Feb 24, 2026

Description

Establishes stricter nullable type standards using true-myth (Maybe<T>, Result<T, E>) and begins fixing the most dangerous || "" ID fallback patterns. Adds 35 safety tests that lock down null/falsy-ID behavior as a prerequisite for the broader migration.

Changes

  • Install true-myth v9.3.1 for Maybe<T> and Result<T, E> types
  • Update .claude/coding-standards.md with nullable type hierarchy: Maybe<T>Result<T, E> → discriminated unions
  • Update .claude/CLAUDE.md with top-level nullable type rule
  • Replace 4 dangerous || "" ID fallbacks with render guards in coaching-tabs-container.tsx and page.tsx
  • Remove 1 unnecessary || "" in coaching-session-list.tsx (hook already accepts null)
  • Add 14 SWR hook null-path tests verifying no-fetch behavior with falsy IDs
  • Add 1 test for CoachingSessionApi.list(null) early return
  • Add 11 tests for sanitizeCallbackUrl null/undefined/empty handling
  • Add 6 tests for buildInitialOrder null-return contract

Testing Strategy

  • npm run test — all 612 tests pass (35 new)
  • npm run build — compiles cleanly with no TypeScript errors
  • Manual: navigate to a coaching session, verify Notes/Agreements/Actions tabs still render and function correctly
  • Manual: verify agreements tab only renders content once the session ID loads (render guard)

Concerns

  • This is the first phase of a larger nullable type migration. The assessment report (nullable-type-assessment.md, not committed) identifies ~65 domain-level violations across 6 tiers. This PR covers the standards + Tier 1 fixes only.
  • The AgreementsList render guard changes the always-mounted CSS display pattern slightly — the component now mounts when the session ID becomes available rather than on initial render. Tab switch state preservation is unaffected since the session ID doesn't change during tab switches.

Install true-myth for Maybe<T> and Result<T, E> types. Update coding
standards with concrete hierarchy: Maybe first, Result at async
boundaries, custom discriminated unions only when neither fits.
…ards

Step 0: 35 new tests locking down null/falsy-ID behavior before the
nullable type migration. Covers SWR hook URL/key nullification,
CoachingSessionApi.list early return, sanitizeCallbackUrl, and
buildInitialOrder contracts.

Step 1: Remove dangerous || "" ID fallbacks:
- coaching-tabs-container: render guard on AgreementsList, non-null
  assertions in handlers (guaranteed by the guard)
- page.tsx: render guard on EditorCacheProvider
- coaching-session-list: delete unnecessary || "" (hook already
  accepts null)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant