fix: EnsureNamespace in doCreate + sanitize API errors in UI
- doCreate() calls EnsureNamespace before creating device (idempotent) Fixes namespace-not-found when session was cached before v0.1.62 - Added sanitizeApiError() — hides internal details (namespace names, k8s paths) from user, shows friendly Russian messages instead - Patterns handled: namespace not found, already exists, HTTP 5xx Image: v0.1.63
This commit is contained in:
@@ -333,6 +333,21 @@ async function namespaceFromToken(token) {
|
||||
// API
|
||||
// =============================================================
|
||||
|
||||
// sanitizeApiError — убирает служебные детали из сообщений об ошибках API.
|
||||
// Пользователь не должен видеть namespace, k8s-пути, internal имена объектов.
|
||||
function sanitizeApiError(msg) {
|
||||
if (!msg) return 'Внутренняя ошибка. Попробуйте ещё раз.';
|
||||
// Скрываем k8s-сообщения с namespace/not found
|
||||
if (/namespaces?.*not found/i.test(msg)) return 'Ошибка инициализации. Выйдите и войдите снова.';
|
||||
if (/not found/i.test(msg) && /sless-/i.test(msg)) return 'Ресурс не найден.';
|
||||
if (/already exists/i.test(msg)) return 'Устройство с таким именем уже существует.';
|
||||
if (/device.*id.*already/i.test(msg) || /device_id.*exists/i.test(msg)) return 'Device ID уже занят.';
|
||||
if (/cannot decode jwt/i.test(msg) || /not a jwt/i.test(msg)) return 'Неверный токен.';
|
||||
// HTTP 5xx — общая фраза
|
||||
if (/HTTP 5/i.test(msg)) return 'Ошибка сервера. Попробуйте ещё раз.';
|
||||
return msg;
|
||||
}
|
||||
|
||||
// apiCall — универсальная обёртка для REST запросов к оператору
|
||||
async function apiCall(method, path, body) {
|
||||
const opts = {
|
||||
@@ -738,12 +753,17 @@ async function doCreate() {
|
||||
btn.disabled = true; btn.textContent = 'Создание...';
|
||||
|
||||
try {
|
||||
// EnsureNamespace — идемпотентный вызов.
|
||||
// Страховка на случай если сессия была сохранена до автосоздания namespace при логине.
|
||||
await apiCall('POST', `/v1/namespaces/${S.ns}/ensure`, {});
|
||||
await apiCreateDevice(name, did);
|
||||
closeModal();
|
||||
await renderDevices();
|
||||
} catch(e) {
|
||||
btn.disabled = false; btn.textContent = 'Создать';
|
||||
document.getElementById('m-err').innerHTML = `<div class="alert alert-error">${h(e.message)}</div>`;
|
||||
// Скрываем служебные детали (namespace, k8s-пути) от пользователя
|
||||
const msg = sanitizeApiError(e.message);
|
||||
document.getElementById('m-err').innerHTML = `<div class="alert alert-error">${h(msg)}</div>`;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user