betty2 / ai-handler copy 6.js
sdgsdggds's picture
Upload folder using huggingface_hub
e7c953d verified
// AI Handler for Gemini API integration - Simple version
const https = require('https');
class AIHandler {
constructor(apiKey) {
this.apiKey = apiKey;
console.log('AI Handler initialized with simple implementation');
}
/**
* Make a request to the Gemini API and get a response for chat
* @param {string} userMessage - The message from the chat user
* @returns {Promise<string>} - The AI response or error message
*/
async getAIResponse(userMessage) {
return new Promise((resolve, reject) => {
try {
console.log(`AI processing message: ${userMessage}`);
// Create a well-formatted prompt for Gemini models
const prompt = `You are a helpful assistant. you must use Korean.
User message: "${userMessage}"
`;
// Use a supported model from the Gemini family
//
const url = `https://generativelanguage.googleapis.com/v1beta/models/gemini-2.5-flash-preview-05-20:generateContent?key=${this.apiKey}`;
// Standard request body that works with both Gemini 1.x and Gemini 2.x models
const body = JSON.stringify({
contents: [{
parts: [{
text: prompt
}]
}],
generationConfig: {
temperature: 0.7,
maxOutputTokens: 5000, // Keep responses shorter for chat
topP: 0.95,
topK: 40
},
safetySettings: [
{
category: "HARM_CATEGORY_HARASSMENT",
threshold: "BLOCK_MEDIUM_AND_ABOVE"
},
{
category: "HARM_CATEGORY_HATE_SPEECH",
threshold: "BLOCK_MEDIUM_AND_ABOVE"
}
]
});
// Log the request URL to debug
console.log(`Sending request to: ${url.replace(this.apiKey, 'API_KEY')}`);
// Parse the URL for the request
const urlObj = new URL(url);
// Set up the request options
const options = {
hostname: urlObj.hostname,
path: urlObj.pathname + urlObj.search,
method: 'POST',
headers: {
'Content-Type': 'application/json',
'Content-Length': Buffer.byteLength(body)
}
};
const req = https.request(options, (res) => {
let responseBody = '';
// Collect data chunks
res.on('data', (chunk) => {
responseBody += chunk;
});
// Process complete response
res.on('end', () => {
console.log(`API Response status: ${res.statusCode}`);
// Check for success
if (res.statusCode !== 200) {
console.error(`API Error ${res.statusCode}: ${responseBody}`);
return resolve('Sorry, I had a problem connecting to my AI brain.');
}
try {
const response = JSON.parse(responseBody);
// Full debug of the response structure
console.log('Full API response:', JSON.stringify(response));
// Handle different response formats for different Gemini versions
let text = null;
// Try different response formats
if (response.candidates && response.candidates[0]) {
const candidate = response.candidates[0];
// Format 1: Standard parts array with text
if (candidate.content &&
candidate.content.parts &&
candidate.content.parts[0] &&
candidate.content.parts[0].text) {
text = candidate.content.parts[0].text.trim();
}
// Format 2: Content with text property directly
else if (candidate.content && candidate.content.text) {
text = candidate.content.text.trim();
}
// Format 3: Text property directly on candidate
else if (candidate.text) {
text = candidate.text.trim();
}
// Format 4: For chat-style responses with finish reasons
else if (candidate.content && candidate.finishReason) {
if (candidate.finishReason === 'STOP') {
text = 'I understand what you mean.'; // Reasonable fallback
} else if (candidate.finishReason === 'MAX_TOKENS') {
text = 'I have thoughts about that, but let me keep it brief.'; // Token limit fallback
}
}
}
if (text) {
// Log success and clean up the text
console.log(`AI generated: ${text.substring(0, 50)}...`);
// Clean up common issues with AI responses
text = text.replace(/^("|'|`)/, ''); // Remove starting quotes
text = text.replace(/("|'|`)$/, ''); // Remove ending quotes
text = text.replace(/^Your helpful, concise response: ?/i, ''); // Remove any prompt echoing
// Enforce length limit for chat
const maxLength = 150;
if (text.length > maxLength) {
text = text.substring(0, maxLength - 3) + '...';
}
resolve(text);
} else {
console.error('Could not extract text from response:', JSON.stringify(response));
// Good fallback responses for a music chat bot
const fallbacks = [
'Interesting thoughts about the music! What else are you enjoying in the queue?',
'That is a good point! Music brings people together in so many ways.',
'I like how you think about music. What is your favorite genre?',
'Thanks for sharing that with me! The song selection here is always interesting.',
'I appreciate your perspective on this. Music is such a universal language.'
];
// Return a random fallback
resolve(fallbacks[Math.floor(Math.random() * fallbacks.length)]);
}
} catch (error) {
console.error('Error parsing response:', error);
console.error('Raw response:', responseBody.substring(0, 200));
resolve('Sorry, I had trouble understanding the response.');
}
});
});
// Handle request errors
req.on('error', (error) => {
console.error('Request error:', error);
resolve('Sorry, I had trouble connecting to my AI brain. Try again later?');
});
// Send the request
req.write(body);
req.end();
} catch (error) {
console.error('Unexpected error in getAIResponse:', error);
resolve('Sorry, something unexpected happened with my AI processing.');
}
});
}
}
module.exports = AIHandler;