Files
TTW_Bot_GO/internal/webui/templates/ai.html
T
2026-04-15 08:00:15 +03:00

159 lines
7.2 KiB
HTML

{{define "content"}}
<h2>Настройки нейросетей</h2>
<div class="card">
<form id="ai-form">
<label>Провайдер:</label>
<select id="provider" name="provider">
<option value="ollama">Ollama (локальная)</option>
<option value="chatgpt">ChatGPT (OpenAI)</option>
<option value="gigachat">GigaChat (Сбер)</option>
</select>
<div id="ollama-fields" class="provider-fields">
<label>Endpoint:</label>
<input type="text" id="endpoint" name="endpoint" placeholder="http://localhost:11434">
<label>Модель:</label>
<input type="text" id="model" name="model" placeholder="llama2, mistral, ...">
</div>
<div id="chatgpt-fields" class="provider-fields" style="display:none;">
<label>API Key:</label>
<input type="password" id="api_key" name="api_key" placeholder="sk-...">
<label>Модель:</label>
<input type="text" id="model_gpt" name="model_gpt" placeholder="gpt-3.5-turbo">
</div>
<div id="gigachat-fields" class="provider-fields" style="display:none;">
<label>Client ID:</label>
<input type="text" id="client_id" name="client_id" placeholder="ваш client_id">
<label>Client Secret:</label>
<input type="password" id="client_secret" name="client_secret" placeholder="ваш client_secret">
<label>Endpoint (опционально):</label>
<input type="text" id="endpoint_giga" name="endpoint_giga" placeholder="https://gigachat.devices.sberbank.ru/api/v1">
<label>Модель (опционально):</label>
<input type="text" id="model_giga" name="model_giga" placeholder="GigaChat">
</div>
<label>Системный промпт (префикс):</label>
<textarea id="system_prompt" name="system_prompt" rows="3">ты в чате твитча, ответь одним предложением.</textarea>
<button type="submit">Сохранить</button>
</form>
</div>
<div class="card">
<h3>Тестирование</h3>
<input type="text" id="test-prompt" placeholder="Введите вопрос для нейросети" style="width: 70%;">
<button id="test-btn">Отправить</button>
<div id="test-result" class="test-result-block"></div>
</div>
<script>
const providerSelect = document.getElementById('provider');
const ollamaFields = document.getElementById('ollama-fields');
const chatgptFields = document.getElementById('chatgpt-fields');
const gigachatFields = document.getElementById('gigachat-fields');
function showProviderFields() {
const prov = providerSelect.value;
ollamaFields.style.display = 'none';
chatgptFields.style.display = 'none';
gigachatFields.style.display = 'none';
if (prov === 'ollama') ollamaFields.style.display = 'block';
else if (prov === 'chatgpt') chatgptFields.style.display = 'block';
else if (prov === 'gigachat') gigachatFields.style.display = 'block';
}
providerSelect.addEventListener('change', showProviderFields);
async function loadConfig() {
const res = await fetch('/api/ai/config');
const cfg = await res.json();
providerSelect.value = cfg.provider || 'ollama';
document.getElementById('endpoint').value = cfg.endpoint || '';
document.getElementById('model').value = cfg.model || '';
document.getElementById('api_key').value = cfg.api_key || '';
document.getElementById('model_gpt').value = cfg.model || '';
document.getElementById('client_id').value = cfg.client_id || '';
document.getElementById('client_secret').value = cfg.client_secret || '';
document.getElementById('endpoint_giga').value = cfg.endpoint || '';
document.getElementById('model_giga').value = cfg.model || '';
document.getElementById('system_prompt').value = cfg.system_prompt || 'ты в чате твитча, ответь одним предложением.';
showProviderFields();
}
document.getElementById('ai-form').addEventListener('submit', async (e) => {
e.preventDefault();
const provider = providerSelect.value;
let apiKey = '', endpoint = '', model = '', clientId = '', clientSecret = '';
if (provider === 'ollama') {
endpoint = document.getElementById('endpoint').value;
model = document.getElementById('model').value;
} else if (provider === 'chatgpt') {
apiKey = document.getElementById('api_key').value;
model = document.getElementById('model_gpt').value;
} else if (provider === 'gigachat') {
clientId = document.getElementById('client_id').value;
clientSecret = document.getElementById('client_secret').value;
endpoint = document.getElementById('endpoint_giga').value;
model = document.getElementById('model_giga').value;
}
const systemPrompt = document.getElementById('system_prompt').value;
const body = {
provider,
api_key: apiKey,
endpoint,
model,
system_prompt: systemPrompt,
client_id: clientId,
client_secret: clientSecret
};
try {
const res = await fetch('/api/ai/config', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify(body)
});
if (res.ok) {
alert('Настройки сохранены');
await loadConfig();
} else {
const err = await res.text();
alert('Ошибка сохранения: ' + err);
}
} catch (err) {
alert('Ошибка соединения: ' + err.message);
}
});
document.getElementById('test-btn').addEventListener('click', async () => {
const prompt = document.getElementById('test-prompt').value;
if (!prompt) return;
try {
const res = await fetch('/api/ai/test', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ prompt })
});
if (res.ok) {
const data = await res.json();
document.getElementById('test-result').innerHTML = `<strong>Ответ:</strong> ${escapeHtml(data.answer)}`;
} else {
const err = await res.text();
document.getElementById('test-result').innerHTML = `<span style="color:red;">Ошибка: ${escapeHtml(err)}</span>`;
}
} catch (err) {
document.getElementById('test-result').innerHTML = `<span style="color:red;">Ошибка соединения: ${err.message}</span>`;
}
});
function escapeHtml(str) {
if (!str) return '';
return str.replace(/[&<>]/g, function(m) {
if (m === '&') return '&amp;';
if (m === '<') return '&lt;';
if (m === '>') return '&gt;';
return m;
});
}
loadConfig();
</script>
{{end}}