757 lines
17 KiB
Markdown
757 lines
17 KiB
Markdown
# 🧪 TurboTrades Testing Guide
|
|
|
|
## Overview
|
|
|
|
This guide covers all testing capabilities in the TurboTrades test client, including WebSocket tests, stress tests, and marketplace API tests.
|
|
|
|
---
|
|
|
|
## 🚀 Quick Start
|
|
|
|
1. **Start the server:**
|
|
```bash
|
|
npm run dev
|
|
```
|
|
|
|
2. **Open the test client:**
|
|
- Open `test-client.html` in your browser
|
|
- Or navigate to: `file:///path/to/TurboTrades/test-client.html`
|
|
- **Note:** CORS is configured to allow `file://` protocol, so the test client works directly from your filesystem
|
|
|
|
3. **Connect to WebSocket:**
|
|
- Leave token field empty for anonymous connection
|
|
- Or paste your JWT token for authenticated connection
|
|
- Click "Connect"
|
|
|
|
---
|
|
|
|
## 📡 WebSocket Tests
|
|
|
|
### Basic Connection Tests
|
|
|
|
#### Anonymous Connection
|
|
```
|
|
1. Leave "Access Token" field empty
|
|
2. Click "Connect"
|
|
3. Expected: ⚠️ WebSocket connection without authentication (public)
|
|
```
|
|
|
|
#### Authenticated Connection
|
|
```
|
|
1. Get access token:
|
|
- Login via http://localhost:3000/auth/steam
|
|
- Extract token from browser cookies
|
|
- Or use /auth/decode-token endpoint
|
|
|
|
2. Paste token in "Access Token" field
|
|
3. Click "Connect"
|
|
4. Expected: ✅ WebSocket authenticated for user: {steamId} ({username})
|
|
5. Expected welcome message:
|
|
{
|
|
"type": "connected",
|
|
"data": {
|
|
"steamId": "76561198012345678",
|
|
"username": "YourName",
|
|
"userId": "...",
|
|
"timestamp": 1234567890000
|
|
}
|
|
}
|
|
```
|
|
|
|
### Message Tests
|
|
|
|
#### Ping/Pong Test
|
|
```
|
|
1. Connect to WebSocket
|
|
2. Click "Send Ping"
|
|
3. Expected response:
|
|
{
|
|
"type": "pong",
|
|
"timestamp": 1234567890000
|
|
}
|
|
```
|
|
|
|
#### Custom Messages
|
|
```
|
|
1. Edit the "JSON Message" field
|
|
2. Examples:
|
|
{"type": "ping"}
|
|
{"type": "custom", "data": {"test": true}}
|
|
3. Click "Send Message"
|
|
4. Check response in Messages section
|
|
```
|
|
|
|
---
|
|
|
|
## 🔥 Socket Stress Tests
|
|
|
|
### Purpose
|
|
Test WebSocket stability, throughput, and error handling under load.
|
|
|
|
### Test Types
|
|
|
|
#### 1. Gradual Stress Test
|
|
**What it does:** Sends messages at a controlled interval.
|
|
|
|
**How to use:**
|
|
```
|
|
1. Set "Number of Messages": 10-1000
|
|
2. Set "Interval (ms)": 100-5000
|
|
3. Click "🚀 Run Stress Test"
|
|
4. Monitor: Test Status and Messages Queued
|
|
5. Click "⏹️ Stop Test" to abort early
|
|
```
|
|
|
|
**Recommended Tests:**
|
|
- **Light Load:** 10 messages @ 500ms interval
|
|
- **Medium Load:** 100 messages @ 100ms interval
|
|
- **Heavy Load:** 500 messages @ 50ms interval
|
|
- **Stress Test:** 1000 messages @ 10ms interval
|
|
|
|
**What to check:**
|
|
- All messages are received
|
|
- Server responds to each message
|
|
- No disconnections occur
|
|
- Message order is preserved
|
|
|
|
#### 2. Burst Test
|
|
**What it does:** Sends 100 messages instantly.
|
|
|
|
**How to use:**
|
|
```
|
|
1. Click "💥 Send Burst (100 msgs)"
|
|
2. 100 messages sent immediately
|
|
3. Check server can handle rapid fire
|
|
```
|
|
|
|
**What to check:**
|
|
- Server doesn't crash
|
|
- WebSocket stays connected
|
|
- Messages are queued properly
|
|
- No memory leaks
|
|
|
|
### Expected Results
|
|
|
|
| Test Type | Messages | Interval | Expected Behavior |
|
|
|-----------|----------|----------|-------------------|
|
|
| Light | 10 | 500ms | All received, no issues |
|
|
| Medium | 100 | 100ms | All received, slight delay |
|
|
| Heavy | 500 | 50ms | All received, noticeable delay |
|
|
| Stress | 1000 | 10ms | May drop some, connection stable |
|
|
| Burst | 100 | 0ms | Queued properly, no crash |
|
|
|
|
### Troubleshooting
|
|
|
|
**If messages are dropped:**
|
|
- Server may have rate limiting enabled
|
|
- Network buffer overflow
|
|
- Expected behavior under extreme stress
|
|
|
|
**If connection closes:**
|
|
- Server timeout
|
|
- Too many messages too fast
|
|
- Check server logs for errors
|
|
|
|
**If browser freezes:**
|
|
- Too many DOM updates
|
|
- Clear messages before large tests
|
|
- Reduce message count
|
|
|
|
---
|
|
|
|
## 🛒 Trade & Marketplace Tests
|
|
|
|
### Prerequisites
|
|
|
|
Most marketplace endpoints require authentication:
|
|
1. Login via Steam: http://localhost:3000/auth/steam
|
|
2. Complete Steam OAuth
|
|
3. Token stored in cookies automatically
|
|
4. Test client uses cookies for API calls
|
|
|
|
### Get Listings Test
|
|
|
|
**Endpoint:** `GET /marketplace/listings`
|
|
|
|
**Access:** Public (authentication optional)
|
|
|
|
**How to test:**
|
|
```
|
|
1. Set filters (optional):
|
|
- Game: All, CS2, or Rust
|
|
- Min Price: e.g., 10.00
|
|
- Max Price: e.g., 100.00
|
|
2. Click "Get Listings"
|
|
3. Check response in Messages section
|
|
```
|
|
|
|
**Expected Response:**
|
|
```json
|
|
{
|
|
"success": true,
|
|
"listings": [
|
|
{
|
|
"id": "listing_123",
|
|
"itemName": "AK-47 | Redline",
|
|
"game": "cs2",
|
|
"price": 45.99,
|
|
"seller": {
|
|
"steamId": "76561198012345678",
|
|
"username": "TraderPro"
|
|
},
|
|
"condition": "Field-Tested",
|
|
"float": 0.23,
|
|
"createdAt": "2024-01-01T00:00:00.000Z"
|
|
}
|
|
],
|
|
"pagination": {
|
|
"page": 1,
|
|
"limit": 20,
|
|
"total": 1,
|
|
"pages": 1
|
|
}
|
|
}
|
|
```
|
|
|
|
**Test Cases:**
|
|
- [ ] Get all listings (no filters)
|
|
- [ ] Filter by game (CS2)
|
|
- [ ] Filter by game (Rust)
|
|
- [ ] Filter by min price
|
|
- [ ] Filter by max price
|
|
- [ ] Combine multiple filters
|
|
|
|
---
|
|
|
|
### Create Listing Test
|
|
|
|
**Endpoint:** `POST /marketplace/listings`
|
|
|
|
**Access:** Authenticated users only
|
|
|
|
**Requirements:**
|
|
- Must be logged in
|
|
- Must have verified email (optional)
|
|
- Must have trade URL set
|
|
|
|
**How to test:**
|
|
```
|
|
1. Login via Steam first
|
|
2. Fill in listing details:
|
|
- Item Name: "AK-47 | Redline"
|
|
- Game: CS2 or Rust
|
|
- Price: 45.99
|
|
- Description: "Minimal wear, great stickers" (optional)
|
|
3. Click "Create Listing (Requires Auth)"
|
|
4. Check response
|
|
```
|
|
|
|
**Expected Response (Success):**
|
|
```json
|
|
{
|
|
"success": true,
|
|
"message": "Listing created successfully",
|
|
"listing": {
|
|
"id": "listing_1234567890123",
|
|
"itemName": "AK-47 | Redline",
|
|
"game": "cs2",
|
|
"price": 45.99,
|
|
"seller": {
|
|
"id": "...",
|
|
"steamId": "76561198012345678",
|
|
"username": "YourName",
|
|
"avatar": "https://..."
|
|
},
|
|
"createdAt": "2024-01-01T00:00:00.000Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Expected WebSocket Broadcast:**
|
|
All connected clients receive:
|
|
```json
|
|
{
|
|
"type": "new_listing",
|
|
"data": {
|
|
"listing": { ... },
|
|
"message": "New CS2 item listed: AK-47 | Redline"
|
|
},
|
|
"timestamp": 1234567890000
|
|
}
|
|
```
|
|
|
|
**Error Cases:**
|
|
- `401 Unauthorized` - Not logged in
|
|
- `403 Forbidden` - Email not verified
|
|
- `400 Validation Error` - Trade URL not set
|
|
- `400 Validation Error` - Missing required fields
|
|
|
|
**Test Cases:**
|
|
- [ ] Create CS2 listing
|
|
- [ ] Create Rust listing
|
|
- [ ] Create with description
|
|
- [ ] Create without description
|
|
- [ ] Create without authentication (should fail)
|
|
- [ ] Create with invalid price (should fail)
|
|
- [ ] Verify WebSocket broadcast received
|
|
|
|
---
|
|
|
|
### Update Listing Price Test
|
|
|
|
**Endpoint:** `PATCH /marketplace/listings/:listingId/price`
|
|
|
|
**Access:** Authenticated seller only
|
|
|
|
**How to test:**
|
|
```
|
|
1. Login via Steam
|
|
2. Create a listing first (or use existing ID)
|
|
3. Fill in:
|
|
- Listing ID: "listing_123"
|
|
- New Price: 39.99
|
|
4. Click "Update Price (Requires Auth)"
|
|
5. Check response
|
|
```
|
|
|
|
**Expected Response (Success):**
|
|
```json
|
|
{
|
|
"success": true,
|
|
"message": "Price updated successfully",
|
|
"listing": {
|
|
"id": "listing_123",
|
|
"itemName": "AK-47 | Redline",
|
|
"game": "cs2",
|
|
"price": 39.99,
|
|
"oldPrice": 45.99,
|
|
"updatedAt": "2024-01-01T00:00:00.000Z"
|
|
}
|
|
}
|
|
```
|
|
|
|
**Expected WebSocket Broadcast:**
|
|
```json
|
|
{
|
|
"type": "price_update",
|
|
"data": {
|
|
"listingId": "listing_123",
|
|
"itemName": "AK-47 | Redline",
|
|
"oldPrice": 45.99,
|
|
"newPrice": 39.99,
|
|
"percentChange": "-13.32"
|
|
},
|
|
"timestamp": 1234567890000
|
|
}
|
|
```
|
|
|
|
**Error Cases:**
|
|
- `401 Unauthorized` - Not logged in
|
|
- `403 Forbidden` - Not the listing owner
|
|
- `404 Not Found` - Invalid listing ID
|
|
- `400 Validation Error` - Invalid price
|
|
|
|
**Test Cases:**
|
|
- [ ] Update own listing price
|
|
- [ ] Try to update someone else's listing (should fail)
|
|
- [ ] Update with invalid price (should fail)
|
|
- [ ] Verify WebSocket broadcast received
|
|
- [ ] Verify price change calculation
|
|
|
|
---
|
|
|
|
### Set Trade URL Test
|
|
|
|
**Endpoint:** `PUT /user/trade-url`
|
|
|
|
**Access:** Authenticated users only
|
|
|
|
**How to test:**
|
|
```
|
|
1. Login via Steam
|
|
2. Get your Steam Trade URL:
|
|
- Go to Steam > Inventory > Trade Offers
|
|
- Click "Who can send me trade offers?"
|
|
- Copy your trade URL
|
|
3. Paste URL in "Steam Trade URL" field
|
|
4. Click "Set Trade URL (Requires Auth)"
|
|
```
|
|
|
|
**Expected Response:**
|
|
```json
|
|
{
|
|
"success": true,
|
|
"message": "Trade URL updated successfully"
|
|
}
|
|
```
|
|
|
|
**Trade URL Format:**
|
|
```
|
|
https://steamcommunity.com/tradeoffer/new/?partner=XXXXXXXXX&token=XXXXXXXX
|
|
```
|
|
|
|
**Error Cases:**
|
|
- `401 Unauthorized` - Not logged in
|
|
- `400 Validation Error` - Invalid URL format
|
|
|
|
**Test Cases:**
|
|
- [ ] Set valid trade URL
|
|
- [ ] Set invalid URL (should fail)
|
|
- [ ] Update existing trade URL
|
|
- [ ] Verify trade URL is saved
|
|
|
|
---
|
|
|
|
## 🔍 Testing Best Practices
|
|
|
|
### Before Testing
|
|
|
|
1. **Clear browser cache** if testing authentication
|
|
2. **Check server is running** on port 3000
|
|
3. **Clear messages** for clean test results
|
|
4. **Open browser console** to see detailed logs
|
|
|
|
### During Testing
|
|
|
|
1. **Monitor server logs** for backend behavior
|
|
2. **Check WebSocket messages** for real-time updates
|
|
3. **Verify statistics** (messages sent/received)
|
|
4. **Watch for errors** in Messages section
|
|
|
|
### After Testing
|
|
|
|
1. **Document results** of each test
|
|
2. **Note any errors** or unexpected behavior
|
|
3. **Check server performance** (CPU, memory)
|
|
4. **Verify data persistence** (database)
|
|
|
|
---
|
|
|
|
## 📊 Test Scenarios
|
|
|
|
### Scenario 1: Basic Marketplace Flow
|
|
|
|
```
|
|
1. Login via Steam
|
|
2. Set trade URL
|
|
3. Create a listing
|
|
- Verify WebSocket broadcast
|
|
4. Update listing price
|
|
- Verify WebSocket broadcast
|
|
5. Get all listings
|
|
- Verify your listing appears
|
|
6. Disconnect and reconnect WebSocket
|
|
7. Verify connection restored
|
|
```
|
|
|
|
### Scenario 2: Multi-User Trading
|
|
|
|
```
|
|
1. Open test client in 2 browsers
|
|
2. Browser A: Login as User A
|
|
3. Browser B: Login as User B
|
|
4. Browser A: Create listing
|
|
5. Browser B: Should receive new_listing broadcast
|
|
6. Browser A: Update price
|
|
7. Browser B: Should receive price_update broadcast
|
|
```
|
|
|
|
### Scenario 3: WebSocket Reliability
|
|
|
|
```
|
|
1. Connect to WebSocket
|
|
2. Run gradual stress test (100 msgs @ 100ms)
|
|
3. Create listing during stress test
|
|
4. Verify both stress messages and broadcasts received
|
|
5. Run burst test
|
|
6. Verify connection remains stable
|
|
7. Disconnect and reconnect
|
|
8. Send ping to verify reconnection
|
|
```
|
|
|
|
### Scenario 4: Error Handling
|
|
|
|
```
|
|
1. Try to create listing without login
|
|
- Expected: 401 error
|
|
2. Login via Steam
|
|
3. Try to create listing without trade URL
|
|
- Expected: 400 error
|
|
4. Set trade URL
|
|
5. Create listing (should succeed)
|
|
6. Try to update someone else's listing
|
|
- Expected: 403 error
|
|
```
|
|
|
|
---
|
|
|
|
## 🐛 Common Issues & Solutions
|
|
|
|
### WebSocket Won't Connect
|
|
|
|
**Symptoms:** Connection fails immediately
|
|
|
|
**Solutions:**
|
|
- Check server is running: `curl http://localhost:3000/health`
|
|
- Verify WebSocket URL: `ws://localhost:3000/ws` (not `wss://`)
|
|
- Check firewall settings
|
|
- Try anonymous connection first (no token)
|
|
|
|
### Authentication Errors
|
|
|
|
**Symptoms:** 401 Unauthorized on API calls
|
|
|
|
**Solutions:**
|
|
- Login via Steam: http://localhost:3000/auth/steam
|
|
- Check cookies are enabled
|
|
- Clear browser cookies and login again
|
|
- Verify token is valid: http://localhost:3000/auth/decode-token
|
|
|
|
### WebSocket Disconnects During Stress Test
|
|
|
|
**Symptoms:** Connection closes during high load
|
|
|
|
**Solutions:**
|
|
- Reduce message count or increase interval
|
|
- Check server rate limiting settings
|
|
- Expected behavior under extreme stress (>500 msgs)
|
|
- Monitor server CPU/memory usage
|
|
|
|
### No WebSocket Broadcasts Received
|
|
|
|
**Symptoms:** Actions succeed but no broadcasts
|
|
|
|
**Solutions:**
|
|
- Verify WebSocket is connected
|
|
- Check you're listening to the right event
|
|
- Server may not be broadcasting (check logs)
|
|
- Try reconnecting WebSocket
|
|
|
|
### CORS Errors
|
|
|
|
**Symptoms:** `Cross-Origin Request Blocked` or CORS policy errors
|
|
|
|
**Solutions:**
|
|
- Server is configured to allow `file://` protocol
|
|
- Restart server if you just updated CORS config
|
|
- Check browser console for exact CORS error
|
|
- In development, all localhost ports are allowed
|
|
- Ensure credentials are enabled if sending cookies
|
|
|
|
### Marketplace Endpoints Not Found
|
|
|
|
**Symptoms:** 404 Not Found on marketplace routes
|
|
|
|
**Solutions:**
|
|
- Verify server registered marketplace routes
|
|
- Check `index.js` imports `marketplace.example.js`
|
|
- Restart server: `npm run dev`
|
|
- Check server logs for route registration
|
|
|
|
---
|
|
|
|
## 📈 Performance Benchmarks
|
|
|
|
### Expected Performance
|
|
|
|
| Metric | Target | Acceptable | Poor |
|
|
|--------|--------|------------|------|
|
|
| Ping latency | <10ms | <50ms | >100ms |
|
|
| Message throughput | 100/sec | 50/sec | <20/sec |
|
|
| Connection stability | 99.9% | 95% | <90% |
|
|
| API response time | <100ms | <500ms | >1000ms |
|
|
| WebSocket broadcasts | <50ms | <200ms | >500ms |
|
|
|
|
### Load Testing Results
|
|
|
|
Document your test results here:
|
|
|
|
```
|
|
Date: ____________________
|
|
Server: Local / Production
|
|
Connection: WiFi / Ethernet / 4G
|
|
|
|
Stress Test Results:
|
|
- 10 msgs @ 500ms: _____ (Pass/Fail)
|
|
- 100 msgs @ 100ms: _____ (Pass/Fail)
|
|
- 500 msgs @ 50ms: _____ (Pass/Fail)
|
|
- 1000 msgs @ 10ms: _____ (Pass/Fail)
|
|
- Burst 100 msgs: _____ (Pass/Fail)
|
|
|
|
API Response Times:
|
|
- GET /marketplace/listings: _____ ms
|
|
- POST /marketplace/listings: _____ ms
|
|
- PATCH /marketplace/listings/:id/price: _____ ms
|
|
- PUT /user/trade-url: _____ ms
|
|
|
|
WebSocket Broadcast Latency:
|
|
- new_listing broadcast: _____ ms
|
|
- price_update broadcast: _____ ms
|
|
|
|
Notes:
|
|
_________________________________
|
|
_________________________________
|
|
_________________________________
|
|
```
|
|
|
|
---
|
|
|
|
## 🔐 Security Testing
|
|
|
|
### Authentication Tests
|
|
|
|
- [ ] Access protected endpoints without login (should fail)
|
|
- [ ] Use expired token (should fail)
|
|
- [ ] Use malformed token (should fail)
|
|
- [ ] Use valid token (should succeed)
|
|
|
|
### Authorization Tests
|
|
|
|
- [ ] Update another user's listing (should fail)
|
|
- [ ] Delete another user's listing (should fail)
|
|
- [ ] Access own resources (should succeed)
|
|
|
|
### Input Validation Tests
|
|
|
|
- [ ] Send negative prices (should fail)
|
|
- [ ] Send invalid JSON (should fail)
|
|
- [ ] Send SQL injection attempts (should fail)
|
|
- [ ] Send XSS attempts (should be sanitized)
|
|
- [ ] Send extremely long strings (should be rejected)
|
|
|
|
### Rate Limiting Tests
|
|
|
|
- [ ] Send 100+ API requests rapidly
|
|
- [ ] Verify rate limiting kicks in
|
|
- [ ] Wait and verify rate limit resets
|
|
|
|
---
|
|
|
|
## 📝 Test Checklist
|
|
|
|
### WebSocket Tests
|
|
- [ ] Anonymous connection
|
|
- [ ] Authenticated connection
|
|
- [ ] Send ping/pong
|
|
- [ ] Send custom messages
|
|
- [ ] Stress test (100 msgs)
|
|
- [ ] Burst test
|
|
- [ ] Reconnection after disconnect
|
|
- [ ] Connection stability
|
|
|
|
### Marketplace Tests
|
|
- [ ] Get all listings
|
|
- [ ] Filter listings by game
|
|
- [ ] Filter listings by price
|
|
- [ ] Create new listing
|
|
- [ ] Update listing price
|
|
- [ ] Receive new_listing broadcast
|
|
- [ ] Receive price_update broadcast
|
|
|
|
### User Tests
|
|
- [ ] Steam login
|
|
- [ ] Get current user info
|
|
- [ ] Set trade URL
|
|
- [ ] Verify email (if implemented)
|
|
|
|
### Error Handling
|
|
- [ ] Invalid authentication
|
|
- [ ] Missing required fields
|
|
- [ ] Invalid data types
|
|
- [ ] Rate limiting
|
|
- [ ] Network errors
|
|
|
|
---
|
|
|
|
## 🎓 Advanced Testing
|
|
|
|
### Custom Test Scripts
|
|
|
|
You can extend the test client with custom JavaScript:
|
|
|
|
```javascript
|
|
// Open browser console and run custom tests
|
|
|
|
// Test 1: Measure ping latency
|
|
async function measurePingLatency() {
|
|
const start = Date.now();
|
|
ws.send(JSON.stringify({ type: 'ping' }));
|
|
// Listen for pong and calculate: Date.now() - start
|
|
}
|
|
|
|
// Test 2: Monitor connection health
|
|
setInterval(() => {
|
|
console.log('Socket state:', ws.readyState);
|
|
console.log('Messages sent:', messageCount.sent);
|
|
console.log('Messages received:', messageCount.received);
|
|
}, 5000);
|
|
|
|
// Test 3: Automated stress test
|
|
async function automatedStressTest() {
|
|
for (let i = 0; i < 10; i++) {
|
|
await new Promise(resolve => setTimeout(resolve, 1000));
|
|
ws.send(JSON.stringify({ type: 'test', data: { iteration: i } }));
|
|
}
|
|
}
|
|
```
|
|
|
|
### Integration Testing
|
|
|
|
Test multiple features together:
|
|
|
|
```javascript
|
|
async function fullIntegrationTest() {
|
|
// 1. Connect WebSocket
|
|
connect();
|
|
await wait(1000);
|
|
|
|
// 2. Login (in browser)
|
|
// window.open('http://localhost:3000/auth/steam');
|
|
|
|
// 3. Set trade URL
|
|
await setTradeUrl();
|
|
|
|
// 4. Create listing
|
|
const listing = await createListing();
|
|
|
|
// 5. Verify broadcast received
|
|
// Check Messages section
|
|
|
|
// 6. Update price
|
|
await updateListingPrice();
|
|
|
|
// 7. Verify broadcast received
|
|
|
|
// 8. Get listings
|
|
await getListings();
|
|
|
|
console.log('✅ Integration test complete');
|
|
}
|
|
```
|
|
|
|
---
|
|
|
|
## 📞 Support
|
|
|
|
If you encounter issues:
|
|
|
|
1. Check server logs for errors
|
|
2. Check browser console for client errors
|
|
3. Verify all prerequisites are met
|
|
4. Restart server and try again
|
|
5. Check `FIXED.md` for known issues
|
|
6. Consult `WEBSOCKET_GUIDE.md` for details
|
|
|
|
---
|
|
|
|
## 📚 Additional Resources
|
|
|
|
- **WEBSOCKET_GUIDE.md** - Complete WebSocket documentation
|
|
- **WEBSOCKET_AUTH.md** - Authentication details
|
|
- **README.md** - General project documentation
|
|
- **QUICK_REFERENCE.md** - Quick API reference
|
|
- **COMMANDS.md** - CLI commands and scripts
|
|
|
|
---
|
|
|
|
**Happy Testing! 🎉** |