personal-dash-cl/claudash/proxy-server.js

99 lines
2.9 KiB
JavaScript

import express from 'express';
import cors from 'cors';
const app = express();
const PORT = process.env.PROXY_PORT || 5374;
const DEBUG = process.env.REACT_APP_DEBUG_MODE === 'true';
function debugLog(...args) {
if (DEBUG) console.log(...args);
}
app.use(cors());
// Increase payload limit to 10MB (default is 100kb)
app.use(express.json({ limit: '10mb' }));
// Proxy endpoint for Claude API
app.post('/api/claude', async (req, res) => {
try {
const { messages, apiKey, model, maxTokens } = req.body;
debugLog('=== Proxy received request ===');
debugLog('Model:', model);
debugLog('Max tokens:', maxTokens);
debugLog('Messages count:', messages?.length);
const requestBody = {
model: model,
max_tokens: maxTokens,
messages: messages,
...(req.body.tools && { tools: req.body.tools })
};
debugLog('Request body:', JSON.stringify(requestBody, null, 2));
const response = await fetch('https://api.anthropic.com/v1/messages', {
method: 'POST',
headers: {
'Content-Type': 'application/json',
'x-api-key': apiKey,
'anthropic-version': '2023-06-01'
},
body: JSON.stringify(requestBody)
});
debugLog('Claude API response status:', response.status);
if (!response.ok) {
const error = await response.text();
console.error('Claude API error:', error);
return res.status(response.status).json({ error });
}
const data = await response.json();
debugLog('Claude API success, response content length:', data.content?.[0]?.text?.length);
debugLog('Token usage:', data.usage);
res.json(data);
} catch (error) {
console.error('Proxy error:', error);
res.status(500).json({ error: error.message });
}
});
// Proxy endpoint for scraping web pages (avoids CORS issues)
app.get('/api/scrape', async (req, res) => {
try {
const { url } = req.query;
if (!url) {
return res.status(400).json({ error: 'Missing url query parameter' });
}
debugLog('=== Scrape proxy request ===');
debugLog('URL:', url);
const response = await fetch(url, {
headers: {
'User-Agent': 'Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36',
'Accept': 'text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8',
'Accept-Language': 'en-US,en;q=0.5',
}
});
if (!response.ok) {
console.error('Scrape failed:', response.status, response.statusText);
return res.status(response.status).json({ error: `Failed to fetch: ${response.status} ${response.statusText}` });
}
const html = await response.text();
debugLog('Scraped HTML length:', html.length);
res.type('text/html').send(html);
} catch (error) {
console.error('Scrape proxy error:', error);
res.status(500).json({ error: error.message });
}
});
app.listen(PORT, () => {
console.log(`Proxy server running on http://localhost:${PORT}`);
});