# FAQ ## Does this project still require npm/frontend TypeScript tooling? No. The legacy TypeScript frontend pipeline was removed after the Blazor rewrite. `scripts/ci-local.ps1` is now a .NET-only flow (restore, build, tests, coverage checks). ## Is frontend JavaScript handwritten? The runtime UI is now built with Blazor components (`RpgRoller/Components/*`). There is still small handwritten JavaScript in `RpgRoller/wwwroot/js/rpgroller-api.js` for: - browser `fetch` calls with cookie auth - SSE connection/reconnect handling - per-tab session storage helpers used by the Blazor UI There is no TypeScript runtime frontend in the current codebase. ## Where is backend state stored locally? Backend state is persisted via EF Core + SQLite. - Development default: `RpgRoller/App_Data/rpgroller.development.db` - Non-development default: `RpgRoller/App_Data/rpgroller.db` To start with a clean backend state, stop the app and remove the corresponding SQLite file. ## Do I need to run manual DB migrations after updating the app? Usually no. Startup now uses EF Core migration-based schema upgrades (`Database.Migrate`) and applies pending migrations automatically. ## How do I add a new EF migration in this repo? Use the repo-local tool manifest: ```powershell dotnet tool restore dotnet dotnet-ef migrations add --project RpgRoller/RpgRoller.csproj --startup-project RpgRoller/RpgRoller.csproj ``` ## Does the backend read SQLite on every API call? No. The backend loads state from SQLite once during startup into in-memory state and serves requests from memory. Successful state mutations are then written back to SQLite. ## Where is the frontend UX plan documented? The canonical frontend UX design lives in `UX.md` at the repository root. It defines roles, flows, screen behavior, validation/error handling, responsive behavior, and real-time update expectations to guide implementation. ## What does test coverage include? Coverage now includes the entire backend project (`RpgRoller`), including API/hosting/bootstrap code and services. It is no longer restricted to `RpgRoller.Services.*`. ## Why do backend services avoid API request DTO dependencies? Service workflows accept explicit parameters (for example, `CreateCampaign(sessionToken, name, rulesetId)`) instead of API request DTOs. This keeps the service layer independent from HTTP transport contracts while avoiding extra service-only wrapper command types. ## How do d6 wild dice and fumbles work now? d6 skills now store two explicit options: - `wildDice`: number of wild dice for the skill - `allowFumble`: whether wild dice rolling `1` can trigger fumble removal Roll responses and campaign log entries include per-die state flags (`crit`, `fumble`, `wild`, `removed`, `added`) so the frontend can render the full die-by-die outcome, not just the final total. ## How is the active character chosen in the Play screen? There is no separate activate button in Play. The selected character in the character picker is treated as active context and the UI syncs that choice to the backend for owned characters. ## Where did the Home page logic move after the refactor? `Home.razor` + `Home.razor.cs` now act as a small gateway that switches between loading, anonymous auth, and workspace views. Authenticated application state and behavior were moved into `Components/Pages/Workspace.razor`, while reusable concern UI remains under `Components/Pages/HomeControls/`. ## Why does the workspace header sometimes show "Loading user..." briefly? `Workspace` initializes authenticated session data after the first render (`OnAfterRenderAsync`). During that first render pass, the header now intentionally shows a null-safe fallback label instead of dereferencing user fields before `/api/me` has been loaded. ## Where did Play/Campaign Management switching move? Screen switching is now inside the header hamburger menu. The menu exposes `Play` and `Campaign Management` options while keeping the top bar compact. ## How do I create, edit, and roll skills in the Play column now? Skills now use inline row chip actions: - `✎` chip on each skill row to edit that skill - `⚄` chip on each skill row to roll immediately - a final `+` dummy row styled like a skill row to create a new skill Roll visibility remains controlled in the skills header row. ## Why was the "Last Roll" card removed from the character panel? The character column now prioritizes vertical density. Roll history is represented by the campaign log feed, so the dedicated last-roll card was removed to free space for skills and character context. ## Why does the character picker scroll horizontally? The picker was intentionally compressed into a single compact row to minimize vertical real estate in the Play layout. When many characters exist, it scrolls horizontally instead of growing taller. ## Why is there empty space below skills in the character panel? The panel now keeps card content condensed at the top and lets any remaining height expand below the skills list. This avoids stretched card sections while preserving full-height column behavior. ## Why is auth form state kept in `AuthSection` instead of `Home`? Auth inputs, validation, and submit workflows are transient UI concerns, so they now live in `AuthSection`. `Home` keeps shared session/workspace state and cross-control refresh/orchestration only. ## Why are there `.razor.cs` files next to Razor components? Component behavior was moved out of inline `@code` blocks into code-behind classes so `.razor` files stay markup-focused while state, parameters, handlers, and injected services live in typed C# files.