- Updated README.md with automation features and Docker troubleshooting - Enhanced copilot-instructions.md with multi-timeframe patterns and Docker workflows - Created DEVELOPMENT_GUIDE.md with comprehensive implementation patterns - Added troubleshooting section for volume mount issues - Documented fresh implementation approach vs file editing - Included performance optimization tips and future roadmap - Added testing strategies and common pitfall solutions Key knowledge preserved: - Multi-timeframe UI patterns and state management - Docker Compose v2 syntax and volume mount troubleshooting - Fresh file creation approach for problematic edits - Complete automation page implementation examples
10 KiB
🛠️ Development Guide: Multi-Timeframe Trading Bot
🚀 Quick Reference for Future Development
This guide contains lessons learned and best practices from implementing the multi-timeframe automation functionality. Use this to accelerate future development and avoid common pitfalls.
🎯 Multi-Timeframe Implementation Pattern
Core Architecture
// Standard timeframes configuration
const timeframes = ['5m', '15m', '30m', '1h', '2h', '4h', '1d'];
// State management
const [selectedTimeframes, setSelectedTimeframes] = useState(['1h', '4h']);
const [balance, setBalance] = useState({ balance: 0, collateral: 0 });
// Toggle function - EXACT implementation required
const toggleTimeframe = (tf) => {
setSelectedTimeframes(prev =>
prev.includes(tf)
? prev.filter(t => t !== tf) // Remove if selected
: [...prev, tf] // Add if not selected
);
};
// Preset configurations
const presets = {
scalping: ['5m', '15m', '1h'],
day: ['1h', '4h', '1d'],
swing: ['4h', '1d']
};
UI Components Pattern
// Timeframe checkbox grid
<div className="grid grid-cols-4 gap-2 mb-4">
{timeframes.map(tf => (
<button
key={tf}
onClick={() => toggleTimeframe(tf)}
className={`p-2 rounded border transition-all ${
selectedTimeframes.includes(tf)
? 'bg-blue-600 border-blue-500 text-white'
: 'bg-gray-700 border-gray-600 text-gray-300 hover:bg-gray-600'
}`}
>
{tf}
</button>
))}
</div>
// Preset buttons
<div className="flex gap-2 mb-4">
{Object.entries(presets).map(([name, tfs]) => (
<button
key={name}
onClick={() => setSelectedTimeframes(tfs)}
className="px-3 py-1 bg-purple-600 hover:bg-purple-700 rounded text-sm"
>
{name.charAt(0).toUpperCase() + name.slice(1)}
</button>
))}
</div>
// Position sizing with balance integration
<select
value={positionPercentage}
onChange={(e) => setPositionPercentage(parseFloat(e.target.value))}
className="bg-gray-700 border border-gray-600 rounded px-3 py-2"
>
<option value={1}>1% (${(balance.balance * 0.01).toFixed(2)})</option>
<option value={5}>5% (${(balance.balance * 0.05).toFixed(2)})</option>
<option value={10}>10% (${(balance.balance * 0.10).toFixed(2)})</option>
<option value={25}>25% (${(balance.balance * 0.25).toFixed(2)})</option>
<option value={50}>50% (${(balance.balance * 0.50).toFixed(2)})</option>
</select>
🐳 Docker Development Best Practices
Essential Commands (Docker Compose v2)
# Development environment (ALWAYS use for active development)
npm run docker:dev # Port 9001:3000 with hot reload
docker compose -f docker-compose.dev.yml up --build
# Production environment
npm run docker:up # Port 9000:3000 optimized
docker compose -f docker-compose.prod.yml up --build
# Debugging and maintenance
npm run docker:logs # View container logs
npm run docker:exec # Shell access to container
docker compose -f docker-compose.dev.yml restart app # Quick restart
Volume Mount Troubleshooting
Problem: File changes not reflecting in running container
Root Cause: Docker volume mount synchronization issues, especially on Linux systems
Solutions (in order of preference):
-
Fresh Implementation Approach (RECOMMENDED)
# Instead of editing problematic files, create new ones cp app/automation/page.js app/automation/page-v2.js # OR create entirely new directory mkdir app/automation-v2 # Edit the new file instead -
Container Restart
docker compose -f docker-compose.dev.yml restart app -
Full Rebuild
docker compose -f docker-compose.dev.yml down docker compose -f docker-compose.dev.yml up --build -
Volume Mount Verification
# Test if volume mount is working echo "test-$(date)" > test-volume-mount.txt docker compose -f docker-compose.dev.yml exec app cat test-volume-mount.txt # Should show the same timestamp -
Manual File Copy (for immediate testing)
docker cp ./app/automation/page.js trader_dev:/app/app/automation/page.js
Text Editing Pitfalls
NEVER use sed/awk for JSX files - They often corrupt the syntax. Examples of problematic approaches:
# ❌ DON'T DO THIS - Often corrupts JSX
sed -i 's/old_pattern/new_pattern/' app/automation/page.js
# ❌ DON'T DO THIS - Breaks React syntax
awk 'pattern {action}' file.js > newfile.js
✅ PREFERRED approaches:
- Create new files instead of editing
- Use proper editing tools that understand JSX
- Manual copy/paste for small changes
- Use the
replace_string_in_filetool with proper context
📁 File Organization Strategy
Current Page Structure
app/
├── analysis/page.js # ✅ Original analysis with multi-timeframe
├── automation/
│ ├── page.js # ❌ Legacy, may have corruption issues
│ └── page-v2.js # ✅ Clean backup implementation
├── automation-v2/
│ └── page.js # ✅ NEW: Current working automation
└── ...
Naming Conventions for New Features
- Primary Implementation: Use descriptive directory names (
automation-v2/) - Backup/Alternative: Add
-v2,-clean,-workingsuffixes - Test Files: Prefix with
test-or put in/test/directory - Backup Files: Add
.backup,.working-backupextensions
🔍 Feature Copying Workflow
When copying functionality between pages (like analysis → automation):
Step 1: Research Existing Implementation
# Find timeframe-related code
grep -r "timeframes.*=.*\[" app/ --include="*.js" --include="*.jsx"
grep -r "selectedTimeframes" app/ --include="*.js" --include="*.jsx"
grep -r "toggleTimeframe" app/ --include="*.js" --include="*.jsx"
Step 2: Create Clean Target File
# DON'T modify existing problematic files
# CREATE new clean implementation
cp app/analysis/page.js app/automation-v2/page.js
# OR start completely fresh
Step 3: Copy Core Components
Required elements to copy:
timeframesarray definitionselectedTimeframesstate managementtoggleTimeframefunction- Timeframe checkbox grid UI
- Preset buttons (Scalping, Day Trading, Swing)
- Balance integration and formatting
- Position sizing calculations
Step 4: Test in Container
# Ensure container sees changes
npm run docker:dev
# Access http://localhost:9001/automation-v2
# Verify all functionality works
Step 5: Commit Clean Implementation
git add .
git commit -m "feat: Add automation V2 with multi-timeframe support"
git push
🧪 Testing Strategy
Functional Testing Checklist
- Timeframe checkboxes toggle correctly
- Preset buttons select correct timeframes
- Balance displays with proper formatting (2 decimal places)
- Position sizing calculates correctly
- Selected timeframes persist during page interaction
- Visual feedback shows selected state
- All 7 timeframes available (5m, 15m, 30m, 1h, 2h, 4h, 1d)
Docker Testing
# Test volume mount functionality
echo "test-$(date)" > test-volume-mount.txt
docker compose -f docker-compose.dev.yml exec app cat test-volume-mount.txt
# Test hot reload
# Make a small change to a file and verify it reflects in browser
# Test container logs
npm run docker:logs | grep -i error
🚨 Common Pitfalls & Solutions
Issue: "selectedTimeframes is not defined"
Cause: State hook not properly imported or defined Solution:
import { useState } from 'react';
const [selectedTimeframes, setSelectedTimeframes] = useState(['1h', '4h']);
Issue: Checkboxes not showing selected state
Cause: Missing .includes() check in className
Solution:
className={`... ${selectedTimeframes.includes(tf) ? 'selected-styles' : 'default-styles'}`}
Issue: Balance showing as NaN or undefined
Cause: Balance not properly fetched or formatted Solution:
const [balance, setBalance] = useState({ balance: 0, collateral: 0 });
// Format with: parseFloat(balance.balance).toFixed(2)
Issue: File changes not reflecting in container
Cause: Docker volume mount sync issues Solution: Use fresh implementation approach (create new files)
Issue: JSX syntax errors after text manipulation
Cause: sed/awk corruption of JSX syntax Solution: Start with clean file, avoid text manipulation tools
🎯 Performance Optimization
Multi-Timeframe Rendering
// Efficient timeframe rendering with React.memo for large lists
const TimeframeButton = React.memo(({ tf, isSelected, onToggle }) => (
<button
onClick={() => onToggle(tf)}
className={`... ${isSelected ? 'selected' : 'default'}`}
>
{tf}
</button>
));
// Use in parent component
{timeframes.map(tf => (
<TimeframeButton
key={tf}
tf={tf}
isSelected={selectedTimeframes.includes(tf)}
onToggle={toggleTimeframe}
/>
))}
Balance Updates
// Throttle balance updates to avoid excessive API calls
useEffect(() => {
const fetchBalance = async () => {
try {
const response = await fetch('/api/balance');
const data = await response.json();
setBalance(data);
} catch (error) {
console.error('Balance fetch failed:', error);
}
};
fetchBalance();
const interval = setInterval(fetchBalance, 30000); // Every 30 seconds
return () => clearInterval(interval);
}, []);
📊 Future Development Roadmap
Immediate Improvements
- Add timeframe-specific position sizing recommendations
- Implement timeframe conflict detection (opposing signals)
- Add saved timeframe combinations (custom presets)
- Enhance balance integration with real-time updates
Advanced Features
- Multi-symbol automation across timeframes
- Automated position sizing based on volatility
- Cross-timeframe correlation analysis
- Risk management integration per timeframe
Code Quality
- TypeScript migration for automation pages
- Unit tests for timeframe logic
- Integration tests for Docker workflows
- Performance monitoring for multi-timeframe operations
Key Takeaway: When in doubt, create new files instead of editing problematic ones. Docker volume mount issues are easier to solve with fresh implementations than complex debugging.
Success Pattern: Analysis page → Clean automation-v2 implementation → Working multi-timeframe functionality