File size: 7,544 Bytes
cc036ff
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
# Test ID Implementation Guide for Cross-Platform E2E Tests

## Overview

This document explains how to add `data-testid` attributes to frontend components for cross-platform E2E testing. The test ID constants are defined in `frontend-nextjs/src/lib/testIds.ts`.

## Why Test IDs?

**Problem**: CSS selectors (classes, IDs) are fragile and break when styling changes.
**Solution**: Use `data-testid` attributes that are stable and only used for testing.

## Cross-Platform Consistency

- **Web (Next.js)**: Uses `data-testid="..."` attributes
- **Mobile (React Native)**: Uses `testID="..."` props (same values)
- **Desktop (Tauri)**: Uses `data-testid="..."` attributes (same values)

This ensures E2E tests can use the same selectors across all platforms.

## Test ID Constants File

**Location**: `frontend-nextjs/src/lib/testIds.ts`

This file exports all test ID constants to avoid typos and ensure consistency.

### Usage Example

```tsx

import { TEST_IDS } from '@/lib/testIds';



// In your component

<input

  data-testid={TEST_IDS.AGENT_CHAT.INPUT}

  type="text"

  placeholder="Type a message..."

/>



<button data-testid={TEST_IDS.AGENT_CHAT.SEND_BUTTON}>

  Send

</button>

```

## Required Test IDs by Component

### 1. Agent Chat Components

**File**: `frontend-nextjs/pages/chat/index.tsx` or equivalent

Required test IDs:
- `agent-chat-input`: Message input field
- `send-message-button`: Send button
- `agent-response`: Agent response container
- `streaming-indicator`: Loading indicator during streaming
- `history-button`: Toggle history sidebar
- `execution-history-list`: History list container
- `history-item-{index}`: Individual history items

### 2. Canvas Components

**File**: `frontend-nextjs/components/canvas/CanvasContainer.tsx` or equivalent

Required test IDs:
- `canvas-container`: Main canvas container
- `canvas-type-{type}`: Canvas type-specific container (generic, docs, email, sheets, orchestration, terminal, coding)
- `close-canvas-button`: Close button

### 3. Authentication Components

**File**: `frontend-nextjs/pages/login.tsx` or equivalent

Required test IDs:
- `login-email-input`: Email input field
- `login-password-input`: Password input field
- `login-submit-button`: Login button
- `login-error-message`: Error message
- `logout-button`: Logout button

### 4. Form Components

**File**: Any form component (canvas forms, settings forms, etc.)

Required test IDs:
- `form-field-{name}`: Form field (use field name as suffix)
- `form-submit-button`: Submit button
- `form-success-message`: Success message

### 5. Skills Components

**File**: `frontend-nextjs/pages/marketplace.tsx` or equivalent

Required test IDs:
- `skills-marketplace-list`: Skills list
- `skill-install-button`: Install button
- `skill-execute-button`: Execute button
- `skill-output`: Output container

### 6. Settings Components

**File**: `frontend-nextjs/pages/settings/index.tsx` or equivalent

Required test IDs:
- `settings-theme-toggle`: Theme toggle
- `settings-notifications-toggle`: Notifications toggle
- `settings-preferences`: Preferences section

## Implementation Checklist

### Phase 1: Web Components (Current)
- [ ] Add data-testid to agent chat page (`pages/chat/index.tsx`)
- [ ] Add data-testid to canvas components (`components/canvas/`)
- [ ] Add data-testid to login page (`pages/login.tsx`)
- [ ] Add data-testid to skills marketplace (`pages/marketplace.tsx`)
- [ ] Add data-testid to settings page (`pages/settings/index.tsx`)

### Phase 2: Mobile Components (React Native)
- [ ] Create `mobile/src/constants/testIds.ts` with same values
- [ ] Add testID props to mobile AgentChatScreen
- [ ] Add testID props to mobile CanvasScreen
- [ ] Add testID props to mobile LoginScreen

### Phase 3: Desktop Components (Tauri)
- [ ] Ensure Tauri components use same data-testid values
- [ ] Verify tauri-driver can access data-testid attributes

## Example Implementation

### Before (Fragile)

```tsx

// ❌ Bad: Breaks if CSS classes change

<input className="chat-input w-full px-4 py-2" />

<button className="bg-blue-500 text-white">Send</button>

```

### After (Resilient)

```tsx

// ✅ Good: Stable test selectors

import { TEST_IDS } from '@/lib/testIds';



<input

  data-testid={TEST_IDS.AGENT_CHAT.INPUT}

  className="chat-input w-full px-4 py-2"

/>

<button

  data-testid={TEST_IDS.AGENT_CHAT.SEND_BUTTON}

  className="bg-blue-500 text-white"

>

  Send

</button>

```

## Testing Your Implementation

After adding test IDs, verify they exist in the DOM:

1. Start dev server: `cd frontend-nextjs && npm run dev`
2. Open browser DevTools (F12)
3. Go to Elements tab
4. Use search (Ctrl+F) for `data-testid`
5. Verify all expected test IDs are present

```bash

# Run E2E tests to verify selectors work

cd backend/tests/e2e_ui

pytest tests/cross-platform/test_shared_workflows.py -v

```

## JSDoc Documentation

Add JSDoc comments to components that use test IDs:

```tsx

/**

 * Agent Chat Input Component

 *

 * **data-testid attributes used by E2E tests - do not remove without updating test plans**

 * - agent-chat-input: Main input field

 * - send-message-button: Send button

 */

export function AgentChatInput() {

  // ...

}

```

## Migration Path

If you encounter existing components without test IDs:

1. **Import test ID constants**:
   ```tsx

   import { TEST_IDS } from '@/lib/testIds';

   ```

2. **Add data-testid to key interactive elements**:
   - Inputs, buttons, links
   - Containers, lists, grids
   - Modals, popovers, dropdowns

3. **Run E2E tests to verify**:
   ```bash

   pytest backend/tests/e2e_ui/tests/cross-platform/ -v

   ```

4. **Document in component JSDoc** (see above)

## Troubleshooting

### E2E tests can't find elements

**Problem**: `Locator.click: Target closed` or `TimeoutError`
**Solution**:
1. Verify data-testid is spelled correctly
2. Check browser DevTools to confirm element exists
3. Ensure element is visible (not hidden by CSS)
4. Check for dynamic IDs (use data-testid instead)

### Tests work locally but fail in CI

**Problem**: Flaky tests in CI environment
**Solution**:
1. Ensure data-testid values are constants (not generated)
2. Avoid using index-based selectors (e.g., `li:nth-child(3)`)
3. Use explicit waits: `await page.waitForSelector('[data-testid="..."]')`

### Mobile testID props not working

**Problem**: React Native testID not found by Detox
**Solution**:
1. Verify `testID` prop (not `data-testid`) for React Native
2. Check mobile/constants/testIds.ts exports match web values
3. Ensure component is rendered (not conditionally hidden)

## References

- **Web Tests**: `backend/tests/e2e_ui/tests/cross-platform/test_shared_workflows.py`
- **Test Constants**: `frontend-nextjs/src/lib/testIds.ts`
- **Page Objects**: `backend/tests/e2e_ui/pages/cross_platform_objects.py`
- **Playwright Selectors**: https://playwright.dev/docs/selectors
- **Detox Selectors**: https://wix.github.io/Detox/docs/api/simulation/matchers

## Summary

By following this guide, you ensure that:
1. E2E tests are resilient to styling changes
2. Test selectors are consistent across web, mobile, and desktop
3. Tests are easier to maintain and debug
4. New developers can understand the testing approach

**Remember**: Test IDs are for testing only. Don't use them for CSS styling or JavaScript logic.