diff --git a/README.md b/README.md index 5d10b034..87cd7fc8 100644 --- a/README.md +++ b/README.md @@ -165,11 +165,9 @@ To run **bitvid** locally: _(Note: The application runs via `npx serve`. The default port is 3000, but it may select a different port if 3000 is occupied. Check your terminal output for the correct URL.)_ - _Note: If you prefer manual steps, run `npm run build` followed by `npx serve dist` (or `cd dist && python3 -m http.server 3000`), then open the root URL printed by the server (for example `http://localhost:3000/`). Because `dist` is the document root in this mode, always open `/` rather than appending `/dist`._ + _Note: If you prefer manual steps, run `npm run build` followed by `npx serve dist`. Because `dist` is the document root in this mode, always open `/` rather than appending `/dist`._ - _If you use a static server from the repository root (for example VS Code Live Server or `python3 -m http.server`), open `http://127.0.0.1:8000/dist/` with the trailing slash. `http://127.0.0.1:8000/dist` (no trailing slash) can resolve incorrectly depending on server routing._ - - _Optional: Add a local rewrite/redirect rule from `/dist` → `/dist/` so manual local testing always lands on the correct path._ + _If you use a static server from the repository root (for example VS Code Live Server or `python3 -m http.server`), open `http://127.0.0.1:8000/dist/` with the trailing slash._ 5. Verify setup: @@ -188,6 +186,7 @@ To run **bitvid** locally: - **Run unit tests**: `npm run test:unit` - **Format code**: `npm run format` (CSS, HTML, MD, Config - no JS logic) - **Lint code**: `npm run lint` (Styles, Tokens, Hex, Tailwind guards, file size, innerHTML, assets, SW compat - no ESLint/logic linting) +- **Visual tests**: `npm run test:visual` (Playwright snapshots) ### Dev Container @@ -604,4 +603,3 @@ See [`docs/qa.md`](docs/qa.md) for the copy/paste-friendly checklist we share wi ## License GPL-3.0-or-later. See [LICENSE](./LICENSE). - diff --git a/docs/agents/AGENT_TASK_LOG.csv b/docs/agents/AGENT_TASK_LOG.csv index 43ec2571..cb15cf3e 100644 --- a/docs/agents/AGENT_TASK_LOG.csv +++ b/docs/agents/AGENT_TASK_LOG.csv @@ -6,3 +6,5 @@ date,agent_name,prompt_file,status,branch,summary 2026-02-13,decompose-agent,bitvid-decompose-agent.md,completed,ai/decompose/daily-run,"Extracted ProfileHashtagController from profileModalController.js, reducing file size by ~600 lines" 2026-02-13,deps-security-agent,bitvid-deps-security-agent.md,started,ai/deps-security/daily-run,"Task claimed — execution beginning" 2026-02-13,deps-security-agent,bitvid-deps-security-agent.md,completed,ai/deps-security/daily-run,"Generated npm audit/outdated artifacts and deps report; upgrade attempts blocked by Node >=22 engine requirement in environment" +2026-02-13,docs-agent,bitvid-docs-agent.md,started,ai/docs/daily-run,"Task claimed — execution beginning" +2026-02-13,docs-agent,bitvid-docs-agent.md,completed,ai/docs/daily-run,"Updated README.md with clearer dev setup instructions" diff --git a/js/ui/profileModalController.js b/js/ui/profileModalController.js index f154ea52..d6b42703 100644 --- a/js/ui/profileModalController.js +++ b/js/ui/profileModalController.js @@ -96,11 +96,6 @@ export class ProfileModalController { this.showStatus = showStatus; this.designSystem = normalizeDesignSystemContext(designSystem); - this.dmController = new ProfileDirectMessageController(this); - this.relayController = new ProfileRelayController(this); - this.hashtagController = new ProfileHashtagController(this); - this.hashtagController.initialize(); - const resolvedMaxWalletDefaultZap = typeof providedConstants.MAX_WALLET_DEFAULT_ZAP === "number" && Number.isFinite(providedConstants.MAX_WALLET_DEFAULT_ZAP) @@ -168,8 +163,6 @@ export class ProfileModalController { this.adminSuperNpub = resolvedAdminSuperNpub; this.adminDmImageUrl = resolvedAdminDmImageUrl; this.bitvidWebsiteUrl = resolvedbitvidWebsiteUrl; - this.dmController.enableNip17RelayWarning = resolvedEnableNip17RelayWarning; - this.dmController.hasShownRelayWarning = false; this.internalState = { savedProfiles: [], @@ -183,11 +176,18 @@ export class ProfileModalController { dmRelayHints: new Map(), }; - this.dmController.dmMobileView = "list"; - this.services = buildServicesContract(services, this.internalState); this.state = buildStateContract(state, this.internalState); + this.dmController = new ProfileDirectMessageController(this); + this.relayController = new ProfileRelayController(this); + this.hashtagController = new ProfileHashtagController(this); + this.hashtagController.initialize(); + + this.dmController.enableNip17RelayWarning = resolvedEnableNip17RelayWarning; + this.dmController.hasShownRelayWarning = false; + this.dmController.dmMobileView = "list"; + this.normalizeHexPubkey = this.services.normalizeHexPubkey; this.safeEncodeNpub = this.services.safeEncodeNpub; this.safeDecodeNpub = this.services.safeDecodeNpub; diff --git a/tests/profile-modal-controller.test.mjs b/tests/profile-modal-controller.test.mjs index b0fc2e3f..8c8df906 100644 --- a/tests/profile-modal-controller.test.mjs +++ b/tests/profile-modal-controller.test.mjs @@ -312,6 +312,8 @@ function createController(options = {}) { eventId: null, createdAt: null, loaded: true, + uiReady: true, + dataReady: true, }), describeHashtagPreferencesError: () => '', onAccessControlUpdated: async () => {}, @@ -961,7 +963,7 @@ for (const _ of [0]) { const interestList = document.getElementById('profileHashtagInterestList'); assert.equal(interestList?.querySelectorAll('li').length, 1); - controller.hashtagPreferencesService.removeInterest('art'); + controller.services.hashtagPreferences.removeInterest('art'); await controller.handleAuthLogout({}); await waitForAnimationFrame(window, 2);