From 749875a3cda8a25ae8c38eea3314967f8ed90e64 Mon Sep 17 00:00:00 2001 From: nogueiraguh Date: Tue, 3 Mar 2026 20:22:47 -0300 Subject: [PATCH] refactor: move GenAI parameters to Chat tab, simplify GenAI Config Remove temperature, max_tokens, top_p, top_k, frequency/presence penalty fields from the GenAI Config tab. That tab is now focused on adding custom models not in the catalog. Parameters are now managed exclusively in the Chat tab via the collapsible gear panel, available for both direct models and saved configs. Inline params override stored defaults when using presets. --- backend/app.py | 11 ++++++++++- frontend/index.html | 32 ++++++++++++-------------------- 2 files changed, 22 insertions(+), 21 deletions(-) diff --git a/backend/app.py b/backend/app.py index 1a327e5..2eb49a5 100644 --- a/backend/app.py +++ b/backend/app.py @@ -1577,7 +1577,16 @@ async def chat(msg: ChatMsg, u=Depends(current_user)): genai_cfg = None if msg.genai_config_id: with db() as c: - genai_cfg = c.execute("SELECT * FROM genai_configs WHERE id=?", (msg.genai_config_id,)).fetchone() + row = c.execute("SELECT * FROM genai_configs WHERE id=?", (msg.genai_config_id,)).fetchone() + if row: + genai_cfg = dict(row) + # Override params from inline chat settings if provided + if msg.temperature is not None: genai_cfg["temperature"] = msg.temperature + if msg.max_tokens is not None: genai_cfg["max_tokens"] = msg.max_tokens + if msg.top_p is not None: genai_cfg["top_p"] = msg.top_p + if msg.top_k is not None: genai_cfg["top_k"] = msg.top_k + if msg.frequency_penalty is not None: genai_cfg["frequency_penalty"] = msg.frequency_penalty + if msg.presence_penalty is not None: genai_cfg["presence_penalty"] = msg.presence_penalty elif msg.model_id and msg.oci_config_id: # Direct model mode: build synthetic config dict with db() as c: diff --git a/frontend/index.html b/frontend/index.html index 1bf6da3..e135990 100644 --- a/frontend/index.html +++ b/frontend/index.html @@ -272,13 +272,14 @@ function rChat(){ const provOrder=['openai','google','meta','cohere','xai']; const catalogOpts=provOrder.filter(p=>provs[p]).map(p=>{const label=p.charAt(0).toUpperCase()+p.slice(1);const opts=provs[p].map(m=>``).join('');return`${opts}`}).join(''); const isDirect=S.chatModel&&!S.chatModel.startsWith('cfg:'); + const hasModel=!!S.chatModel; // OCI selector for direct mode const ociSel=isDirect?``:''; - const gearBtn=isDirect?`
${S.chatParamsOpen?'✕':'⚙️'}
`:''; + const gearBtn=hasModel?`
${S.chatParamsOpen?'✕':'⚙️'}
`:''; const ragBadge=S.adbCfg.some(c=>c.genai_config_id&&c.is_active)?'RAG':''; - // Params panel + // Params panel - available for any model (direct or preset) const pp=S.chatParams; - const paramsPanel=isDirect&&S.chatParamsOpen?`
+ const paramsPanel=hasModel&&S.chatParamsOpen?`
@@ -294,8 +295,7 @@ ${paramsPanel}
${ms}
`} function chatModelChanged(){S.chatModel=document.getElementById('cmod').value; - if(S.chatModel.startsWith('cfg:')){S.chatParamsOpen=false} - else if(S.chatModel&&!S.chatOci&&S.ociCfg.length){S.chatOci=S.ociCfg[0].id;const c=S.ociCfg[0];S.chatRegion=c.region;S.chatCompartment=c.compartment_id||''} + if(S.chatModel&&!S.chatModel.startsWith('cfg:')&&!S.chatOci&&S.ociCfg.length){S.chatOci=S.ociCfg[0].id;const c=S.ociCfg[0];S.chatRegion=c.region;S.chatCompartment=c.compartment_id||''} R()} function chatOciChanged(){S.chatOci=document.getElementById('coci').value;const c=S.ociCfg.find(x=>x.id===S.chatOci);if(c){S.chatRegion=c.region;S.chatCompartment=c.compartment_id||''}} function toggleChatParams(){S.chatParamsOpen=!S.chatParamsOpen;R()} @@ -303,7 +303,10 @@ function fm(t){return t.replace(/\*\*(.*?)\*\*/g,'$1').replace( async function sChat(){const el=document.getElementById('chi');const m=el.value.trim();if(!m)return;el.value=''; S.msgs.push({r:'user',c:m});R();scCh(); try{const body={message:m,session_id:S.sid}; - if(S.chatModel.startsWith('cfg:')){body.genai_config_id=S.chatModel.slice(4)} + if(S.chatModel.startsWith('cfg:')){ + body.genai_config_id=S.chatModel.slice(4); + body.temperature=S.chatParams.temperature;body.max_tokens=S.chatParams.max_tokens;body.top_p=S.chatParams.top_p; + body.top_k=S.chatParams.top_k;body.frequency_penalty=S.chatParams.frequency_penalty;body.presence_penalty=S.chatParams.presence_penalty} else if(S.chatModel){ if(!S.chatOci){S.msgs.push({r:'assistant',c:'⚠️ Selecione uma credencial OCI para usar o modelo direto.'});R();return} body.model_id=S.chatModel;body.oci_config_id=S.chatOci;body.genai_region=S.chatRegion;body.compartment_id=S.chatCompartment; @@ -418,29 +421,21 @@ function rGenAI(){const eg=S.editing?.type==='genai'?S.genaiCfg.find(g=>g.id===S const mOpts=''+Object.entries(S.models).map(([k,v])=>``).join(''); const rOpts=S.regions.map(r=>``).join(''); return`
🧠 Modelos Configurados
- +
ConfigModeloRegiãoTempTokensAções
${S.genaiCfg.map(g=>{const mi=S.models[g.model_id]||{};return` -`}).join('')}
ConfigModeloRegiãoAções
${g.name||'—'}${g.is_default?' ⭐':''} ${mi.name||(g.model_ocid?'OCID Personalizado':g.model_id)}
${mi.provider||(g.model_ocid?'custom':'?')}
${g.genai_region}${g.temperature}${g.max_tokens}
${!S.genaiCfg.length?'

Nenhum modelo configurado.

':''}
${eg?'✏️ Editar Modelo GenAI':'➕ Novo Modelo GenAI'}
-
${eg?'Editando: '+eg.name+'':'Configura conexão via OCI SDK (GenerativeAiInferenceClient). O endpoint é gerado automaticamente pela região selecionada.'}
-
+
${eg?'Editando: '+eg.name+'':'Adicione modelos personalizados que não estão no catálogo do Chat Agent, ou crie presets com credenciais específicas.'}
+
Cole o OCID do modelo do portal OCI. Se preenchido, será usado no lugar do modelo selecionado acima.
-
Parâmetros
-
-
-
-
-
-
${eg?'':''}
`+rConfigLogs('genai')} async function sGenai(){const btn=document.getElementById('gbtn');btn.disabled=true;btn.textContent='Salvando...';sm('gm',' Salvando modelo...','i'); @@ -453,9 +448,6 @@ async function sGenai(){const btn=document.getElementById('gbtn');btn.disabled=t model_ocid:ocid, compartment_id:document.getElementById('gcmp').value,genai_region:document.getElementById('greg').value, endpoint:null,serving_type:'ON_DEMAND',dedicated_endpoint_id:null, - temperature:parseFloat(document.getElementById('gtemp').value),max_tokens:parseInt(document.getElementById('gmt').value), - top_p:parseFloat(document.getElementById('gtp').value),top_k:parseInt(document.getElementById('gtk').value), - frequency_penalty:parseFloat(document.getElementById('gfp').value),presence_penalty:parseFloat(document.getElementById('gpp').value), is_default:isEdit?(S.genaiCfg.find(g=>g.id===S.editing.id)?.is_default||false):S.genaiCfg.length===0}; try{const url=isEdit?'/genai/configs/'+S.editing.id:'/genai/config';const method=isEdit?'PUT':'POST'; await $api(url,{method,body});S.editing=null;S.genaiCfg=await $api('/genai/configs');sm('gm','✅ Modelo '+(isEdit?'atualizado':'salvo')+' com sucesso!','s');R()}catch(e){sm('gm',e.message,'e');btn.disabled=false;btn.textContent=isEdit?'Salvar Alterações':'Salvar Modelo'}}