Files
roa2web-service-auto/features/phases/phase-1-forms.md
Marius Mutu bff37e78d8 docs(css): Add comprehensive CSS refactoring plan and documentation
Add complete planning documentation for CSS architecture refactoring project:
- 7-phase implementation plan (92-120 hours)
- 123 detailed tasks across all phases
- Target: ~3,260 lines CSS reduction (40-50%)
- Complete requirements analysis
- Progress tracking system
- Phase-by-phase breakdown with acceptance criteria

Documentation structure:
- features/README.md - Project overview and quick start
- features/CSS_REFACTORING_PLAN.md - Implementation strategy
- features/CSS_REFACTORING_REQUIREMENTS.md - Detailed requirements
- features/PROGRESS_TRACKER.md - Live progress tracking
- features/phases/*.md - 7 phase documents with tasks

Ready to begin Phase 1: Forms Standardization

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude <noreply@anthropic.com>
2025-11-18 13:10:57 +02:00

17 KiB

Phase 1: Standardizare Formulare

Priority: 🔥 High (User-facing impact) Duration: 10-12 hours Status: ⏸️ Not Started Risk Level: Medium


Obiective

  1. Elimină pattern-uri inconsistente - 3 pattern-uri diferite → 1 standard
  2. Utilizează forms.css existent - 460 linii de sistem complet
  3. Șterge CSS duplicat - ~150 linii eliminate
  4. Crează template - Pentru formulare viitoare

Situație Actuală

Problem Statement

Fiecare view reinventează formulare-le diferit:

View Field Wrapper Label Class Lines CSS Status
LoginView.vue .field .field-label 70 lines Custom
InvoicesView.vue .filter-group .filter-label 80 lines Custom
forms.css .form-group .form-label 460 lines Standard NEUTILIZAT

Impact

  • User experience inconsistent
  • Duplicate code maintenance
  • forms.css (460 linii) este neutilizat
  • Hardcoded PrimeVue overrides cu !important

Task Breakdown (18 tasks)

1. Setup & Preparation (3 tasks)

Task 1.1: Create Feature Branch

Status: ⏸️ Not Started | Est: 5 min

# Create and switch to feature branch
git checkout -b feature/css-refactoring

# Verify clean state
git status

Acceptance Criteria:

  • Branch created: feature/css-refactoring
  • No uncommitted changes
  • Pushed to remote

Task 1.2: Capture Playwright Baseline Snapshots

Status: ⏸️ Not Started | Est: 15 min

cd reports-app/frontend

# Capture baseline screenshots before any changes
npm run test:e2e -- --update-snapshots

# Verify snapshots created
ls -la tests/e2e/**/*.png

Snapshots to Capture:

  • Login page (desktop, tablet, mobile)
  • Dashboard page
  • Invoices page
  • All form states (empty, filled, error, valid)

Acceptance Criteria:

  • Baseline snapshots captured for all views
  • Snapshots committed to git
  • Test suite passes with snapshots

Task 1.3: Review Existing forms.css

Status: ⏸️ Not Started | Est: 30 min

File: reports-app/frontend/src/assets/css/components/forms.css

Review:

  • Read all 460 lines
  • Document available classes:
    • .form - Form container
    • .form-group - Field wrapper
    • .form-label - Label styling
    • .form-input - Input styling
    • .form-row - Horizontal layout
    • .form-error - Error message
    • .form-help - Help text
  • Note validation states: .valid, .invalid
  • Understand responsive behavior

Acceptance Criteria:

  • All available classes documented
  • Pattern examples identified
  • Ready to apply to components

2. LoginView.vue Refactoring (6 tasks)

File: reports-app/frontend/src/views/LoginView.vue

Task 2.1: Update Template - Field Wrapper

Status: ⏸️ Not Started | Est: 20 min

Current (lines 95-106):

<div class="field">
  <label for="username" class="field-label">Utilizator</label>
  <InputText
    id="username"
    v-model="credentials.username"
    placeholder="Introduceți numele de utilizator"
    :class="{ 'p-invalid': formErrors.username }"
    class="w-full"
  />
</div>

Updated:

<div class="form-group">
  <label for="username" class="form-label required">Utilizator</label>
  <InputText
    id="username"
    v-model="credentials.username"
    placeholder="Introduceți numele de utilizator"
    :class="{ 'invalid': formErrors.username }"
    class="form-input w-full"
  />
  <span v-if="formErrors.username" class="form-error">
    {{ formErrors.username }}
  </span>
</div>

Changes:

  • .field.form-group
  • .field-label.form-label (with .required for required fields)
  • p-invalidinvalid (forms.css class)
  • Add .form-input to InputText
  • Add .form-error for error messages

Acceptance Criteria:

  • All form fields updated
  • Error messages use .form-error
  • No custom field wrapper classes

Task 2.2: Update Template - Password Field

Status: ⏸️ Not Started | Est: 15 min

Current:

<div class="field">
  <label for="password" class="field-label">Parolă</label>
  <Password
    id="password"
    v-model="credentials.password"
    :feedback="false"
    toggleMask
  />
</div>

Updated:

<div class="form-group">
  <label for="password" class="form-label required">Parolă</label>
  <Password
    id="password"
    v-model="credentials.password"
    :feedback="false"
    toggleMask
    :class="{ 'invalid': formErrors.password }"
    class="w-full"
  />
  <span v-if="formErrors.password" class="form-error">
    {{ formErrors.password }}
  </span>
</div>

Acceptance Criteria:

  • Password field uses .form-group
  • Label uses .form-label required
  • Error handling consistent

Task 2.3: Remove Custom Form CSS

Status: ⏸️ Not Started | Est: 10 min

Delete Lines 234-243:

/* DELETE THIS - forms.css provides these */
.field {
  margin-bottom: 1.5rem;
}

.field-label {
  display: block;
  margin-bottom: 0.5rem;
  font-weight: 600;
  color: var(--text-color);
}

Acceptance Criteria:

  • Lines 234-243 deleted
  • No .field or .field-label in scoped styles
  • Form still renders correctly

Task 2.4: Remove PrimeVue Deep Overrides

Status: ⏸️ Not Started | Est: 15 min

Delete Lines 269-288:

/* DELETE THIS - Will be moved to global primevue-overrides.css in Phase 3 */
:deep(.p-inputtext),
:deep(.p-password input) {
  border: 2px solid #e5e7eb !important;
  padding: 12px !important;
  font-size: 16px !important;
  transition: all 0.3s ease !important;
  border-radius: 8px !important;
}

:deep(.p-inputtext:focus),
:deep(.p-password input:focus) {
  border-color: #3b82f6 !important;
  box-shadow: 0 0 0 3px rgba(59, 130, 246, 0.1) !important;
  outline: none !important;
}

/* ... more :deep() rules ... */

Note: These will be added to global primevue-overrides.css in Phase 3.

Acceptance Criteria:

  • All :deep() rules removed from LoginView.vue
  • No !important in scoped styles
  • Form inputs still styled (via forms.css)

Task 2.5: Test Login Functionality

Status: ⏸️ Not Started | Est: 30 min

Test Checklist:

  • Login form renders correctly
  • All fields are accessible
  • Validation works on blur
  • Error messages display correctly
  • Form submission works
  • Success login redirects to dashboard
  • Failed login shows error
  • Keyboard navigation works (Tab through fields)
  • Enter key submits form

Test Scenarios:

  1. Empty form submission → validation errors
  2. Invalid credentials → API error message
  3. Valid credentials → successful login
  4. Field focus states visible
  5. Error states visible

Acceptance Criteria:

  • All test scenarios pass
  • No functionality broken
  • No console errors

Task 2.6: Visual Regression Test

Status: ⏸️ Not Started | Est: 15 min

# Run Playwright tests
npm run test:e2e -- tests/e2e/auth/login.spec.ts

# Check for visual differences
npm run test:e2e:report

Visual Checks:

  • Login form layout identical
  • Field spacing correct
  • Label styling identical
  • Error message styling identical
  • Button styling unchanged
  • Responsive layout works (mobile, tablet)

Acceptance Criteria:

  • Playwright tests pass
  • No unexpected visual differences
  • Any differences documented and approved

3. InvoicesView.vue Refactoring (5 tasks)

File: reports-app/frontend/src/views/InvoicesView.vue

Task 3.1: Update Template - Filter Groups

Status: ⏸️ Not Started | Est: 30 min

Current (lines 45-60):

<div class="filters-container">
  <div class="filters-row">
    <div class="filter-group">
      <label class="filter-label">Tip Factură</label>
      <Dropdown
        v-model="filters.type"
        :options="invoiceTypes"
        option-label="label"
        option-value="value"
        placeholder="Tip factură"
        @change="handleFilterChange"
      />
    </div>
  </div>
</div>

Updated:

<div class="form">
  <div class="form-row">
    <div class="form-col">
      <div class="form-group">
        <label class="form-label">Tip Factură</label>
        <Dropdown
          v-model="filters.type"
          :options="invoiceTypes"
          option-label="label"
          option-value="value"
          placeholder="Tip factură"
          @change="handleFilterChange"
          class="w-full"
        />
      </div>
    </div>
  </div>
</div>

Changes:

  • .filters-container.form
  • .filters-row.form-row
  • .filter-group.form-group (inside .form-col)
  • .filter-label.form-label

Acceptance Criteria:

  • All filter fields updated
  • Grid layout preserved (form-row + form-col)
  • No custom filter classes

Task 3.2: Update Date Range Filters

Status: ⏸️ Not Started | Est: 20 min

Current:

<div class="filter-group">
  <label class="filter-label">De la</label>
  <Calendar
    v-model="filters.dateFrom"
    dateFormat="dd/mm/yy"
    placeholder="Data început"
  />
</div>
<div class="filter-group">
  <label class="filter-label">Până la</label>
  <Calendar
    v-model="filters.dateTo"
    dateFormat="dd/mm/yy"
    placeholder="Data sfârșit"
  />
</div>

Updated:

<div class="form-col">
  <div class="form-group">
    <label class="form-label">De la</label>
    <Calendar
      v-model="filters.dateFrom"
      dateFormat="dd/mm/yy"
      placeholder="Data început"
      class="w-full"
    />
  </div>
</div>
<div class="form-col">
  <div class="form-group">
    <label class="form-label">Până la</label>
    <Calendar
      v-model="filters.dateTo"
      dateFormat="dd/mm/yy"
      placeholder="Data sfârșit"
      class="w-full"
    />
  </div>
</div>

Acceptance Criteria:

  • Date pickers use standard form classes
  • Side-by-side layout preserved
  • Calendar styling works

Task 3.3: Remove Custom Filter CSS

Status: ⏸️ Not Started | Est: 15 min

Delete Lines 545-578:

/* DELETE THIS */
.filters-container {
  padding: 1rem;
}

.filters-row {
  display: grid;
  grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
  gap: 1rem;
  margin-bottom: 1rem;
}

.filter-group {
  display: flex;
  flex-direction: column;
  gap: 0.5rem;
}

.filter-label {
  font-size: 0.875rem;
  font-weight: 600;
  color: var(--text-color);
}

Note: forms.css provides .form-row with grid layout.

Acceptance Criteria:

  • Custom filter CSS deleted
  • Form layout still correct via forms.css
  • Grid behavior preserved

Task 3.4: Remove Filter-Specific Overrides

Status: ⏸️ Not Started | Est: 10 min

Find and remove any filter-specific PrimeVue overrides:

# Search for filter-related :deep() in InvoicesView.vue
grep -n ":deep" reports-app/frontend/src/views/InvoicesView.vue

Remove any found overrides (will be centralized in Phase 3).

Acceptance Criteria:

  • No :deep() for filter components
  • No hardcoded filter styling

Task 3.5: Visual Regression Test

Status: ⏸️ Not Started | Est: 20 min

# Run invoice tests
npm run test:e2e -- tests/e2e/invoices/

# Check snapshots
npm run test:e2e:report

Visual Checks:

  • Filter card layout identical
  • Filter field alignment correct
  • Grid layout responsive
  • Date pickers styled correctly
  • Dropdown styling correct

Functional Checks:

  • All filters work
  • Filter changes trigger data reload
  • Clear filters works
  • Filter combinations work

Acceptance Criteria:

  • Playwright tests pass
  • No visual regressions
  • All filters functional

4. Testing & Validation (3 tasks)

Task 4.1: Playwright Snapshot Comparison

Status: ⏸️ Not Started | Est: 30 min

# Run full test suite
npm run test:e2e

# Generate report
npm run test:e2e:report

# Open report
npx playwright show-report

Compare:

  • Login page (desktop, tablet, mobile)
  • Invoices filter section
  • All form states (empty, filled, error, valid)

Document any differences:

  • Expected differences: None (should be pixel-perfect)
  • Acceptable differences: Font rendering variations
  • Unacceptable differences: Layout shifts, color changes, missing elements

Acceptance Criteria:

  • All visual regression tests pass
  • Any differences documented and approved
  • Screenshots archived

Task 4.2: Manual Testing All Breakpoints

Status: ⏸️ Not Started | Est: 45 min

Desktop Testing (1920x1080):

  • Login form centered and styled
  • Invoice filters in grid layout
  • All fields accessible
  • Hover states work
  • Focus states visible

Tablet Testing (768x1024):

  • Login form responsive
  • Filter grid adapts to tablet
  • Touch targets adequate (min 44px)
  • No horizontal scroll

Mobile Testing (375x667):

  • Login form full-width
  • Filters stack vertically
  • Font size 16px (no zoom on iOS)
  • Virtual keyboard doesn't break layout

Acceptance Criteria:

  • All breakpoints tested
  • Forms responsive on all devices
  • No layout breaks

Task 4.3: Browser Compatibility Check

Status: ⏸️ Not Started | Est: 30 min

Test on:

  • Chrome (latest) - Primary browser
  • Firefox (latest)
  • Safari (latest) - macOS/iOS
  • Edge (latest)

Check:

  • Form layout identical
  • CSS variables supported
  • Flexbox/Grid working
  • Focus outlines visible
  • No console errors

Acceptance Criteria:

  • Forms work on all browsers
  • Visual consistency across browsers
  • No JavaScript errors

5. Documentation (1 task)

Task 5.1: Create Form Template Documentation

Status: ⏸️ Not Started | Est: 1 hour

Create: docs/FORM_TEMPLATE.md

Content:

  1. Standard form structure
  2. Field types (text, password, dropdown, date)
  3. Validation pattern
  4. Error handling
  5. Responsive layout
  6. Accessibility guidelines

Template Example:

<template>
  <form @submit.prevent="handleSubmit" class="form">
    <!-- Single field -->
    <div class="form-group">
      <label for="field" class="form-label required">Label</label>
      <input
        id="field"
        v-model="formData.field"
        type="text"
        class="form-input"
        :class="{ 'invalid': errors.field }"
      />
      <span v-if="errors.field" class="form-error">
        {{ errors.field }}
      </span>
    </div>

    <!-- Horizontal fields -->
    <div class="form-row">
      <div class="form-col">
        <!-- Field 1 -->
      </div>
      <div class="form-col">
        <!-- Field 2 -->
      </div>
    </div>

    <!-- Form actions -->
    <div class="form-actions">
      <button type="submit" class="btn btn-primary">
        Submit
      </button>
    </div>
  </form>
</template>

Acceptance Criteria:

  • Template documented with examples
  • All field types covered
  • Validation pattern explained
  • Accessibility notes included

Completion Criteria

Code Quality

  • Zero custom form wrapper classes (.field, .filter-group)
  • All forms use .form-group + .form-label
  • No :deep() PrimeVue overrides in components
  • ~150 lines of CSS eliminated

Functionality

  • Login works identically
  • Invoice filters work identically
  • All validation works
  • No console errors

Testing

  • Playwright visual regression tests pass
  • Manual testing complete (all breakpoints)
  • Browser compatibility verified

Documentation

  • Form template created
  • Pattern documented

Files Modified

  1. reports-app/frontend/src/views/LoginView.vue

    • Template: Updated field wrappers and labels
    • CSS: Deleted lines 234-243, 269-288 (~90 lines)
  2. reports-app/frontend/src/views/InvoicesView.vue

    • Template: Updated filter structure
    • CSS: Deleted lines 545-578 (~80 lines)
  3. docs/FORM_TEMPLATE.md (new file)

    • Standard form template and guidelines

Total: 2 files modified, 1 file created, ~150 lines deleted


Commit Message

feat(css): Phase 1 - Standardize form patterns across views

BREAKING: None (visual changes only, no API changes)

Changes:
- Standardize LoginView.vue to use forms.css patterns
- Standardize InvoicesView.vue filter forms
- Remove ~150 lines of duplicate form CSS
- Eliminate custom form wrapper classes
- Create standard form template documentation

Impact:
- Consistent form UX across application
- Reduced CSS duplication (70% → 65%)
- Cleaner component code
- forms.css (460 lines) now utilized

Testing:
- ✅ Playwright visual regression tests pass
- ✅ Manual testing on desktop/tablet/mobile
- ✅ Browser compatibility verified (Chrome/Firefox/Safari/Edge)
- ✅ All form functionality preserved

Files:
- Modified: LoginView.vue, InvoicesView.vue
- Created: docs/FORM_TEMPLATE.md
- CSS eliminated: ~150 lines

Refs: #CSS-REFACTORING Phase 1/7

Next Phase

Phase 2: Fundație Pattern-uri Globale


Created: 2025-11-18 Last Updated: 2025-11-18 Status: ⏸️ Awaiting Start