mirror of
https://github.com/qingchencloud/clawpanel.git
synced 2026-07-08 08:01:48 +08:00
fix(engine-select): release 0.16.4
This commit is contained in:
@@ -26,7 +26,7 @@ const PATTERNS = [
|
||||
// 网络
|
||||
{
|
||||
key: 'network',
|
||||
re: /(failed to fetch|networkerror|networkfailure|enetunreach|econnreset|econnrefused|ehostunreach|err_network|fetch failed|connection refused|connection reset|getaddrinfo|dns error|no route to host|aborted|broken pipe|connect timed out|tcp connect)/i,
|
||||
re: /(failed to fetch|networkerror|networkfailure|enetunreach|econnreset|econnrefused|ehostunreach|err_network|fetch failed|connection refused|connection reset|getaddrinfo|dns error|no route to host|aborted|broken pipe|connect timed out|tcp connect|backend service is not running|web deployment mode|后端服务未运行)/i,
|
||||
},
|
||||
// Gateway 未启动(特殊的 connection refused / port not listen 情况)
|
||||
{
|
||||
|
||||
@@ -231,7 +231,13 @@ export async function checkBackendHealth() {
|
||||
if (isTauriRuntime()) { _setBackendOnline(true); return true }
|
||||
try {
|
||||
const resp = await fetch('/__api/health', { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: '{}' })
|
||||
const ok = resp.ok
|
||||
const ct = (resp.headers.get('content-type') || '').toLowerCase()
|
||||
if (!resp.ok || !ct.includes('application/json')) {
|
||||
_setBackendOnline(false)
|
||||
return false
|
||||
}
|
||||
const data = await resp.json().catch(() => null)
|
||||
const ok = !!data?.ok
|
||||
_setBackendOnline(ok)
|
||||
return ok
|
||||
} catch {
|
||||
|
||||
@@ -110,7 +110,7 @@ function showBackendDownOverlay() {
|
||||
<div style="color:var(--text-tertiary);margin-bottom:4px"># ${t('common.devMode')}</div>
|
||||
npm run dev<br>
|
||||
<div style="color:var(--text-tertiary);margin-top:8px;margin-bottom:4px"># ${t('common.prodMode')}</div>
|
||||
npm run preview
|
||||
npm run serve
|
||||
</div>
|
||||
<button class="login-btn" id="btn-backend-retry" style="margin-top:8px">
|
||||
<span id="backend-retry-text">${t('common.checkAgain')}</span>
|
||||
|
||||
@@ -2,6 +2,7 @@ import { navigate } from '../router.js'
|
||||
import { t } from '../lib/i18n.js'
|
||||
import { applyEngineSelection } from '../lib/engine-manager.js'
|
||||
import { toast } from '../components/toast.js'
|
||||
import { humanizeError } from '../lib/humanize-error.js'
|
||||
|
||||
const PRIMARY_OPTIONS = [
|
||||
{
|
||||
@@ -167,7 +168,7 @@ function bindClick(page) {
|
||||
navigate(option.targetRoute)
|
||||
} catch (error) {
|
||||
console.error('[engine-select] secondary choose failed:', error)
|
||||
toast(t('engine.choiceSaveFailed'), 'error')
|
||||
toast(humanizeError(error, t('engine.choiceSaveFailed')), 'error')
|
||||
_busy = false
|
||||
btn.classList.remove('loading')
|
||||
}
|
||||
@@ -213,7 +214,7 @@ async function chooseWithAnimation(page, panel, option, engine) {
|
||||
}, 280))
|
||||
} catch (error) {
|
||||
console.error('[engine-select] choose failed:', error)
|
||||
toast(t('engine.choiceSaveFailed'), 'error')
|
||||
toast(humanizeError(error, t('engine.choiceSaveFailed')), 'error')
|
||||
// 失败回退:移除动画层 + 解除 busy
|
||||
removeRevealNodes()
|
||||
// stage 可能已不在 DOM(路由已切走)— 防御性访问
|
||||
|
||||
Reference in New Issue
Block a user