86 lines
2.7 KiB
JavaScript
86 lines
2.7 KiB
JavaScript
const { Router } = require('express');
|
||
const settings = require('../config/settings');
|
||
const fs = require('fs');
|
||
|
||
const router = Router();
|
||
|
||
router.get('/', (req, res) => {
|
||
res.json(settings.load());
|
||
});
|
||
|
||
router.patch('/', (req, res) => {
|
||
const { recentEpisodeLimit, semanticLimit, scoreThreshold } = req.body;
|
||
const updates = {};
|
||
|
||
if (recentEpisodeLimit !== undefined) {
|
||
const val = Number(recentEpisodeLimit);
|
||
if (!Number.isInteger(val) || val < 1 || val > 20)
|
||
return res.status(400).json({ error: 'recentEpisodeLimit must be 1–20' });
|
||
updates.recentEpisodeLimit = val;
|
||
}
|
||
|
||
if (semanticLimit !== undefined) {
|
||
const val = Number(semanticLimit);
|
||
if (!Number.isInteger(val) || val < 1 || val > 20)
|
||
return res.status(400).json({ error: 'semanticLimit must be 1–20' });
|
||
updates.semanticLimit = val;
|
||
}
|
||
|
||
if (scoreThreshold !== undefined) {
|
||
const val = Number(scoreThreshold);
|
||
if (isNaN(val) || val < 0 || val > 1)
|
||
return res.status(400).json({ error: 'scoreThreshold must be 0–1' });
|
||
updates.scoreThreshold = val;
|
||
}
|
||
|
||
if (req.body.modelsFolderPath !== undefined) {
|
||
const val = req.body.modelsFolderPath.trim();
|
||
if (!val) return res.status(400).json({ error: 'modelsFolderPath cannot be empty' });
|
||
// Verify the path exists and is readable
|
||
try {
|
||
fs.readdirSync(val);
|
||
} catch {
|
||
return res.status(400).json({ error: `Path not accessible: ${val}` });
|
||
}
|
||
updates.modelsFolderPath = val;
|
||
}
|
||
|
||
if (req.body.temperature !== undefined) {
|
||
const val = Number(req.body.temperature);
|
||
if (isNaN(val) || val < 0 || val > 2)
|
||
return res.status(400).json({ error: 'temperature must be 0–2' });
|
||
updates.temperature = val;
|
||
}
|
||
|
||
if (req.body.repeatPenalty !== undefined) {
|
||
const val = Number(req.body.repeatPenalty);
|
||
if (isNaN(val) || val < 1 || val > 2)
|
||
return res.status(400).json({ error: 'repeatPenalty must be 1–2' });
|
||
updates.repeatPenalty = val;
|
||
}
|
||
|
||
if (req.body.topP !== undefined) {
|
||
const val = Number(req.body.topP);
|
||
if (isNaN(val) || val < 0 || val > 1)
|
||
return res.status(400).json({ error: 'topP must be 0–1' });
|
||
updates.topP = val;
|
||
}
|
||
|
||
if (req.body.topK !== undefined) {
|
||
const val = Number(req.body.topK);
|
||
if (!Number.isInteger(val) || val < 1 || val > 100)
|
||
return res.status(400).json({ error: 'topK must be 1–100' });
|
||
updates.topK = val;
|
||
}
|
||
|
||
if (req.body.systemPrompt !== undefined) {
|
||
const val = req.body.systemPrompt;
|
||
if (typeof val !== 'string')
|
||
return res.status(400).json({ error: 'systemPrompt must be a string' });
|
||
updates.systemPrompt = val.trim() || null; // null reverts to default
|
||
}
|
||
|
||
res.json(settings.save(updates));
|
||
});
|
||
|
||
module.exports = router; |