Skip to content

feat: post-redesign cleanup (isDefaultDir, PlanList icon, strip PropTypes) - #27

Merged
guarzo merged 7 commits into
mainfrom
worktree-post-redesign-cleanup
May 5, 2026
Merged

feat: post-redesign cleanup (isDefaultDir, PlanList icon, strip PropTypes)#27
guarzo merged 7 commits into
mainfrom
worktree-post-redesign-cleanup

Conversation

@guarzo

@guarzo guarzo commented May 5, 2026

Copy link
Copy Markdown
Owner

Summary

Three loose ends from PR #26:

  • Profiles.isDefaultDir now derives from a backend signal. Adds IsDefaultSettingsDir() to ConfigurationService, exposes it as isDefaultDir in GET /api/config, threads it through Routes → Profiles. The Reset-to-default button hides correctly on first load when the user is already on the default Tranquility directory.
  • PlanList uses the EveTypeIcon primitive (introduced in feat(ui): SkillPlans Timeline + merged Profiles page; six shared primitives #26) instead of duplicating the inline <img>.
  • PropTypes stripped from all 46 renderer source files. PropTypes runtime validation is inert in React 19; the declarations were misleading. The prop-types npm dep is removed.

Spec / plan

  • Spec: docs/superpowers/specs/2026-05-05-post-redesign-cleanup-design.md
  • Plan: docs/superpowers/plans/2026-05-05-post-redesign-cleanup.md

Commits (in order)

  1. feat(profiles): drive isDefaultDir from backend config — Section A end-to-end
  2. refactor(skill-plans): use EveTypeIcon in PlanList rows — Section B
  3. chore: strip PropTypes (inert in React 19) from renderer source — Section C.1
  4. chore: remove prop-types from renderer dependencies — Section C.2

55 files changed (+113/-499). The strip is net negative as expected.

Tooling

scripts/strip-proptypes.mjs is checked in as a one-shot tool used to do the strip. Idempotent — running it again is a no-op. Two files needed manual cleanup the regex couldn't handle (StatusDot's adjacent-helper case and Connector/PairSelect's standalone PropType-shape consts); those are also fixed.

Test plan

  • go test ./... passes
  • cd renderer && npm test — 30/30 files, 119/119 tests passing
  • cd renderer && npm run build succeeds
  • Manual: /profiles?view=sync on first launch with default Tranquility dir → Reset button is hidden
  • Manual: choose a custom dir → Reset button appears → click Reset → button hides again
  • Manual: /skill-plans By-plan view still renders plan icons correctly

Notes

  • The 588 lint errors reported by ESLint are pre-existing on main (mostly no-console and React 19 prop-types rule violations that are now resolved by the strip — net lint count actually drops). No new errors introduced.
  • The prop-types npm package itself is still present transitively (pulled in by @mui/utils). That's expected — we only removed the direct dependency.

🤖 Generated with Claude Code

Summary by CodeRabbit

  • New Features

    • Detect and expose whether the app is using the default settings directory; Profiles now receives this and the UI shows/hides the reset-to-default action accordingly.
    • Plan list icons upgraded to use a consistent icon component for clearer plan visuals.
  • Refactor

    • Removed runtime PropTypes checks and dependency; components rely on implicit props/defaults.
  • Tests

    • Added tests validating reset-to-default button visibility when default vs custom directory is used.

guarzo added 6 commits May 5, 2026 15:34
Adds IsDefaultSettingsDir() to ConfigurationService, returns it as
isDefaultDir in the GET /api/config response, and threads it through
Routes -> Profiles as a prop. Profiles drops its local useState; the
Reset-to-default button now hides correctly on first load when the
current directory matches the OS default Tranquility location.
PropTypes runtime validation was deprecated in React 19 — declarations
are no longer checked. Removed all 'import PropTypes from prop-types'
lines and all <Component>.propTypes = { … } blocks across 46 files via
scripts/strip-proptypes.mjs (kept for reference / re-runs).

The 'prop-types' npm dep is removed in the next commit.
PropTypes were stripped from source in the previous commit; this removes
the now-unused npm dependency.
@coderabbitai

coderabbitai Bot commented May 5, 2026

Copy link
Copy Markdown

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: b4c3dd52-b0fe-40a1-87d1-d4eea2e53850

📥 Commits

Reviewing files that changed from the base of the PR and between 7afd110 and c1ec259.

📒 Files selected for processing (1)
  • renderer/src/pages/Profiles.jsx

📝 Walkthrough

Walkthrough

This PR adds a backend signal IsDefaultSettingsDir → exposes isDefaultDir on GET /api/config and passes it to Profiles; swaps PlanList’s inline plan icon rendering to use EveTypeIcon; and mechanically strips PropTypes imports/declarations from 40+ renderer files and removes the prop-types dependency, plus an idempotent strip script.

Changes

Backend isDefaultDir Signal & Frontend Integration

Layer / File(s) Summary
Service Interface & Mock
internal/services/interfaces/configuration.go, internal/testutil/mock_interfaces.go
Adds IsDefaultSettingsDir() (bool, error) to ConfigurationService interface and mock MockConfigService method.
Configuration Service Implementation
internal/services/config/configuration_service.go
Implements IsDefaultSettingsDir() that compares configured settings dir to OS default; handles errors.
Config Handler
internal/handlers/config.go
GET /api/config now calls IsDefaultSettingsDir(), logs non-fatal errors, and includes "isDefaultDir": <bool> in the response payload.
Frontend Config Routing
renderer/src/Routes.jsx
Reads isDefaultDir from config (supports isDefaultDir or IsDefaultDir) and passes it as a prop to Profiles.
Profiles Component & Tests
renderer/src/pages/Profiles.jsx, renderer/src/pages/Profiles.test.jsx
Profiles now accepts isDefaultDir (default false) and lastBackupDir; internal isDefaultDir state removed; handlers no longer mutate local isDefaultDir; tests added to assert reset button visibility based on the prop.

PlanList Icon Enhancement

Layer / File(s) Summary
UI Component Update
renderer/src/components/skillplan/PlanList.jsx
Imports EveTypeIcon and replaces conditional inline <img>/placeholder icon rendering with <EveTypeIcon name={p.name} conversions={conversions} />; PropTypes block removed.

PropTypes Removal Across Frontend

Layer / File(s) Summary
Automated Strip Script
scripts/strip-proptypes.mjs
New Node script to remove prop-types import lines and Identifier.propTypes = { ... } blocks idempotently; logs per-file and aggregate counts.
Dependency Cleanup
renderer/package.json
Removed prop-types dependency.
Component PropTypes Removal
renderer/src/components/*/*, renderer/src/pages/*, renderer/src/components/ui/*
Removed import PropTypes from 'prop-types'; and *.propTypes declarations across ~40+ components; one component (LoadingScreen) updated to use a default parameter for message.

Sequence Diagram

sequenceDiagram
    participant Backend as ConfigurationService
    participant Handler as Config Handler
    participant API as GET /api/config
    participant Routes as Routes.jsx
    participant Profiles as Profiles Component

    Routes->>API: request config
    API->>Handler: run handler
    Handler->>Backend: IsDefaultSettingsDir()
    Backend-->>Handler: returns bool / error
    Handler->>API: include isDefaultDir in payload
    API-->>Routes: config with isDefaultDir
    Routes->>Routes: extract isDefaultDir (camel/Pascal fallback)
    Routes->>Profiles: pass isDefaultDir prop
    Profiles->>Profiles: render UI (reset button visibility)
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~45 minutes

Possibly related PRs

  • guarzo/canifly#11: Overlaps changes to many renderer UI components where PropTypes are removed or modified.
  • guarzo/canifly#26: Related frontend wiring for Profiles/Routes and PlanList/EveTypeIcon changes.
  • guarzo/canifly#21: Touches shared renderer UI components (PlanList and others) with overlapping edits.

Poem

🐰
I hopped from handler down to Routes,
A flag in config snugly routes,
Icons swapped to Eve’s neat art,
PropTypes trimmed — a lighter heart,
Fresh commits, one tidy start.

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title accurately and concisely summarizes the three main changes in the changeset: introducing isDefaultDir tracking from the backend, replacing PlanList's inline icon with EveTypeIcon, and stripping PropTypes declarations.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch worktree-post-redesign-cleanup
✨ Simplify code
  • Create PR with simplified code
  • Commit simplified code in branch worktree-post-redesign-cleanup

Comment @coderabbitai help to get the list of available commands and usage tips.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
renderer/src/pages/Profiles.jsx (1)

156-166: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Add refreshData() call after successful reset to update UI.

The handleResetToDefault operation calls resetToDefaultDirectory() but the run() function doesn't trigger a data refresh. After the API succeeds, the isDefaultDir prop won't update, leaving the Reset button visible until the user manually refreshes the page. Call refreshData() (from useAppData) on success to reflect the backend state change.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@renderer/src/pages/Profiles.jsx` around lines 156 - 166, handleResetToDefault
currently calls resetToDefaultDirectory via run but never refreshes application
state; after the run completes successfully, call refreshData() (from
useAppData) to update isDefaultDir and the UI — i.e., in handleResetToDefault,
after the await run(...) resolves and indicates success, invoke refreshData() so
the profile page reflects the backend change (referencing handleResetToDefault,
run, resetToDefaultDirectory, and refreshData).
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@docs/superpowers/plans/2026-05-05-post-redesign-cleanup.md`:
- Around line 614-615: The document line "Expected: same error count as on
baseline (the codebase has 230 pre-existing errors, mostly `no-console`).
Crucially: no **new** errors." is out of date; update that text to reflect the
current pre-existing ESLint error count (588) or replace the hard-coded number
with a number-agnostic phrase like "must match baseline" / "no new errors beyond
baseline" so CI/triage isn't misled; update the same sentence in the "Expected:"
block and any nearby references to the baseline number to ensure consistency.
- Line 7: There are inconsistent expected Vitest totals: update every occurrence
of the phrases "117 tests" and "119" in this document so they all match the
actual current Vitest run count; run the test suite locally to determine the
correct total and replace all instances (search for the exact text "117 tests"
and the other "119" mentions) so the runbook uses one consistent number
throughout.

---

Outside diff comments:
In `@renderer/src/pages/Profiles.jsx`:
- Around line 156-166: handleResetToDefault currently calls
resetToDefaultDirectory via run but never refreshes application state; after the
run completes successfully, call refreshData() (from useAppData) to update
isDefaultDir and the UI — i.e., in handleResetToDefault, after the await
run(...) resolves and indicates success, invoke refreshData() so the profile
page reflects the backend change (referencing handleResetToDefault, run,
resetToDefaultDirectory, and refreshData).
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro

Run ID: b4d633eb-1ccb-4b8e-a773-d295370d43c6

📥 Commits

Reviewing files that changed from the base of the PR and between fe34d50 and 7afd110.

⛔ Files ignored due to path filters (1)
  • renderer/package-lock.json is excluded by !**/package-lock.json
📒 Files selected for processing (56)
  • docs/superpowers/plans/2026-05-05-post-redesign-cleanup.md
  • docs/superpowers/specs/2026-05-05-post-redesign-cleanup-design.md
  • internal/handlers/config.go
  • internal/services/config/configuration_service.go
  • internal/services/interfaces/configuration.go
  • internal/testutil/mock_interfaces.go
  • renderer/package.json
  • renderer/src/Routes.jsx
  • renderer/src/components/character-overview/CharacterOverviewFilter.jsx
  • renderer/src/components/character-overview/CharacterOverviewToolbar.jsx
  • renderer/src/components/character-overview/CharacterRow.jsx
  • renderer/src/components/character-overview/ExpandedRow.jsx
  • renderer/src/components/character-overview/GroupBlock.jsx
  • renderer/src/components/character-overview/RowMenu.jsx
  • renderer/src/components/common/AccountPromptModal.jsx
  • renderer/src/components/common/CharacterDetailModal.jsx
  • renderer/src/components/common/CustomConfirmDialog.jsx
  • renderer/src/components/common/Header.jsx
  • renderer/src/components/common/HeaderNav.jsx
  • renderer/src/components/common/HeaderToolbarActions.jsx
  • renderer/src/components/common/HeaderUserMenu.jsx
  • renderer/src/components/common/SubPageHeader.jsx
  • renderer/src/components/landing/LoginButton.jsx
  • renderer/src/components/profiles/MapAccountCard.jsx
  • renderer/src/components/profiles/MapCharacterCard.jsx
  • renderer/src/components/profiles/MappingView.jsx
  • renderer/src/components/profiles/MtimeSwatch.jsx
  • renderer/src/components/profiles/SwatchBridge.jsx
  • renderer/src/components/profiles/SyncProfileRow.jsx
  • renderer/src/components/profiles/SyncView.jsx
  • renderer/src/components/setup/FirstRunDialog.jsx
  • renderer/src/components/skillplan/AddSkillPlanModal.jsx
  • renderer/src/components/skillplan/MatrixShell.jsx
  • renderer/src/components/skillplan/MissingSkillsPopover.jsx
  • renderer/src/components/skillplan/PlanList.jsx
  • renderer/src/components/skillplan/PlanMatrix.jsx
  • renderer/src/components/skillplan/PlanTimeline.jsx
  • renderer/src/components/skills/SkillProgress.jsx
  • renderer/src/components/ui/Connector.jsx
  • renderer/src/components/ui/EveTypeIcon.jsx
  • renderer/src/components/ui/FilterBar.jsx
  • renderer/src/components/ui/Kbd.jsx
  • renderer/src/components/ui/LoadingScreen.jsx
  • renderer/src/components/ui/PageShell.jsx
  • renderer/src/components/ui/PairSelect.jsx
  • renderer/src/components/ui/ProgressRail.jsx
  • renderer/src/components/ui/SegmentedControl.jsx
  • renderer/src/components/ui/SkeletonLoader.jsx
  • renderer/src/components/ui/StatusDot.jsx
  • renderer/src/components/ui/Subheader.jsx
  • renderer/src/components/ui/Surface.jsx
  • renderer/src/pages/CharacterOverview.jsx
  • renderer/src/pages/Profiles.jsx
  • renderer/src/pages/Profiles.test.jsx
  • renderer/src/pages/SkillPlans.jsx
  • scripts/strip-proptypes.mjs
💤 Files with no reviewable changes (45)
  • renderer/src/components/profiles/SyncProfileRow.jsx
  • renderer/src/components/skillplan/PlanMatrix.jsx
  • renderer/src/components/ui/Surface.jsx
  • renderer/src/components/ui/Kbd.jsx
  • renderer/src/components/common/AccountPromptModal.jsx
  • renderer/src/components/skillplan/MatrixShell.jsx
  • renderer/src/components/landing/LoginButton.jsx
  • renderer/src/components/profiles/MapAccountCard.jsx
  • renderer/src/components/ui/FilterBar.jsx
  • renderer/src/components/ui/Subheader.jsx
  • renderer/src/components/profiles/MtimeSwatch.jsx
  • renderer/src/components/skillplan/PlanTimeline.jsx
  • renderer/src/components/common/HeaderUserMenu.jsx
  • renderer/src/components/character-overview/ExpandedRow.jsx
  • renderer/src/components/ui/SegmentedControl.jsx
  • renderer/src/components/profiles/MappingView.jsx
  • renderer/src/components/ui/ProgressRail.jsx
  • renderer/src/components/character-overview/CharacterOverviewFilter.jsx
  • renderer/src/components/skillplan/AddSkillPlanModal.jsx
  • renderer/src/components/skillplan/MissingSkillsPopover.jsx
  • renderer/src/components/common/CustomConfirmDialog.jsx
  • renderer/package.json
  • renderer/src/components/profiles/SwatchBridge.jsx
  • renderer/src/components/ui/Connector.jsx
  • renderer/src/components/profiles/SyncView.jsx
  • renderer/src/components/common/CharacterDetailModal.jsx
  • renderer/src/components/ui/PairSelect.jsx
  • renderer/src/components/skills/SkillProgress.jsx
  • renderer/src/components/character-overview/RowMenu.jsx
  • renderer/src/components/ui/EveTypeIcon.jsx
  • renderer/src/pages/SkillPlans.jsx
  • renderer/src/pages/CharacterOverview.jsx
  • renderer/src/components/ui/SkeletonLoader.jsx
  • renderer/src/components/character-overview/CharacterOverviewToolbar.jsx
  • renderer/src/components/ui/StatusDot.jsx
  • renderer/src/components/common/HeaderNav.jsx
  • renderer/src/components/common/HeaderToolbarActions.jsx
  • renderer/src/components/common/SubPageHeader.jsx
  • renderer/src/components/character-overview/GroupBlock.jsx
  • renderer/src/components/common/Header.jsx
  • renderer/src/components/setup/FirstRunDialog.jsx
  • renderer/src/components/profiles/MapCharacterCard.jsx
  • renderer/src/components/ui/PageShell.jsx
  • renderer/src/components/character-overview/CharacterRow.jsx
  • renderer/src/components/ui/LoadingScreen.jsx


**Goal:** Tie up three loose ends from PR #26: drive `Profiles.isDefaultDir` from a new backend signal; replace the inline icon in `PlanList` with `EveTypeIcon`; strip the now-inert PropTypes declarations and the `prop-types` dependency.

**Architecture:** A → B → C in one PR with three logical commits (Section A is one commit because the frontend depends on the new backend field). Section C is mechanical — a Node script walks `renderer/src/`, deletes the `prop-types` import line and the `<Component>.propTypes = { … };` block from each file. The PR ships when lint, full vitest suite (117 tests), and `npm run build` are all green.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Unify the expected Vitest test count in this runbook.

Line 7 says 117 tests, while Line 407 and Line 630 say 119. Keep one consistent expected total to prevent false alarms during execution handoff.

Also applies to: 407-407, 630-630

🧰 Tools
🪛 LanguageTool

[grammar] ~7-~7: Ensure spelling is correct
Context: ...each file. The PR ships when lint, full vitest suite (117 tests), and npm run build ...

(QB_NEW_EN_ORTHOGRAPHY_ERROR_IDS_1)

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/superpowers/plans/2026-05-05-post-redesign-cleanup.md` at line 7, There
are inconsistent expected Vitest totals: update every occurrence of the phrases
"117 tests" and "119" in this document so they all match the actual current
Vitest run count; run the test suite locally to determine the correct total and
replace all instances (search for the exact text "117 tests" and the other "119"
mentions) so the runbook uses one consistent number throughout.

Comment on lines +614 to +615
Expected: same error count as on baseline (the codebase has 230 pre-existing errors, mostly `no-console`). Crucially: no **new** errors. If new errors appear, they're caused by malformed deletions — revert and investigate.

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Update the ESLint baseline count to match current project reality.

This section says baseline is 230 errors, but the PR context for this change indicates 588 pre-existing errors. Use either the current number or a number-agnostic check (“must match baseline”) to avoid mis-triage.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/superpowers/plans/2026-05-05-post-redesign-cleanup.md` around lines 614
- 615, The document line "Expected: same error count as on baseline (the
codebase has 230 pre-existing errors, mostly `no-console`). Crucially: no
**new** errors." is out of date; update that text to reflect the current
pre-existing ESLint error count (588) or replace the hard-coded number with a
number-agnostic phrase like "must match baseline" / "no new errors beyond
baseline" so CI/triage isn't misled; update the same sentence in the "Expected:"
block and any nearby references to the baseline number to ensure consistency.

handleResetToDefault and handleChooseSettingsDir mutate state on the
backend but never invalidated the frontend's cached config, so the
isDefaultDir-driven Reset button stayed visible after a successful
reset until the 10-min HTTP cache expired. Both handlers now call
refreshData() on success so the UI reflects the backend change.

Same pattern as the original Sync.jsx pre-redesign; we lost it in the
A.4 cleanup that removed the local setIsDefaultDir state and assumed
the backend would drive the prop on its own.
@guarzo
guarzo merged commit 4f60ec0 into main May 5, 2026
2 checks passed
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