683 lines
16 KiB
Markdown
683 lines
16 KiB
Markdown
# Stack Priorities And Playwright Plan
|
||
|
||
> **Date:** 2026-03-16
|
||
> **Product:** ResolutionFlow
|
||
> **Purpose:** Turn the recent stack-gap review into a practical, sequenced execution plan
|
||
|
||
---
|
||
|
||
## Summary
|
||
|
||
ResolutionFlow already has a credible application stack:
|
||
|
||
- React 19 + TypeScript + Vite on the frontend
|
||
- FastAPI + async SQLAlchemy + PostgreSQL on the backend
|
||
- Sentry on both frontend and backend
|
||
- CI with backend coverage plus frontend lint/test/build
|
||
- Strong backend integration test coverage
|
||
- Route-level lazy loading and bundle chunking already in place
|
||
|
||
The next step is not a stack rewrite.
|
||
|
||
The biggest gains now come from:
|
||
|
||
1. Better product visibility
|
||
2. Better release confidence
|
||
3. Better enterprise trust signals
|
||
4. Better workflow gravity inside the app
|
||
|
||
---
|
||
|
||
## Ranked Recommendations
|
||
|
||
### 1. Fastest Wins
|
||
|
||
These are the best short-term upgrades if the goal is to make the product feel more polished and more professional quickly.
|
||
|
||
#### 1. Product analytics instrumentation
|
||
**Why:** Sentry tells us when the app breaks. It does not tell us what users value, where they stall, or what converts.
|
||
|
||
**Recommended:** PostHog
|
||
|
||
**Track first:**
|
||
- Account created
|
||
- First successful login
|
||
- First flow viewed
|
||
- First session started
|
||
- First session completed
|
||
- First export generated
|
||
- First AI feature used
|
||
- First PSA integration connected
|
||
- First shared session created
|
||
|
||
**Why this is a fast win:** High leverage with low UI churn.
|
||
|
||
#### 2. Better empty states and onboarding guidance
|
||
**Why:** Mature apps reduce ambiguity. Empty libraries, empty analytics, and empty integrations pages should guide the next action immediately.
|
||
|
||
**Add first:**
|
||
- Empty flow library CTA
|
||
- Empty analytics explanation + “how data appears here”
|
||
- Empty integrations state with benefit-oriented copy
|
||
- New team “starter checklist”
|
||
|
||
#### 3. Professional exports
|
||
**Why:** Exports are one of the fastest ways for a B2B product to feel premium.
|
||
|
||
**Add first:**
|
||
- Client-ready PDF export
|
||
- Logo/header metadata block
|
||
- Cleaner ticket/session summary layout
|
||
- Optional evidence attachment section
|
||
|
||
#### 4. Coverage gates in CI
|
||
**Why:** Cheap trust signal internally. Prevents quality drift as the codebase expands.
|
||
|
||
**Add first:**
|
||
- Fail backend CI if total coverage drops below agreed threshold
|
||
- Publish frontend coverage report
|
||
|
||
---
|
||
|
||
### 2. Best ROI
|
||
|
||
These are the best medium-term investments if the goal is to improve product quality and roadmap clarity without taking on huge platform risk.
|
||
|
||
#### 1. Playwright end-to-end coverage
|
||
**Why:** Backend coverage is strong, but frontend confidence is still thinner than the app’s complexity now deserves.
|
||
|
||
**High-value flows to cover first:**
|
||
- Login
|
||
- Authenticated app shell loads
|
||
- Session history loads
|
||
- Account settings save flow
|
||
- Feedback submission
|
||
- Shared session page access
|
||
|
||
**Why this is high ROI:** It catches real regressions users actually feel.
|
||
|
||
#### 2. Security header hardening
|
||
**Why:** MSP buyers care about security posture. This is both a real protection layer and a professionalism layer.
|
||
|
||
**Add first:**
|
||
- Content-Security-Policy
|
||
- Strict-Transport-Security
|
||
- X-Frame-Options or CSP `frame-ancestors`
|
||
- Referrer-Policy
|
||
- Permissions-Policy
|
||
- Trusted host validation where appropriate
|
||
|
||
#### 3. Web Vitals and performance budgeting
|
||
**Why:** Route splitting is already implemented, so the next step is protecting performance over time.
|
||
|
||
**Track first:**
|
||
- LCP
|
||
- INP
|
||
- CLS
|
||
- Initial JS size
|
||
- Editor route chunk size
|
||
- Landing page chunk size
|
||
|
||
#### 4. Search and recall improvements
|
||
**Why:** One of the biggest compounding opportunities is turning ResolutionFlow into team memory, not just a flow runner.
|
||
|
||
**Good first step:**
|
||
- Search for similar sessions and prior resolutions by flow, tag, client, or ticket context
|
||
|
||
---
|
||
|
||
### 3. Biggest Enterprise / Trust Upgrades
|
||
|
||
These are the moves most likely to change how serious buyers perceive the product.
|
||
|
||
#### 1. Evidence-rich sessions
|
||
**Add:**
|
||
- Screenshot upload/paste
|
||
- Attachments
|
||
- Command output capture
|
||
- Evidence in exports
|
||
|
||
**Why it matters:** MSP work is proof-heavy. Evidence makes the platform feel operationally complete.
|
||
|
||
#### 2. Smart PSA / client context
|
||
**Add:**
|
||
- Ticket details
|
||
- Client/site context
|
||
- Related recent sessions
|
||
- Asset/configuration context
|
||
- SLA metadata
|
||
|
||
**Why it matters:** This is what reduces alt-tabbing and makes ResolutionFlow feel indispensable.
|
||
|
||
#### 3. Queue / worker architecture
|
||
**Why:** AI tasks, indexing, imports, notifications, and integration syncs will eventually compete with request handling.
|
||
|
||
**Likely candidates:**
|
||
- AI generation jobs
|
||
- KB imports
|
||
- Embedding/indexing
|
||
- Webhook fan-out
|
||
- Scheduled maintenance orchestration
|
||
- PDF generation
|
||
|
||
#### 4. Buyer-facing trust surfaces
|
||
**Add:**
|
||
- Changelog
|
||
- Status page
|
||
- Security page
|
||
- Backup/export promise
|
||
- Clear onboarding docs
|
||
|
||
**Why it matters:** Buyers infer maturity from these before they inspect the product deeply.
|
||
|
||
---
|
||
|
||
## Recommended Execution Order
|
||
|
||
### Do Now
|
||
1. Add product analytics
|
||
2. Add Playwright for core journeys
|
||
3. Add security headers and trust hardening
|
||
4. Improve empty states and professional exports
|
||
|
||
### Do Next
|
||
1. Add smart PSA/client context in sessions
|
||
2. Add evidence-rich sessions and attachments
|
||
3. Add search/recall improvements
|
||
4. Add Web Vitals and performance budgets
|
||
|
||
### Explore After That
|
||
1. Add queue/worker architecture
|
||
2. Expand offline/PWA support for session running
|
||
3. Add deeper RMM context integrations
|
||
|
||
---
|
||
|
||
## Playwright Implementation Plan
|
||
|
||
## Goal
|
||
|
||
Add Playwright in a way that improves confidence quickly without creating a brittle, high-maintenance test suite.
|
||
|
||
The right strategy is:
|
||
|
||
- start with a small smoke suite
|
||
- prefer stable selectors and seeded users
|
||
- avoid highly dynamic AI/editor interactions in phase 1
|
||
- run Chromium first
|
||
- only expand once the suite is reliable in CI
|
||
|
||
---
|
||
|
||
## Why Playwright Fits This Stack
|
||
|
||
ResolutionFlow is a good Playwright candidate because:
|
||
|
||
- the frontend is a browser-heavy SPA
|
||
- route transitions and auth flows matter a lot
|
||
- many important regressions are UI integration issues, not backend unit issues
|
||
- CI already exists, so there is a natural place to add an e2e job
|
||
|
||
---
|
||
|
||
## Recommended Phase 1 Scope
|
||
|
||
Start with the least brittle, highest-signal journeys.
|
||
|
||
### Phase 1 tests
|
||
|
||
1. **Login smoke test**
|
||
- visit `/login`
|
||
- sign in with seeded test user
|
||
- verify redirect into authenticated app
|
||
|
||
2. **Authenticated shell loads**
|
||
- verify sidebar/nav renders
|
||
- verify key route content appears
|
||
|
||
3. **Session history page loads**
|
||
- navigate to `/sessions`
|
||
- verify tabs or session history shell renders
|
||
|
||
4. **Account settings save flow**
|
||
- navigate to `/account/profile` or `/account`
|
||
- edit a safe field if possible
|
||
- verify success toast/message
|
||
|
||
5. **Feedback form flow**
|
||
- navigate to `/feedback`
|
||
- submit a simple feedback entry
|
||
- verify success state
|
||
|
||
6. **Shared session public page**
|
||
- only if a reliable fixture exists
|
||
- otherwise defer to phase 2
|
||
|
||
### Avoid in Phase 1
|
||
|
||
- AI chat assertions
|
||
- Monaco-heavy editor interactions
|
||
- drag-and-drop editor behavior
|
||
- cross-reference graph assertions
|
||
- timing-sensitive maintenance flows
|
||
|
||
Those are better once the test harness is stable.
|
||
|
||
---
|
||
|
||
## Test User Strategy
|
||
|
||
Use your existing seeded local users from [seed_test_users.py](/home/michaelchihlas/dev/patherly/backend/scripts/seed_test_users.py).
|
||
|
||
### Existing seeded accounts
|
||
|
||
- `admin@resolutionflow.example.com`
|
||
- `pro@resolutionflow.example.com`
|
||
- `teamadmin@resolutionflow.example.com`
|
||
- `engineer@resolutionflow.example.com`
|
||
|
||
### Shared password
|
||
|
||
- `TestPass123!`
|
||
|
||
### Recommended test account for phase 1
|
||
|
||
Use `teamadmin@resolutionflow.example.com` for most authenticated tests.
|
||
|
||
Why:
|
||
- broad enough permissions
|
||
- less risky than binding all tests to super admin
|
||
- closer to realistic team usage
|
||
|
||
---
|
||
|
||
## How To Implement Playwright
|
||
|
||
## 1. Add dependencies
|
||
|
||
From `frontend/`:
|
||
|
||
```bash
|
||
npm install -D @playwright/test
|
||
npx playwright install chromium
|
||
```
|
||
|
||
Optional later:
|
||
|
||
```bash
|
||
npx playwright install
|
||
```
|
||
|
||
That installs Firefox/WebKit too, but Chromium is the right starting point.
|
||
|
||
---
|
||
|
||
## 2. Add package scripts
|
||
|
||
Add these scripts to [frontend/package.json](/home/michaelchihlas/dev/patherly/frontend/package.json):
|
||
|
||
```json
|
||
{
|
||
"scripts": {
|
||
"test:e2e": "playwright test",
|
||
"test:e2e:ui": "playwright test --ui",
|
||
"test:e2e:headed": "playwright test --headed",
|
||
"test:e2e:debug": "playwright test --debug"
|
||
}
|
||
}
|
||
```
|
||
|
||
---
|
||
|
||
## 3. Add Playwright config
|
||
|
||
Create [frontend/playwright.config.ts](/home/michaelchihlas/dev/patherly/frontend/playwright.config.ts).
|
||
|
||
Recommended shape:
|
||
|
||
```ts
|
||
import { defineConfig, devices } from '@playwright/test'
|
||
|
||
export default defineConfig({
|
||
testDir: './e2e',
|
||
fullyParallel: true,
|
||
forbidOnly: !!process.env.CI,
|
||
retries: process.env.CI ? 2 : 0,
|
||
workers: process.env.CI ? 2 : undefined,
|
||
reporter: [['html'], ['list']],
|
||
use: {
|
||
baseURL: process.env.PLAYWRIGHT_BASE_URL || 'http://127.0.0.1:4173',
|
||
trace: 'on-first-retry',
|
||
screenshot: 'only-on-failure',
|
||
video: 'retain-on-failure',
|
||
},
|
||
webServer: {
|
||
command: 'npm run preview -- --host 127.0.0.1 --port 4173',
|
||
port: 4173,
|
||
reuseExistingServer: !process.env.CI,
|
||
timeout: 120_000,
|
||
},
|
||
projects: [
|
||
{
|
||
name: 'chromium',
|
||
use: { ...devices['Desktop Chrome'] },
|
||
},
|
||
],
|
||
})
|
||
```
|
||
|
||
### Why `vite preview` instead of `vite dev`
|
||
|
||
Use the built app in e2e so tests are closer to production behavior and less vulnerable to dev-server quirks.
|
||
|
||
---
|
||
|
||
## 4. Add an e2e folder structure
|
||
|
||
Recommended:
|
||
|
||
```text
|
||
frontend/
|
||
e2e/
|
||
auth.spec.ts
|
||
navigation.spec.ts
|
||
feedback.spec.ts
|
||
fixtures/
|
||
auth.ts
|
||
utils/
|
||
session.ts
|
||
```
|
||
|
||
Keep helpers small. Avoid building a giant abstraction layer too early.
|
||
|
||
---
|
||
|
||
## 5. Add a login helper
|
||
|
||
Because the app stores tokens in `localStorage`, there are two valid strategies:
|
||
|
||
### Option A: Log in through the UI
|
||
Best for the first smoke test.
|
||
|
||
Pros:
|
||
- verifies the real login flow
|
||
- simple to understand
|
||
|
||
Cons:
|
||
- slower when repeated across many specs
|
||
|
||
### Option B: Log in through the API and set storage state
|
||
Best after the first smoke test works.
|
||
|
||
Pros:
|
||
- much faster
|
||
- reduces duplicated login steps across tests
|
||
|
||
Cons:
|
||
- does not itself verify the login form UI
|
||
|
||
### Recommended approach
|
||
|
||
- keep **one** UI login spec
|
||
- use **API login + saved storage state** for the rest
|
||
|
||
Because the backend already supports `POST /api/v1/auth/login/json`, Playwright can authenticate directly.
|
||
|
||
Example shape:
|
||
|
||
```ts
|
||
import { request, expect } from '@playwright/test'
|
||
|
||
export async function loginViaApi(baseApiUrl: string) {
|
||
const api = await request.newContext()
|
||
const response = await api.post(`${baseApiUrl}/api/v1/auth/login/json`, {
|
||
data: {
|
||
email: 'teamadmin@resolutionflow.example.com',
|
||
password: 'TestPass123!',
|
||
},
|
||
})
|
||
|
||
expect(response.ok()).toBeTruthy()
|
||
return response.json()
|
||
}
|
||
```
|
||
|
||
Then inject `access_token` and `refresh_token` into localStorage before page load.
|
||
|
||
---
|
||
|
||
## 6. Make selectors stable
|
||
|
||
Playwright is easiest to maintain when the UI exposes stable selectors.
|
||
|
||
The current UI already has some good `aria-label` coverage, which is enough for many tests. Where a flow is critical or copy is likely to change, add `data-testid`.
|
||
|
||
### Recommended `data-testid` targets
|
||
|
||
- login form
|
||
- login submit button
|
||
- app sidebar
|
||
- session history page shell
|
||
- feedback form
|
||
- save buttons on important settings pages
|
||
|
||
### Rule of thumb
|
||
|
||
- prefer `getByRole()` and `getByLabel()` first
|
||
- add `data-testid` for high-value flows where text is decorative or likely to change
|
||
|
||
---
|
||
|
||
## 7. Seed data before e2e runs
|
||
|
||
Phase 1 should not depend on manually-created accounts.
|
||
|
||
Recommended flow:
|
||
|
||
1. start Postgres
|
||
2. run backend migrations
|
||
3. run `python -m scripts.seed_test_users`
|
||
4. start backend
|
||
5. start frontend preview server
|
||
6. run Playwright
|
||
|
||
If later tests need trees, add a second seed step for flows:
|
||
|
||
```bash
|
||
python -m scripts.seed_trees
|
||
python -m scripts.seed_trees_v2
|
||
python -m scripts.seed_procedural_flows
|
||
```
|
||
|
||
For the very first phase, user-seeding alone is enough if tests stay focused on auth, navigation, feedback, and settings.
|
||
|
||
---
|
||
|
||
## 8. Add initial smoke specs
|
||
|
||
### `auth.spec.ts`
|
||
|
||
Covers:
|
||
- login page loads
|
||
- valid login succeeds
|
||
- invalid login shows error
|
||
|
||
### `navigation.spec.ts`
|
||
|
||
Covers:
|
||
- authenticated app shell renders
|
||
- `/sessions` loads
|
||
- `/feedback` loads
|
||
- `/account` loads
|
||
|
||
### `feedback.spec.ts`
|
||
|
||
Covers:
|
||
- feedback form submit
|
||
- success state visible
|
||
|
||
Keep these small. One assertion-heavy mega-test is worse than a few short focused tests.
|
||
|
||
---
|
||
|
||
## 9. Add Playwright to CI
|
||
|
||
Your existing CI workflow is already in [.github/workflows/ci.yml](/home/michaelchihlas/dev/patherly/.github/workflows/ci.yml). Add a separate `e2e` job instead of mixing Playwright into the existing frontend unit-test job.
|
||
|
||
### Recommended CI job shape
|
||
|
||
1. checkout
|
||
2. set up Python
|
||
3. set up Node
|
||
4. start Postgres service
|
||
5. install backend dependencies
|
||
6. install frontend dependencies
|
||
7. run migrations
|
||
8. seed test users
|
||
9. start backend in background
|
||
10. build frontend
|
||
11. install Playwright browser
|
||
12. run Playwright against `vite preview`
|
||
13. upload Playwright report/artifacts on failure
|
||
|
||
### Important detail
|
||
|
||
Set `VITE_API_URL=http://127.0.0.1:8000` for the frontend build used in CI e2e.
|
||
|
||
---
|
||
|
||
## Suggested CI Commands
|
||
|
||
Backend:
|
||
|
||
```bash
|
||
cd backend
|
||
alembic upgrade head
|
||
python -m scripts.seed_test_users
|
||
uvicorn app.main:app --host 127.0.0.1 --port 8000 &
|
||
```
|
||
|
||
Frontend:
|
||
|
||
```bash
|
||
cd frontend
|
||
npm ci
|
||
npm run build
|
||
npx playwright install --with-deps chromium
|
||
npm run test:e2e
|
||
```
|
||
|
||
Use environment variables:
|
||
|
||
```bash
|
||
VITE_API_URL=http://127.0.0.1:8000
|
||
PLAYWRIGHT_BASE_URL=http://127.0.0.1:4173
|
||
```
|
||
|
||
---
|
||
|
||
## Phase 2 Expansion
|
||
|
||
Once the smoke suite is stable, expand into actual business-critical flows.
|
||
|
||
### Phase 2 candidates
|
||
|
||
1. Start and resume a session
|
||
2. Export a session
|
||
3. Create a share link
|
||
4. Open analytics pages
|
||
5. Validate account integrations page behavior
|
||
|
||
### Phase 2.5 candidates
|
||
|
||
1. Tree library filters
|
||
2. Fork flow flow
|
||
3. Step library browse/search
|
||
4. Public shared session experience
|
||
|
||
### Phase 3 candidates
|
||
|
||
1. Editor workflows
|
||
2. Procedural runner
|
||
3. Drag-and-drop interactions
|
||
4. AI-assisted workflows
|
||
|
||
Only bring editors and AI into Playwright once the harness is already trustworthy.
|
||
|
||
---
|
||
|
||
## Practical Advice For This Repo
|
||
|
||
### Keep Playwright separate from Vitest
|
||
|
||
Vitest should stay for:
|
||
- small component logic
|
||
- hooks
|
||
- utilities
|
||
- API client logic
|
||
|
||
Playwright should cover:
|
||
- auth
|
||
- routing
|
||
- critical user journeys
|
||
- integration behavior
|
||
|
||
### Don’t try to test everything
|
||
|
||
You do not need Playwright coverage for every page. Cover the flows that:
|
||
|
||
- affect demos
|
||
- affect activation
|
||
- affect trust
|
||
- are expensive to break
|
||
|
||
### Start with one browser
|
||
|
||
Chromium first.
|
||
|
||
Only add Firefox/WebKit after the suite is stable and worth the extra runtime.
|
||
|
||
### Prefer reliable fixture creation over brittle UI setup
|
||
|
||
Use backend seeds and API helpers whenever possible.
|
||
|
||
---
|
||
|
||
## Recommended First PR For Playwright
|
||
|
||
Keep the first implementation intentionally small.
|
||
|
||
### Include
|
||
|
||
1. `@playwright/test` dependency
|
||
2. `playwright.config.ts`
|
||
3. e2e scripts in `package.json`
|
||
4. one UI login smoke test
|
||
5. one authenticated navigation smoke test
|
||
6. CI e2e job
|
||
|
||
### Do not include yet
|
||
|
||
- editor drag-and-drop tests
|
||
- AI flow tests
|
||
- PDF validation
|
||
- multi-browser matrix
|
||
- large helper framework
|
||
|
||
That first PR should prove the harness works end to end.
|
||
|
||
---
|
||
|
||
## Final Recommendation
|
||
|
||
If only one quality investment gets prioritized right now, it should be:
|
||
|
||
**Playwright + product analytics together**
|
||
|
||
Why:
|
||
|
||
- Playwright improves confidence in shipping
|
||
- analytics improves confidence in prioritizing
|
||
|
||
That combination is one of the cleanest ways to make ResolutionFlow feel more professional both internally and externally.
|