[FIX] ARIA: mappa navigazione reale + contesto pagina (ticket #424)
ARIA citava voci di menu inesistenti (es. 'A4 - Analisi e Valutazione del Rischio' / 'Fase 4.1 - Inventario') non corrispondenti alla barra laterale, e non sapeva da quale pagina scrivesse l'utente. - AIService::askWithRag: iniettata la mappa REALE della sidebar (navigationMapBlock, sincronizzata con common-bi.js) con regole che vietano di inventare menu/fasi/codici; aggiunto contesto pagina utente. - AiController::ask: accetta e passa il campo 'page' dal frontend. - common.js (ARIA FAB): invia la pagina corrente in /api/ai/ask. - Cache-buster common.js 20260623->20260623h su tutte le pagine. NB: questo commit include anche il fix #419 gia' applicato e live in common.js (email bug-reporter recuperata via api.getMe quando assente nelle claims JWT), finora non committato — incluso come backup. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
co-authored by
Claude Opus 4.8
parent
d45bd472cd
commit
ea5966eaee
@@ -39,10 +39,14 @@ class AiController extends BaseController
|
|||||||
}
|
}
|
||||||
|
|
||||||
$user = $this->getCurrentUser() ?? [];
|
$user = $this->getCurrentUser() ?? [];
|
||||||
|
// Pagina corrente (facoltativa) inviata dal frontend, per dare ad ARIA
|
||||||
|
// contesto sulla schermata da cui l'utente sta scrivendo (ticket #424).
|
||||||
|
$page = mb_substr(trim((string) $this->getParam('page', '')), 0, 120);
|
||||||
$userContext = [
|
$userContext = [
|
||||||
'user_id' => $userId,
|
'user_id' => $userId,
|
||||||
'organization_id' => $this->getCurrentOrgId(), // può essere null
|
'organization_id' => $this->getCurrentOrgId(), // può essere null
|
||||||
'consulting_firm_id' => $user['consulting_firm_id'] ?? null,
|
'consulting_firm_id' => $user['consulting_firm_id'] ?? null,
|
||||||
|
'page' => $page,
|
||||||
];
|
];
|
||||||
|
|
||||||
try {
|
try {
|
||||||
|
|||||||
@@ -56,6 +56,30 @@ class AIService
|
|||||||
. "5. ENISA, NIST e ISO sono best practice di settore, NON fonti normative vincolanti: gli obblighi italiani derivano da Direttiva (UE) 2022/2555, D.Lgs. 138/2024 e Determinazioni ACN.\n";
|
. "5. ENISA, NIST e ISO sono best practice di settore, NON fonti normative vincolanti: gli obblighi italiani derivano da Direttiva (UE) 2022/2555, D.Lgs. 138/2024 e Determinazioni ACN.\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Mappa REALE della barra laterale dell'applicazione, da iniettare nel
|
||||||
|
* system prompt dell'assistente ARIA cosi' che le indicazioni di navigazione
|
||||||
|
* usino i nomi ESATTI del menu e non vengano inventati moduli/fasi inesistenti.
|
||||||
|
*
|
||||||
|
* ⚠️ TENERE SINCRONIZZATA con la fonte di verita' della sidebar:
|
||||||
|
* public/js/common-bi.js (array navItems). Se aggiungi/rinomini una voce
|
||||||
|
* di menu li', aggiorna anche questo elenco.
|
||||||
|
* (Ticket #424, 2026-06-23: ARIA citava voci di menu inesistenti.)
|
||||||
|
*/
|
||||||
|
private function navigationMapBlock(): string
|
||||||
|
{
|
||||||
|
return "\n## MAPPA DELLA NAVIGAZIONE (barra laterale REALE dell'app)\n"
|
||||||
|
. "Sezione \"Principale\": Dashboard · Calendario · Compliance Journey · Gap Analysis · Misure e Requisiti · Modello SGSI (ISO 27001).\n"
|
||||||
|
. "Sezione \"Gestione\": Organigramma · Competenze · Rischi · Incidenti · Policy · Supply Chain · Stakeholder · Attivita' stakeholder · Segnalazioni · Normative · AI Cross-Analysis · Knowledge Base.\n"
|
||||||
|
. "Sezione \"Operativo\": Formazione · Inventario · Audit interni · Controlli periodici · Riesame di Direzione · Audit & Report.\n"
|
||||||
|
. "Sezione \"Sistema\": Guida all'uso · Impostazioni · Architettura · Simulazione Demo · Integrazioni Esterne.\n"
|
||||||
|
. "\nREGOLE DI NAVIGAZIONE (vincolanti):\n"
|
||||||
|
. "1. Quando indichi DOVE cliccare o COME raggiungere una funzione, usa ESCLUSIVAMENTE i nomi delle voci qui sopra, esattamente come scritti, indicando la sezione (es. \"nella sezione Operativo, voce Inventario\").\n"
|
||||||
|
. "2. NON inventare nomi di menu, \"fasi\", codici (es. \"A4\", \"Fase 4.1\") o moduli che NON compaiono in questo elenco.\n"
|
||||||
|
. "3. L'inventario degli asset si trova in: sezione Operativo > Inventario. La valutazione del rischio in: sezione Gestione > Rischi. Misure e requisiti in: sezione Principale > Misure e Requisiti.\n"
|
||||||
|
. "4. Se l'utente cerca una funzione che non corrisponde ad alcuna voce, dillo chiaramente e suggerisci la voce piu' vicina, senza inventarne una.\n";
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Analizza risultati gap analysis e genera raccomandazioni
|
* Analizza risultati gap analysis e genera raccomandazioni
|
||||||
*/
|
*/
|
||||||
@@ -702,9 +726,20 @@ PROMPT;
|
|||||||
error_log('[AIService::askWithRag] RAG failed, fallback diretto: ' . $e->getMessage());
|
error_log('[AIService::askWithRag] RAG failed, fallback diretto: ' . $e->getMessage());
|
||||||
}
|
}
|
||||||
|
|
||||||
$systemPrompt = "Sei un esperto consulente di cybersecurity NIS2 (EU 2022/2555) e D.Lgs. 138/2024.\n"
|
$systemPrompt = "Sei ARIA, l'assistente dell'applicazione NIS2 Agile, esperta di cybersecurity NIS2 (EU 2022/2555) e D.Lgs. 138/2024.\n"
|
||||||
. "Rispondi in modo preciso e cita le fonti del contesto quando rilevanti.\n"
|
. "Rispondi in modo preciso e cita le fonti del contesto quando rilevanti.\n"
|
||||||
. $this->authoritativeSourcesBlock();
|
. $this->authoritativeSourcesBlock()
|
||||||
|
. $this->navigationMapBlock();
|
||||||
|
|
||||||
|
// Pagina corrente dell'utente (se inviata dal frontend): aiuta ARIA a
|
||||||
|
// dare indicazioni contestuali invece di rimandare a moduli a caso.
|
||||||
|
$page = trim((string) ($userContext['page'] ?? ''));
|
||||||
|
if ($page !== '') {
|
||||||
|
$systemPrompt .= "\n## CONTESTO UTENTE\n"
|
||||||
|
. "L'utente si trova attualmente nella pagina: \"" . $page . "\". "
|
||||||
|
. "Tieni conto di dove si trova quando dai indicazioni di navigazione.\n";
|
||||||
|
}
|
||||||
|
|
||||||
if (!empty($contextBlock)) {
|
if (!empty($contextBlock)) {
|
||||||
$systemPrompt .= "\n## Contesto documentale (knowledge base)\n" . $contextBlock
|
$systemPrompt .= "\n## Contesto documentale (knowledge base)\n" . $contextBlock
|
||||||
. "\n\nQuando rispondi, cita esplicitamente i numeri tra parentesi quadre [1], [2], ... che corrispondono ai documenti del contesto.";
|
. "\n\nQuando rispondi, cita esplicitamente i numeri tra parentesi quadre [1], [2], ... che corrispondono ai documenti del contesto.";
|
||||||
|
|||||||
@@ -71,7 +71,7 @@
|
|||||||
|
|
||||||
<!-- Stessa logica della app: api.js + common.js (helper) + common-bi.js (override BI) -->
|
<!-- Stessa logica della app: api.js + common.js (helper) + common-bi.js (override BI) -->
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script src="js/common-bi.js?v=20260631"></script>
|
<script src="js/common-bi.js?v=20260631"></script>
|
||||||
<script>
|
<script>
|
||||||
// Renderizza la sidebar BI (loadSidebar è stato ridefinito da common-bi.js)
|
// Renderizza la sidebar BI (loadSidebar è stato ridefinito da common-bi.js)
|
||||||
|
|||||||
@@ -318,7 +318,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260620"></script>
|
<script src="/js/api.js?v=20260620"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -148,7 +148,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="../js/api.js?v=20260620"></script>
|
<script src="../js/api.js?v=20260620"></script>
|
||||||
<script src="../js/common.js?v=20260623"></script>
|
<script src="../js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -170,7 +170,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="../js/api.js?v=20260620"></script>
|
<script src="../js/api.js?v=20260620"></script>
|
||||||
<script src="../js/common.js?v=20260623"></script>
|
<script src="../js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -1091,7 +1091,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="js/i18n.js?v=20260631"></script>
|
<script src="js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -155,7 +155,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
+1
-1
@@ -362,7 +362,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260623g"></script>
|
<script src="/js/api.js?v=20260623g"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -152,7 +152,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -350,7 +350,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle + override sidebar BI (common-bi.js dopo common.js: ridefinisce solo loadSidebar) -->
|
<!-- Bootstrap Italia bundle + override sidebar BI (common-bi.js dopo common.js: ridefinisce solo loadSidebar) -->
|
||||||
<script src="vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script>if (window.bootstrap && bootstrap.loadFonts) { bootstrap.loadFonts('vendor/bootstrap-italia/dist/fonts'); }</script>
|
<script>if (window.bootstrap && bootstrap.loadFonts) { bootstrap.loadFonts('vendor/bootstrap-italia/dist/fonts'); }</script>
|
||||||
|
|||||||
@@ -184,7 +184,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -137,7 +137,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -383,7 +383,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -144,7 +144,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
+1
-1
@@ -1143,7 +1143,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (accordion) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (accordion) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI. -->
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI. -->
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
|
|||||||
@@ -352,7 +352,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -912,7 +912,7 @@ curl -H <span class="str">"X-API-Key: nis2_TUA_CHIAVE"</span> \
|
|||||||
|
|
||||||
</main>
|
</main>
|
||||||
|
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script src="js/i18n.js?v=20260631"></script>
|
<script src="js/i18n.js?v=20260631"></script>
|
||||||
<script>
|
<script>
|
||||||
function showTab(id) {
|
function showTab(id) {
|
||||||
|
|||||||
@@ -140,7 +140,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
+1
-1
@@ -185,7 +185,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
+31
-17
@@ -952,22 +952,33 @@ function switchLang(lang) {
|
|||||||
// ── 1. Inietta il bug-reporter Nexus ────────────────────────────────────
|
// ── 1. Inietta il bug-reporter Nexus ────────────────────────────────────
|
||||||
if (!window.__nexusWidgetLoaded) {
|
if (!window.__nexusWidgetLoaded) {
|
||||||
window.__nexusWidgetLoaded = true;
|
window.__nexusWidgetLoaded = true;
|
||||||
var s = document.createElement('script');
|
// [#419 fix] L'email NON e' nelle claims del JWT NIS2 (claims.email vuoto) → se manca,
|
||||||
s.src = 'js/bug-reporter.js?v=20260613';
|
// recuperala dal profilo via api.getMe() PRIMA di iniettare. Senza email il widget crea
|
||||||
s.async = true;
|
// ticket con richiedente vuoto → invisibili in "Le mie segnalazioni". Fallback safe = prec.
|
||||||
s.dataset.product = 'NIS2';
|
var _injectBugReporter = function (email, name) {
|
||||||
s.dataset.tenantId = '7';
|
var s = document.createElement('script');
|
||||||
s.dataset.apiUrl = 'https://agilehub.agile.software';
|
s.src = 'js/bug-reporter.js?v=20260623';
|
||||||
// X-API-Key per il gateway ticket AgileHub. Senza, il widget riceve 401
|
s.async = true;
|
||||||
// "Header X-API-Key o Authorization: Bearer richiesto". Valorizzare con la
|
s.dataset.product = 'NIS2';
|
||||||
// chiave NIS2 emessa da AgileHub (prodotto NIS2, tenant 7). Inietta via
|
s.dataset.tenantId = '7';
|
||||||
// window.NEXUS_WIDGET_API_KEY oppure hardcoda qui quando disponibile.
|
s.dataset.apiUrl = 'https://agilehub.agile.software';
|
||||||
s.dataset.apiKey = (window.NEXUS_WIDGET_API_KEY || 'nis2_ak_dev_109b4bb54557c4ab3bdbed45');
|
s.dataset.apiKey = (window.NEXUS_WIDGET_API_KEY || 'nis2_ak_dev_109b4bb54557c4ab3bdbed45');
|
||||||
s.dataset.userName = userName;
|
s.dataset.userName = name || userName || '';
|
||||||
s.dataset.userEmail = userEmail;
|
s.dataset.userEmail = email || userEmail || '';
|
||||||
s.dataset.userRole = userRole;
|
s.dataset.userRole = userRole;
|
||||||
s.dataset.lang = 'it';
|
s.dataset.lang = 'it';
|
||||||
document.body.appendChild(s);
|
document.body.appendChild(s);
|
||||||
|
};
|
||||||
|
if (userEmail) {
|
||||||
|
_injectBugReporter(userEmail, userName);
|
||||||
|
} else if (typeof api !== 'undefined' && typeof api.getMe === 'function') {
|
||||||
|
api.getMe().then(function (r) {
|
||||||
|
var u = (r && r.data) || {};
|
||||||
|
_injectBugReporter(u.email || '', u.full_name || u.name || '');
|
||||||
|
}).catch(function () { _injectBugReporter('', ''); });
|
||||||
|
} else {
|
||||||
|
_injectBugReporter('', '');
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// ── 2. AI Chat FAB viola "ARIA" ─────────────────────────────────────────
|
// ── 2. AI Chat FAB viola "ARIA" ─────────────────────────────────────────
|
||||||
@@ -1118,6 +1129,9 @@ function switchLang(lang) {
|
|||||||
// AI nativa NIS2 (RAG con KB Multi-Livello già attivo)
|
// AI nativa NIS2 (RAG con KB Multi-Livello già attivo)
|
||||||
var t = localStorage.getItem('nis2_access_token') || '';
|
var t = localStorage.getItem('nis2_access_token') || '';
|
||||||
var orgId = localStorage.getItem('nis2_org_id') || '';
|
var orgId = localStorage.getItem('nis2_org_id') || '';
|
||||||
|
// Pagina corrente: aiuta ARIA a dare indicazioni contestuali (ticket #424).
|
||||||
|
var pageName = (document.title || '').replace(/\s*[—|·-]\s*NIS2.*$/i, '').trim()
|
||||||
|
|| (location.pathname.split('/').pop() || '');
|
||||||
var r = await fetch('/api/ai/ask', {
|
var r = await fetch('/api/ai/ask', {
|
||||||
method: 'POST',
|
method: 'POST',
|
||||||
headers: {
|
headers: {
|
||||||
@@ -1125,7 +1139,7 @@ function switchLang(lang) {
|
|||||||
'Authorization': t ? ('Bearer ' + t) : '',
|
'Authorization': t ? ('Bearer ' + t) : '',
|
||||||
'X-Organization-Id': orgId
|
'X-Organization-Id': orgId
|
||||||
},
|
},
|
||||||
body: JSON.stringify({ question: text, history: history })
|
body: JSON.stringify({ question: text, history: history, page: pageName })
|
||||||
});
|
});
|
||||||
var resp = await r.json();
|
var resp = await r.json();
|
||||||
var answer = (resp && resp.success && resp.data
|
var answer = (resp && resp.success && resp.data
|
||||||
|
|||||||
+1
-1
@@ -151,7 +151,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<!-- Stessa logica JS della pagina live (parita' funzionale assoluta, zero backend). -->
|
<!-- Stessa logica JS della pagina live (parita' funzionale assoluta, zero backend). -->
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI. -->
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI. -->
|
||||||
|
|||||||
+1
-1
@@ -95,7 +95,7 @@
|
|||||||
|
|
||||||
<!-- Stessa logica della login attuale: ZERO modifiche backend -->
|
<!-- Stessa logica della login attuale: ZERO modifiche backend -->
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script>
|
<script>
|
||||||
if (api.isAuthenticated()) { window.location.href = 'dashboard.html'; }
|
if (api.isAuthenticated()) { window.location.href = 'dashboard.html'; }
|
||||||
|
|
||||||
|
|||||||
@@ -127,7 +127,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -168,7 +168,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -426,6 +426,6 @@ curl https://nis2.agile.software/api/services/status</pre>
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
</div>
|
</div>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
</body>
|
</body>
|
||||||
</html>
|
</html>
|
||||||
|
|||||||
@@ -113,7 +113,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -495,7 +495,7 @@
|
|||||||
|
|
||||||
<!-- Stessa logica della onboarding.html: ZERO modifiche backend -->
|
<!-- Stessa logica della onboarding.html: ZERO modifiche backend -->
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script>
|
<script>
|
||||||
// ── Auth check ──────────────────────────────────────────────────
|
// ── Auth check ──────────────────────────────────────────────────
|
||||||
if (!checkAuth()) throw new Error('Not authenticated');
|
if (!checkAuth()) throw new Error('Not authenticated');
|
||||||
|
|||||||
@@ -139,7 +139,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -334,7 +334,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
+1
-1
@@ -132,7 +132,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -269,7 +269,7 @@
|
|||||||
|
|
||||||
<!-- Stessa logica della register.html: ZERO modifiche backend -->
|
<!-- Stessa logica della register.html: ZERO modifiche backend -->
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script>
|
<script>
|
||||||
if (api.isAuthenticated()) { window.location.href = 'dashboard.html'; }
|
if (api.isAuthenticated()) { window.location.href = 'dashboard.html'; }
|
||||||
|
|
||||||
|
|||||||
+1
-1
@@ -444,7 +444,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -142,7 +142,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
+1
-1
@@ -495,7 +495,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -689,7 +689,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -195,7 +195,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -192,7 +192,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="/js/i18n.js?v=20260631"></script>
|
<script src="/js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
@@ -478,7 +478,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -293,7 +293,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
+1
-1
@@ -1 +1 @@
|
|||||||
{"version": "1.24.8", "build": "2026-06-23-v1.24.8", "date": "2026-06-23", "changelog": "Inventario beni — Sottoclassi: ora dalla finestra di modifica del bene si possono anche RINOMINARE e RIMUOVERE le sottoclassi create dalla propria organizzazione (prima si potevano solo aggiungere). I due nuovi link «✎ rinomina» e «🗑 rimuovi» stanno accanto a «+ aggiungi». Le sottoclassi di sistema (predefinite) restano protette e non si modificano/eliminano. Rimuovendo una sottoclasse, i beni che la usavano restano semplicemente senza sottoclasse. Risolto ticket #426."}
|
{"version": "1.24.9", "build": "2026-06-23-v1.24.9", "date": "2026-06-23", "changelog": "Assistente ARIA — Ora ARIA conosce la barra laterale REALE dell'app e, quando ti spiega dove cliccare, usa i nomi esatti delle voci di menu (es. «sezione Operativo > Inventario») senza piu' inventare moduli o «fasi» inesistenti. Inoltre riceve la pagina da cui stai scrivendo, cosi' da darti indicazioni piu' pertinenti al punto in cui ti trovi. Risolto ticket #424."}
|
||||||
|
|||||||
@@ -208,7 +208,7 @@
|
|||||||
<!-- Report Detail Modal handled by common.js showModal -->
|
<!-- Report Detail Modal handled by common.js showModal -->
|
||||||
|
|
||||||
<script src="/js/api.js?v=20260631"></script>
|
<script src="/js/api.js?v=20260631"></script>
|
||||||
<script src="/js/common.js?v=20260623"></script>
|
<script src="/js/common.js?v=20260623h"></script>
|
||||||
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
<!-- Bootstrap Italia bundle (componenti) + override sidebar BI (common-bi.js).
|
||||||
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
common-bi.js va DOPO common.js: ridefinisce solo loadSidebar() con markup BI,
|
||||||
riusando tutti gli helper di common.js (zero backend). -->
|
riusando tutti gli helper di common.js (zero backend). -->
|
||||||
|
|||||||
@@ -322,7 +322,7 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<script src="js/api.js?v=20260631"></script>
|
<script src="js/api.js?v=20260631"></script>
|
||||||
<script src="js/common.js?v=20260623"></script>
|
<script src="js/common.js?v=20260623h"></script>
|
||||||
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
<script src="/vendor/bootstrap-italia/dist/js/bootstrap-italia.bundle.min.js"></script>
|
||||||
<script src="/js/common-bi.js?v=20260631"></script>
|
<script src="/js/common-bi.js?v=20260631"></script>
|
||||||
<script src="js/i18n.js?v=20260631"></script>
|
<script src="js/i18n.js?v=20260631"></script>
|
||||||
|
|||||||
Reference in New Issue
Block a user