Files
OpenQode/bin/sendMessage-api.mjs

135 lines
4.1 KiB
JavaScript

// NEW sendMessage function that uses Qwen Chat API directly
// This replaces the broken CLI-based approach
const QWEN_CHAT_API = 'https://chat.qwen.ai/api/chat/completions';
function randomUUID() {
return crypto.randomUUID();
}
async sendMessage(message, model = 'qwen-coder-plus', imageData = null, onChunk = null, systemPrompt = null) {
// If we have image data, use the Vision API
if (imageData) {
console.log('📷 Image data detected, using Vision API...');
return await this.sendVisionMessage(message, imageData, 'qwen-vl-plus');
}
// Use Qwen Chat API directly with loaded tokens
try {
await this.loadTokens();
if (!this.tokens || !this.tokens.access_token) {
return {
success: false,
error: 'Not authenticated. Please authenticate first.',
response: ''
};
}
// Build messages array
const messages = [];
// Add system prompt if provided
if (systemPrompt) {
messages.push({
role: 'system',
content: systemPrompt
});
}
// Add user message
messages.push({
role: 'user',
content: message
});
const requestBody = {
model: model,
messages: messages,
stream: !!onChunk // Stream if callback provided
};
const response = await fetch(QWEN_CHAT_API, {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Authorization': `Bearer ${this.tokens.access_token}`,
'x-request-id': randomUUID()
},
body: JSON.stringify(requestBody)
});
if (!response.ok) {
const errorText = await response.text();
return {
success: false,
error: `API error: ${response.status} - ${errorText}`,
response: ''
};
}
// Handle streaming response
if (onChunk && response.body) {
let fullResponse = '';
const reader = response.body.getReader();
const decoder = new TextDecoder();
try {
while (true) {
const { done, value } = await reader.read();
if (done) break;
const chunk = decoder.decode(value, { stream: true });
const lines = chunk.split('\n').filter(line => line.trim().startsWith('data: '));
for (const line of lines) {
const data = line.replace(/^data: /, '').trim();
if (data === '[DONE]') continue;
try {
const parsed = JSON.parse(data);
const content = parsed.choices?.[0]?.delta?.content || '';
if (content) {
fullResponse += content;
onChunk(content);
}
} catch (e) {
// Skip invalid JSON
}
}
}
} catch (error) {
return {
success: false,
error: `Streaming error: ${error.message}`,
response: fullResponse
};
}
return {
success: true,
response: fullResponse,
usage: null
};
}
// Handle non-streaming response
const data = await response.json();
const responseText = data.choices?.[0]?.message?.content || '';
return {
success: true,
response: responseText,
usage: data.usage
};
} catch (error) {
console.error('Qwen API error:', error.message);
return {
success: false,
error: error.message || 'API request failed',
response: ''
};
}
}