From f79301b2454eba83b8296e99ec3f6c093dbb5f8b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E2=80=9CNaeel=E2=80=9D?= Date: Thu, 30 Jul 2026 07:47:43 +0400 Subject: [PATCH] v1.1.37: params for all ops + polling try/catch + refresh always + tracker CMDB + firstServiceId --- site/app.py | 2 +- site/routes/api_test.py | 4 ++++ site/static/app.js | 38 ++++++++++++++++++++------------------ site/templates/index.html | 3 ++- 4 files changed, 27 insertions(+), 20 deletions(-) diff --git a/site/app.py b/site/app.py index 6c64fae..0237966 100644 --- a/site/app.py +++ b/site/app.py @@ -18,7 +18,7 @@ from routes.api import bp as api_bp from routes.api_test import bp as api_test_bp # Версия — меняется при КАЖДОМ изменении кода. Показывается в топбаре UI. -VERSION = "1.1.36" +VERSION = "1.1.37" app = Flask(__name__, template_folder="templates", static_folder="static") app.config["NUBES_API_ENDPOINT"] = os.getenv("NUBES_API_ENDPOINT", "https://lk-api-gateway-test.ngcloud.ru/api/v1/svc") diff --git a/site/routes/api_test.py b/site/routes/api_test.py index 095c31b..5f5bb11 100644 --- a/site/routes/api_test.py +++ b/site/routes/api_test.py @@ -220,6 +220,10 @@ def api_test(): cmdb_ok, cmdb_code = client.raw_delete(cmdb_url) _log(f"[CMDB] DELETE {instance_uid} → ok={cmdb_ok} code={cmdb_code}") if cmdb_ok: + try: + tracker_remove(get_client_id(), get_stand(), instance_uid) + except Exception: + pass return jsonify({"status": "OK", "opUid": "cmdb-"+instance_uid[:8], "instanceUid": instance_uid, "displayName": display_name}) if op_name == "redeploy": diff --git a/site/static/app.js b/site/static/app.js index 4cf0b10..f6c34ac 100644 --- a/site/static/app.js +++ b/site/static/app.js @@ -26,7 +26,7 @@ * showStages() — отрисовка этапов выполнения операции (⏳/✅/❌) */ let svcInstances=[], selectedInst=null, selectedOp=null, pollTimer=null; -let currentSvcId=1; // динамический — обновляется при selectService() +let currentSvcId=(window.APP&&window.APP.firstServiceId)||1; // динамический — обновляется при selectService() let currentSvcName=''; // имя текущего сервиса (колонка «тип инстанса») let currentSvcShort=''; // краткое имя (redis, postgres) для displayName let busy=false; // блокировка: запрет операций пока идёт другая @@ -127,14 +127,7 @@ function makeCreateDisplayName(){ function runOp(opName,opId){ if(busy) return; stopPoll(); - selectedOp={opId,opName,svcId:currentSvcId}; - if(opName==='modify'){ - showParams(opId,opName); - }else{ - // confirm and execute immediately - if(!confirm(`Запустить ${opName} для ${findInstName()}?`)) return; - executeOp({}); - } + showParams(opId,opName); } function findInstName(){ @@ -167,7 +160,8 @@ function showParams(opId,opName){ const form=document.getElementById('params-form'); const displayNameValue=isCreate?makeCreateDisplayName():''; const createHeader=isCreate?`
Создание: ${currentSvcName}
`:''; - form.innerHTML=createHeader+(opName==='create'?`
${AUTOTEST_PREFIX}
`:'') + const emptyOpHeader=(!isCreate&¶ms.length===0)?`
Операция: ${_esc(opName)}${_esc(findInstName())}
`:''; + form.innerHTML=createHeader+emptyOpHeader+(opName==='create'?`
${AUTOTEST_PREFIX}
`:'') + params.map(p=>{ const req=p.isRequired; const hasDfl=p.defaultValue!==null&&p.defaultValue!==undefined&&p.defaultValue!==''; @@ -350,17 +344,25 @@ async function executeOp(params){ // start polling const opUid=d.opUid; const instanceName=d.displayName||displayName||findInstName(); + let _pollErrors=0; pollTimer=setInterval(async()=>{ - const sr=await fetch('/api/test/status/'+opUid); - const sd=await sr.json(); - showStages(sd.stages||[]); - if(sd.status!=='RUNNING'){ - stopPoll(); - setFinishedState(sd.status, sd.status==='OK'?'badge-success':'badge', sd.error||sd.errorLog, sd.duration, sd.displayName||instanceName); - if(sd.status==='OK'){ + try{ + const sr=await fetch('/api/test/status/'+opUid); + const sd=await sr.json(); + _pollErrors=0; + showStages(sd.stages||[]); + if(sd.status!=='RUNNING'){ + stopPoll(); + setFinishedState(sd.status, sd.status==='OK'?'badge-success':'badge', sd.error||sd.errorLog, sd.duration, sd.displayName||instanceName); await refreshInstances(); + if(historyOpen) await loadHistory(); + } + }catch(e){ + _pollErrors++; + if(_pollErrors>=5){ + stopPoll(); + setFinishedState('TIMEOUT','','Связь потеряна',0,instanceName); } - if(historyOpen) await loadHistory(); } },2000); }catch(e){ diff --git a/site/templates/index.html b/site/templates/index.html index 8b1b3cb..4b45137 100644 --- a/site/templates/index.html +++ b/site/templates/index.html @@ -138,7 +138,8 @@ window.APP = { version: "{{ config.VERSION | tojson }}", stand: "{{ stand | tojson }}", - hasUserToken: {{ has_user_token | tojson }} + hasUserToken: {{ has_user_token | tojson }}, + firstServiceId: {{ (config.service_ids[0] if config.service_ids else 1) | tojson }} };