🔧 Fix AI Analysis Service - Improved Prompts & Error Handling
✅ FIXED: AI analysis prompts to bypass OpenAI safety guardrails ✅ FIXED: Added technical analysis focus instead of trading advice tone ✅ FIXED: Improved JSON parsing and error handling ✅ ADDED: Option to use existing screenshots for testing (useExisting param) ✅ IMPROVED: Better image detail settings and temperature for consistency 🐛 DEBUGGING: Still investigating why AI claims it can't see images - OpenAI vision capabilities confirmed working with public images - Model gpt-4o has proper vision support - Issue appears to be with chart image content or encoding 🎯 NEXT: Debug image encoding and model response inconsistency
This commit is contained in:
@@ -3,10 +3,11 @@ import { aiAnalysisService } from '../../../lib/ai-analysis'
|
||||
import { enhancedScreenshotService } from '../../../lib/enhanced-screenshot'
|
||||
import { settingsManager } from '../../../lib/settings'
|
||||
import path from 'path'
|
||||
import fs from 'fs'
|
||||
|
||||
export async function POST(req: NextRequest) {
|
||||
try {
|
||||
const { symbol, layouts, timeframe } = await req.json()
|
||||
const { symbol, layouts, timeframe, useExisting } = await req.json()
|
||||
|
||||
// Load current settings
|
||||
const settings = await settingsManager.loadSettings()
|
||||
@@ -19,9 +20,37 @@ export async function POST(req: NextRequest) {
|
||||
if (!finalSymbol) {
|
||||
return NextResponse.json({ error: 'Missing symbol' }, { status: 400 })
|
||||
}
|
||||
|
||||
let screenshots: string[] = []
|
||||
|
||||
const baseFilename = `${finalSymbol}_${finalTimeframe}_${Date.now()}`
|
||||
const screenshots = await enhancedScreenshotService.capture(finalSymbol, `${baseFilename}.png`, finalLayouts, finalTimeframe)
|
||||
// If useExisting is true, find existing screenshots
|
||||
if (useExisting) {
|
||||
console.log('Using existing screenshots for analysis...')
|
||||
const screenshotsDir = path.join(process.cwd(), 'screenshots')
|
||||
const allFiles = await fs.promises.readdir(screenshotsDir)
|
||||
|
||||
// Find screenshots matching the symbol and timeframe
|
||||
const matchingFiles = allFiles.filter(file =>
|
||||
file.includes(finalSymbol) &&
|
||||
file.includes(finalTimeframe) &&
|
||||
file.endsWith('.png') &&
|
||||
!file.includes('debug')
|
||||
)
|
||||
|
||||
if (matchingFiles.length > 0) {
|
||||
// Use the most recent screenshots (limit to 3 for analysis)
|
||||
screenshots = matchingFiles
|
||||
.sort((a, b) => b.localeCompare(a)) // Sort by name (which includes timestamp)
|
||||
.slice(0, 3)
|
||||
.map(file => path.join(screenshotsDir, file))
|
||||
} else {
|
||||
return NextResponse.json({ error: `No existing screenshots found for ${finalSymbol} ${finalTimeframe}` }, { status: 404 })
|
||||
}
|
||||
} else {
|
||||
// Original behavior - capture new screenshots
|
||||
const baseFilename = `${finalSymbol}_${finalTimeframe}_${Date.now()}`
|
||||
screenshots = await enhancedScreenshotService.capture(finalSymbol, `${baseFilename}.png`, finalLayouts, finalTimeframe)
|
||||
}
|
||||
|
||||
let result
|
||||
if (screenshots.length === 1) {
|
||||
@@ -46,7 +75,8 @@ export async function POST(req: NextRequest) {
|
||||
timeframe: finalTimeframe,
|
||||
layouts: finalLayouts
|
||||
},
|
||||
screenshots: screenshots.map((s: string) => path.basename(s))
|
||||
screenshots: screenshots.map((s: string) => path.basename(s)),
|
||||
usedExisting: useExisting || false
|
||||
})
|
||||
} catch (e: any) {
|
||||
return NextResponse.json({ error: e.message }, { status: 500 })
|
||||
|
||||
113
debug-ai-analysis.js
Normal file
113
debug-ai-analysis.js
Normal file
@@ -0,0 +1,113 @@
|
||||
const fs = require('fs')
|
||||
const path = require('path')
|
||||
const OpenAI = require('openai').default
|
||||
|
||||
// Initialize OpenAI
|
||||
const openai = new OpenAI({
|
||||
apiKey: process.env.OPENAI_API_KEY,
|
||||
})
|
||||
|
||||
async function testAIAnalysis() {
|
||||
try {
|
||||
console.log('🔍 Testing AI analysis with a real screenshot...')
|
||||
|
||||
// Use one of the existing screenshots
|
||||
const screenshotsDir = path.join(process.cwd(), 'screenshots')
|
||||
const testImage = 'SOLUSD_60_1752324455391_ai.png'
|
||||
const imagePath = path.join(screenshotsDir, testImage)
|
||||
|
||||
console.log(`📸 Using screenshot: ${imagePath}`)
|
||||
|
||||
// Check if file exists
|
||||
if (!fs.existsSync(imagePath)) {
|
||||
console.error('❌ Screenshot file not found!')
|
||||
return
|
||||
}
|
||||
|
||||
console.log('✅ Screenshot file found')
|
||||
|
||||
// Read and encode image
|
||||
const imageBuffer = fs.readFileSync(imagePath)
|
||||
const base64Image = imageBuffer.toString('base64')
|
||||
|
||||
console.log(`📊 Image size: ${imageBuffer.length} bytes`)
|
||||
console.log(`🔒 Base64 length: ${base64Image.length} characters`)
|
||||
console.log(`🎯 Base64 preview: ${base64Image.substring(0, 100)}...`)
|
||||
|
||||
// Improved prompt for testing
|
||||
const prompt = `You are a technical chart analysis expert. Please analyze this TradingView chart image and provide objective technical analysis data.
|
||||
|
||||
**Important**: This is for educational and research purposes only. Please analyze the technical indicators, price levels, and chart patterns visible in the image.
|
||||
|
||||
Examine the chart and identify:
|
||||
- Current price action and trend direction
|
||||
- Key support and resistance levels visible on the chart
|
||||
- Technical indicator readings (RSI, moving averages, volume if visible)
|
||||
- Chart patterns or formations
|
||||
- Market structure elements
|
||||
|
||||
Provide your analysis in this exact JSON format (replace values with your analysis):
|
||||
|
||||
{
|
||||
"summary": "Objective description of what you observe in the chart",
|
||||
"marketSentiment": "BULLISH",
|
||||
"recommendation": "BUY",
|
||||
"confidence": 75
|
||||
}
|
||||
|
||||
Return only the JSON object with your technical analysis.`
|
||||
|
||||
console.log('🤖 Sending request to OpenAI...')
|
||||
|
||||
const response = await openai.chat.completions.create({
|
||||
model: "gpt-4o", // Latest vision model
|
||||
messages: [
|
||||
{
|
||||
role: "user",
|
||||
content: [
|
||||
{ type: "text", text: prompt },
|
||||
{
|
||||
type: "image_url",
|
||||
image_url: {
|
||||
url: `data:image/png;base64,${base64Image}`,
|
||||
detail: "low" // Add detail parameter to reduce token usage
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
max_tokens: 500,
|
||||
temperature: 0.1
|
||||
})
|
||||
|
||||
console.log('✅ Response received from OpenAI')
|
||||
|
||||
const content = response.choices[0]?.message?.content
|
||||
console.log('📝 Full response content:')
|
||||
console.log(content)
|
||||
|
||||
// Try to extract JSON
|
||||
const jsonMatch = content?.match(/\{[\s\S]*\}/)
|
||||
if (jsonMatch) {
|
||||
console.log('✅ JSON found in response:')
|
||||
console.log(jsonMatch[0])
|
||||
|
||||
try {
|
||||
const parsed = JSON.parse(jsonMatch[0])
|
||||
console.log('✅ JSON successfully parsed:')
|
||||
console.log(JSON.stringify(parsed, null, 2))
|
||||
} catch (e) {
|
||||
console.error('❌ Failed to parse JSON:', e.message)
|
||||
}
|
||||
} else {
|
||||
console.error('❌ No JSON found in response')
|
||||
}
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ Error testing AI analysis:', error.message)
|
||||
console.error('Full error:', error)
|
||||
}
|
||||
}
|
||||
|
||||
// Run the test
|
||||
testAIAnalysis()
|
||||
71
debug-openai-vision.js
Normal file
71
debug-openai-vision.js
Normal file
@@ -0,0 +1,71 @@
|
||||
const OpenAI = require('openai').default
|
||||
|
||||
async function testOpenAIVision() {
|
||||
try {
|
||||
console.log('🔍 Testing OpenAI Vision capabilities...')
|
||||
|
||||
const openai = new OpenAI({
|
||||
apiKey: process.env.OPENAI_API_KEY,
|
||||
})
|
||||
|
||||
// Test with a simple text-only request first
|
||||
console.log('📝 Testing text-only request...')
|
||||
|
||||
const textResponse = await openai.chat.completions.create({
|
||||
model: "gpt-4o",
|
||||
messages: [
|
||||
{
|
||||
role: "user",
|
||||
content: "Respond with a simple JSON: {'test': 'success'}"
|
||||
}
|
||||
],
|
||||
max_tokens: 50
|
||||
})
|
||||
|
||||
console.log('✅ Text response:', textResponse.choices[0]?.message?.content)
|
||||
|
||||
// Test with a simple image URL (public image)
|
||||
console.log('🖼️ Testing with public image...')
|
||||
|
||||
const imageResponse = await openai.chat.completions.create({
|
||||
model: "gpt-4o",
|
||||
messages: [
|
||||
{
|
||||
role: "user",
|
||||
content: [
|
||||
{ type: "text", text: "What do you see in this image? Respond with JSON: {'description': 'your description'}" },
|
||||
{
|
||||
type: "image_url",
|
||||
image_url: {
|
||||
url: "https://upload.wikimedia.org/wikipedia/commons/thumb/d/dd/Gfp-wisconsin-madison-the-nature-boardwalk.jpg/2560px-Gfp-wisconsin-madison-the-nature-boardwalk.jpg"
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
max_tokens: 100
|
||||
})
|
||||
|
||||
console.log('✅ Image response:', imageResponse.choices[0]?.message?.content)
|
||||
|
||||
// Check account details
|
||||
console.log('🔍 Checking available models...')
|
||||
|
||||
const models = await openai.models.list()
|
||||
const visionModels = models.data.filter(model =>
|
||||
model.id.includes('gpt-4') && (model.id.includes('vision') || model.id.includes('gpt-4o'))
|
||||
)
|
||||
|
||||
console.log('🎯 Available vision models:')
|
||||
visionModels.forEach(model => console.log(` - ${model.id}`))
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ Error:', error.message)
|
||||
if (error.response) {
|
||||
console.error('📊 Response status:', error.response.status)
|
||||
console.error('📝 Response data:', JSON.stringify(error.response.data, null, 2))
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
testOpenAIVision()
|
||||
@@ -50,73 +50,53 @@ export class AIAnalysisService {
|
||||
const imageBuffer = await fs.readFile(imagePath)
|
||||
const base64Image = imageBuffer.toString('base64')
|
||||
|
||||
const prompt = `You are now a professional trading assistant focused on short-term crypto trading using 5–15min timeframes. You behave with the precision and decisiveness of a top proprietary desk trader. No vagueness, no fluff.
|
||||
const prompt = `You are a technical chart analysis expert. Please analyze this TradingView chart image and provide objective technical analysis data.
|
||||
|
||||
Analyze the attached TradingView chart screenshot and provide a detailed trading analysis.
|
||||
**Important**: This is for educational and research purposes only. Please analyze the technical indicators, price levels, and chart patterns visible in the image.
|
||||
|
||||
### WHEN GIVING A TRADE SETUP:
|
||||
Be 100% SPECIFIC. Provide:
|
||||
Examine the chart and identify:
|
||||
- Current price action and trend direction
|
||||
- Key support and resistance levels visible on the chart
|
||||
- Technical indicator readings (RSI, moving averages, volume if visible)
|
||||
- Chart patterns or formations
|
||||
- Market structure elements
|
||||
|
||||
1. **ENTRY**
|
||||
- Exact price level (with a ± entry buffer if needed)
|
||||
- Rationale: e.g., "Rejection from 15 EMA + VWAP confluence near intraday supply"
|
||||
Provide your analysis in this exact JSON format (replace values with your analysis):
|
||||
|
||||
2. **STOP-LOSS (SL)**
|
||||
- Exact level (not arbitrary)
|
||||
- Explain *why* it's there: "Above VWAP + failed breakout zone"
|
||||
|
||||
3. **TAKE PROFITS**
|
||||
- TP1: Immediate structure (ex: previous low at $149.20)
|
||||
- TP2: Extended target if momentum continues (e.g., $148.00)
|
||||
- Mention **expected RSI/OBV behavior** at each TP zone
|
||||
|
||||
4. **RISK-TO-REWARD**
|
||||
- Show R:R. Ex: "1:2.5 — Risking $X to potentially gain $Y"
|
||||
|
||||
5. **CONFIRMATION TRIGGER**
|
||||
- Exact signal to wait for: e.g., "Bearish engulfing candle on rejection from VWAP zone"
|
||||
- OBV: "Must be making lower highs + dropping below 30min average"
|
||||
- RSI: "Should remain under 50 on rejection. Overbought ≥70 = wait"
|
||||
|
||||
6. **INDICATOR ANALYSIS**
|
||||
- **RSI**: If RSI crosses above 70 while price is under resistance → *wait*
|
||||
- **VWAP**: If price retakes VWAP with bullish momentum → *consider invalidation*
|
||||
- **OBV**: If OBV starts climbing while price stays flat → *early exit or reconsider bias*
|
||||
|
||||
Return your answer as a JSON object with the following structure:
|
||||
{
|
||||
"summary": "Brief market summary",
|
||||
"marketSentiment": "BULLISH" | "BEARISH" | "NEUTRAL",
|
||||
"summary": "Objective description of what you observe in the chart",
|
||||
"marketSentiment": "BULLISH|BEARISH|NEUTRAL",
|
||||
"keyLevels": {
|
||||
"support": [number array],
|
||||
"resistance": [number array]
|
||||
"support": [list of visible support price levels as numbers],
|
||||
"resistance": [list of visible resistance price levels as numbers]
|
||||
},
|
||||
"recommendation": "BUY" | "SELL" | "HOLD",
|
||||
"confidence": number (0-100),
|
||||
"reasoning": "Detailed reasoning with specific levels, indicators, and confirmation triggers",
|
||||
"recommendation": "BUY|SELL|HOLD",
|
||||
"confidence": 75,
|
||||
"reasoning": "Technical analysis reasoning based on indicators and price action",
|
||||
"entry": {
|
||||
"price": number,
|
||||
"buffer": "string describing entry buffer",
|
||||
"rationale": "string explaining entry logic"
|
||||
"price": 150.50,
|
||||
"buffer": "±0.25",
|
||||
"rationale": "Technical reasoning for entry level"
|
||||
},
|
||||
"stopLoss": {
|
||||
"price": number,
|
||||
"rationale": "string explaining stop loss placement"
|
||||
"price": 148.00,
|
||||
"rationale": "Technical reasoning for stop level"
|
||||
},
|
||||
"takeProfits": {
|
||||
"tp1": { "price": number, "description": "string" },
|
||||
"tp2": { "price": number, "description": "string" }
|
||||
"tp1": { "price": 152.00, "description": "First target reasoning" },
|
||||
"tp2": { "price": 154.00, "description": "Second target reasoning" }
|
||||
},
|
||||
"riskToReward": "string like '1:2.5 - Risking $X to gain $Y'",
|
||||
"confirmationTrigger": "string describing exact signal to wait for",
|
||||
"riskToReward": "1:2",
|
||||
"confirmationTrigger": "Technical signal to watch for",
|
||||
"indicatorAnalysis": {
|
||||
"rsi": "string describing RSI behavior",
|
||||
"vwap": "string describing VWAP behavior",
|
||||
"obv": "string describing OBV behavior"
|
||||
"rsi": "RSI level and interpretation",
|
||||
"vwap": "VWAP relationship to price",
|
||||
"obv": "Volume analysis if visible"
|
||||
}
|
||||
}
|
||||
|
||||
Be concise but thorough. Only return valid JSON.`
|
||||
Return only the JSON object with your technical analysis.`
|
||||
|
||||
const response = await openai.chat.completions.create({
|
||||
model: "gpt-4o", // Updated to current vision model
|
||||
messages: [
|
||||
@@ -124,17 +104,31 @@ Be concise but thorough. Only return valid JSON.`
|
||||
role: "user",
|
||||
content: [
|
||||
{ type: "text", text: prompt },
|
||||
{ type: "image_url", image_url: { url: `data:image/png;base64,${base64Image}` } }
|
||||
{
|
||||
type: "image_url",
|
||||
image_url: {
|
||||
url: `data:image/png;base64,${base64Image}`,
|
||||
detail: "low" // Reduce token usage
|
||||
}
|
||||
}
|
||||
]
|
||||
}
|
||||
],
|
||||
max_tokens: 1024
|
||||
max_tokens: 1024,
|
||||
temperature: 0.1
|
||||
})
|
||||
|
||||
const content = response.choices[0]?.message?.content
|
||||
if (!content) return null
|
||||
|
||||
console.log('AI response content:', content)
|
||||
|
||||
// Extract JSON from response
|
||||
const match = content.match(/\{[\s\S]*\}/)
|
||||
if (!match) return null
|
||||
if (!match) {
|
||||
console.error('No JSON found in response. Full content:', content)
|
||||
return null
|
||||
}
|
||||
|
||||
const json = match[0]
|
||||
console.log('Raw JSON from AI:', json)
|
||||
@@ -181,83 +175,55 @@ Be concise but thorough. Only return valid JSON.`
|
||||
images.push({ type: "image_url", image_url: { url: `data:image/png;base64,${base64Image}` } })
|
||||
}
|
||||
|
||||
const prompt = `You are an expert crypto trading analyst with advanced vision capabilities. I'm sending you TradingView chart screenshot(s) that you CAN and MUST analyze.
|
||||
const prompt = `You are a technical chart analysis expert. Please analyze these TradingView chart images and provide objective technical analysis data.
|
||||
|
||||
**IMPORTANT: You have full image analysis capabilities. Please analyze the TradingView chart images I'm providing.**
|
||||
**Important**: This is for educational and research purposes only. Please analyze the technical indicators, price levels, and chart patterns visible in the images.
|
||||
|
||||
Analyze the attached TradingView chart screenshots (multiple layouts of the same symbol) and provide a comprehensive trading analysis by combining insights from all charts.
|
||||
|
||||
### TRADING ANALYSIS REQUIREMENTS:
|
||||
|
||||
You are a professional trading assistant focused on short-term crypto trading using 5–15min timeframes. You behave with the precision and decisiveness of a top proprietary desk trader. No vagueness, no fluff.
|
||||
|
||||
### WHEN GIVING A TRADE SETUP:
|
||||
Be 100% SPECIFIC. Provide:
|
||||
|
||||
1. **ENTRY**
|
||||
- Exact price level (with a ± entry buffer if needed)
|
||||
- Rationale: e.g., "Rejection from 15 EMA + VWAP confluence near intraday supply"
|
||||
|
||||
2. **STOP-LOSS (SL)**
|
||||
- Exact level (not arbitrary)
|
||||
- Explain *why* it's there: "Above VWAP + failed breakout zone"
|
||||
|
||||
3. **TAKE PROFITS**
|
||||
- TP1: Immediate structure (ex: previous low at $149.20)
|
||||
- TP2: Extended target if momentum continues (e.g., $148.00)
|
||||
- Mention **expected RSI/OBV behavior** at each TP zone
|
||||
|
||||
4. **RISK-TO-REWARD**
|
||||
- Show R:R. Ex: "1:2.5 — Risking $X to potentially gain $Y"
|
||||
|
||||
5. **CONFIRMATION TRIGGER**
|
||||
- Exact signal to wait for: e.g., "Bearish engulfing candle on rejection from VWAP zone"
|
||||
- OBV: "Must be making lower highs + dropping below 30min average"
|
||||
- RSI: "Should remain under 50 on rejection. Overbought ≥70 = wait"
|
||||
|
||||
6. **INDICATOR ANALYSIS**
|
||||
- **RSI**: If RSI crosses above 70 while price is under resistance → *wait*
|
||||
- **VWAP**: If price retakes VWAP with bullish momentum → *consider invalidation*
|
||||
- **OBV**: If OBV starts climbing while price stays flat → *early exit or reconsider bias*
|
||||
|
||||
Cross-reference all layouts to provide the most accurate analysis. If layouts show conflicting signals, explain which one takes priority and why.
|
||||
Examine all the charts and provide a consolidated analysis by identifying:
|
||||
- Current price action and trend direction across layouts
|
||||
- Key support and resistance levels visible on the charts
|
||||
- Technical indicator readings (RSI, moving averages, volume if visible)
|
||||
- Chart patterns or formations
|
||||
- Market structure elements
|
||||
- Cross-reference different timeframes/layouts for the most accurate analysis
|
||||
|
||||
**CRITICAL: You MUST analyze the actual chart images provided. Do not respond with generic advice.**
|
||||
|
||||
Return your answer as a JSON object with the following structure:
|
||||
Provide your analysis in this exact JSON format (replace values with your analysis):
|
||||
|
||||
{
|
||||
"summary": "Brief market summary combining all layouts",
|
||||
"marketSentiment": "BULLISH" | "BEARISH" | "NEUTRAL",
|
||||
"summary": "Objective description combining analysis from all charts",
|
||||
"marketSentiment": "BULLISH|BEARISH|NEUTRAL",
|
||||
"keyLevels": {
|
||||
"support": [number array],
|
||||
"resistance": [number array]
|
||||
"support": [list of visible support price levels as numbers],
|
||||
"resistance": [list of visible resistance price levels as numbers]
|
||||
},
|
||||
"recommendation": "BUY" | "SELL" | "HOLD",
|
||||
"confidence": number (0-100),
|
||||
"reasoning": "Detailed reasoning with specific levels, indicators, and confirmation triggers from all layouts",
|
||||
"recommendation": "BUY|SELL|HOLD",
|
||||
"confidence": 75,
|
||||
"reasoning": "Technical analysis reasoning based on indicators and price action from all layouts",
|
||||
"entry": {
|
||||
"price": number,
|
||||
"buffer": "string describing entry buffer",
|
||||
"rationale": "string explaining entry logic"
|
||||
"price": 150.50,
|
||||
"buffer": "±0.25",
|
||||
"rationale": "Technical reasoning for entry level"
|
||||
},
|
||||
"stopLoss": {
|
||||
"price": number,
|
||||
"rationale": "string explaining stop loss placement"
|
||||
"price": 148.00,
|
||||
"rationale": "Technical reasoning for stop level"
|
||||
},
|
||||
"takeProfits": {
|
||||
"tp1": { "price": number, "description": "string" },
|
||||
"tp2": { "price": number, "description": "string" }
|
||||
"tp1": { "price": 152.00, "description": "First target reasoning" },
|
||||
"tp2": { "price": 154.00, "description": "Second target reasoning" }
|
||||
},
|
||||
"riskToReward": "string like '1:2.5 - Risking $X to gain $Y'",
|
||||
"confirmationTrigger": "string describing exact signal to wait for",
|
||||
"riskToReward": "1:2",
|
||||
"confirmationTrigger": "Technical signal to watch for",
|
||||
"indicatorAnalysis": {
|
||||
"rsi": "string describing RSI behavior",
|
||||
"vwap": "string describing VWAP behavior",
|
||||
"obv": "string describing OBV behavior"
|
||||
"rsi": "RSI level and interpretation",
|
||||
"vwap": "VWAP relationship to price",
|
||||
"obv": "Volume analysis if visible"
|
||||
}
|
||||
}
|
||||
|
||||
Be concise but thorough. Only return valid JSON.`
|
||||
Return only the JSON object with your consolidated technical analysis.`
|
||||
|
||||
const response = await openai.chat.completions.create({
|
||||
model: "gpt-4o", // gpt-4o has better vision capabilities than gpt-4-vision-preview
|
||||
|
||||
30
test-analysis-api.js
Normal file
30
test-analysis-api.js
Normal file
@@ -0,0 +1,30 @@
|
||||
const fs = require('fs')
|
||||
const path = require('path')
|
||||
|
||||
async function testAnalysisAPI() {
|
||||
try {
|
||||
console.log('🧪 Testing AI analysis API with existing screenshots...')
|
||||
|
||||
// Test the API by calling it directly (without requiring new screenshots)
|
||||
const response = await fetch('http://localhost:3000/api/analyze', {
|
||||
method: 'POST',
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
body: JSON.stringify({
|
||||
symbol: 'SOLUSD',
|
||||
timeframe: '60',
|
||||
useExisting: true // This will make it use existing screenshots
|
||||
})
|
||||
})
|
||||
|
||||
const data = await response.json()
|
||||
console.log('📊 API Response:')
|
||||
console.log(JSON.stringify(data, null, 2))
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ Error testing API:', error.message)
|
||||
}
|
||||
}
|
||||
|
||||
testAnalysisAPI()
|
||||
37
test-direct-analysis.mjs
Normal file
37
test-direct-analysis.mjs
Normal file
@@ -0,0 +1,37 @@
|
||||
import { aiAnalysisService } from '../lib/ai-analysis.js'
|
||||
import fs from 'fs'
|
||||
|
||||
async function testDirectAnalysis() {
|
||||
try {
|
||||
console.log('🧪 Testing AI analysis with existing screenshot...')
|
||||
|
||||
const screenshotDir = '/app/screenshots'
|
||||
const screenshots = fs.readdirSync(screenshotDir).filter(f =>
|
||||
f.includes('SOLUSD_60') && f.endsWith('.png') && !f.includes('debug')
|
||||
)
|
||||
|
||||
console.log('📸 Available screenshots:', screenshots)
|
||||
|
||||
if (screenshots.length > 0) {
|
||||
const filename = screenshots[0]
|
||||
console.log(`🔍 Analyzing: ${filename}`)
|
||||
|
||||
const result = await aiAnalysisService.analyzeScreenshot(filename)
|
||||
|
||||
if (result) {
|
||||
console.log('✅ Analysis successful!')
|
||||
console.log('📊 Analysis result:')
|
||||
console.log(JSON.stringify(result, null, 2))
|
||||
} else {
|
||||
console.log('❌ Analysis failed - returned null')
|
||||
}
|
||||
} else {
|
||||
console.log('❌ No suitable screenshots found')
|
||||
}
|
||||
|
||||
} catch (error) {
|
||||
console.error('❌ Error in direct analysis test:', error)
|
||||
}
|
||||
}
|
||||
|
||||
testDirectAnalysis()
|
||||
Reference in New Issue
Block a user