Vue.component('device-zabbix-consolidation', { template: `

Lade und vergleiche Daten von TheTool und Zabbix...

Lat: {{ mapModal.markerCoords ? mapModal.markerCoords.lat.toFixed(6) : 'N/A' }}, Lng: {{ mapModal.markerCoords ? mapModal.markerCoords.lng.toFixed(6) : 'N/A' }}

Bitte wählen Sie ein Template für das Gerät {{ zabbixCreateModal.deviceName }}.

`, data() { return { loading: true, window: window, zabbixUrl: 'https://monitoring.xinon.at', results: {}, sections: { inZabbixOnly: { title: 'Geräte in Zabbix, aber nicht in TheTool', isOpen: false, headerClass: 'bg-warning' }, inTheToolOnly: { title: 'Geräte in TheTool, aber nicht in Zabbix', isOpen: false, headerClass: 'bg-info' }, mismatchedNames: { title: 'Abweichende Namen (IP-basiert)', isOpen: false, headerClass: 'bg-secondary text-white' }, noSnmp: { title: 'Geräte in Zabbix ohne SNMP Template', isOpen: false, headerClass: 'bg-light' }, mismatchedCoords: { title: 'Abweichende Koordinaten', isOpen: false, headerClass: 'bg-danger text-white' }, noCoordsInZabbix: { title: 'Geräte in Zabbix ohne Koordinaten', isOpen: false, headerClass: 'bg-purple text-white' } }, mapModal: { show: false, loading: false, host: null, theToolDevice: null, map: null, marker: null, markerCoords: null, updateTheToolCoords: false, deviceHasPop: false }, zabbixCreateModal: { show: false, loading: false, loadingId: null, deviceId: null, deviceName: '', templates: [], selectedTemplateId: null } }; }, async mounted() { await this.refreshData(); }, methods: { toggleSection(key) { this.sections[key].isOpen = !this.sections[key].isOpen; }, createDeviceFromZabbix(host) { const params = new URLSearchParams(); params.append('name', host.name); params.append('ip', host.host); window.open(`${window.TT_CONFIG.BASE_URL}/Device/add?${params.toString()}`, '_blank'); }, async openCreateZabbixHostModal(deviceId) { const device = this.results.inTheToolOnly.find(d => d.id === deviceId); if (!device) return; this.zabbixCreateModal.deviceId = deviceId; this.zabbixCreateModal.deviceName = device.data.name; this.zabbixCreateModal.loading = true; this.zabbixCreateModal.show = true; try { const response = await axios.get(`${window.TT_CONFIG.API_URL}?do=getZabbixTemplates`); this.zabbixCreateModal.templates = response.data; } catch (e) { window.notify('error', 'Fehler beim Laden der Zabbix Templates.'); this.zabbixCreateModal.show = false; } finally { this.zabbixCreateModal.loading = false; } }, async submitCreateZabbixHost() { if (!this.zabbixCreateModal.selectedTemplateId) { return window.notify('error', 'Bitte wählen Sie ein Template aus.'); } this.zabbixCreateModal.loading = true; this.zabbixCreateModal.loadingId = this.zabbixCreateModal.deviceId; try { const response = await axios.post(`${window.TT_CONFIG.API_URL}?do=createZabbixHost`, { deviceId: this.zabbixCreateModal.deviceId, templateIds: this.zabbixCreateModal.selectedTemplateId }); if (response.data.success) { window.notify('success', response.data.message); this.zabbixCreateModal.show = false; await this.refreshData(); } else { window.notify('error', response.data.message); } } catch (e) { window.notify('error', 'Ein Fehler ist aufgetreten.'); } finally { this.zabbixCreateModal.loading = false; this.zabbixCreateModal.loadingId = null; this.zabbixCreateModal.deviceId = null; this.zabbixCreateModal.selectedTemplateId = null; } }, openMapModal(host, theToolDevice = null) { this.mapModal.host = host; this.mapModal.theToolDevice = theToolDevice; this.mapModal.deviceHasPop = !!(theToolDevice && theToolDevice.data && theToolDevice.data.pop_id); this.mapModal.updateTheToolCoords = false; this.mapModal.show = true; this.$nextTick(this.initMap); }, async initMap() { if (typeof L === 'undefined' || typeof window.GeoSearch === 'undefined') { await this.loadScripts(); } if (this.mapModal.map) { this.mapModal.map.remove(); } const ttDevice = this.mapModal.theToolDevice; const zbxHost = this.mapModal.host; let initialLat = 47.0707; // Default to Graz let initialLon = 15.4395; let zoom = 13; const ttDeviceLat = ttDevice?.data?.pop?.gps_lat ?? ttDevice?.data?.gps_lat; const ttDeviceLon = ttDevice?.data?.pop?.gps_long ?? ttDevice?.data?.gps_long; if (ttDevice && parseFloat(ttDeviceLat) && parseFloat(ttDeviceLon)) { initialLat = parseFloat(ttDeviceLat); initialLon = parseFloat(ttDeviceLon); zoom = 16; } else if (zbxHost.inventory && parseFloat(zbxHost.inventory.location_lat) && parseFloat(zbxHost.inventory.location_lon)) { initialLat = parseFloat(zbxHost.inventory.location_lat); initialLon = parseFloat(zbxHost.inventory.location_lon); zoom = 16; } this.mapModal.map = L.map(this.$refs.leafletMap).setView([initialLat, initialLon], zoom); L.tileLayer('https://{s}.tile.openstreetmap.org/{z}/{x}/{y}.png', { attribution: '© OpenStreetMap contributors' }).addTo(this.mapModal.map); const searchControl = new window.GeoSearch.GeoSearchControl({ provider: new window.GeoSearch.OpenStreetMapProvider(), style: 'bar', showMarker: false, autoClose: true, }); this.mapModal.map.addControl(searchControl); this.mapModal.marker = L.marker([initialLat, initialLon], { draggable: true }).addTo(this.mapModal.map); this.mapModal.markerCoords = this.mapModal.marker.getLatLng(); this.mapModal.marker.on('dragend', (event) => this.mapModal.markerCoords = event.target.getLatLng()); this.mapModal.map.on('click', (e) => { this.mapModal.marker.setLatLng(e.latlng); this.mapModal.markerCoords = e.latlng; }); this.mapModal.map.on('geosearch/showlocation', (result) => { const latLng = L.latLng(result.location.y, result.location.x); this.mapModal.marker.setLatLng(latLng); this.mapModal.markerCoords = latLng; }); setTimeout(() => this.mapModal.map.invalidateSize(), 100); }, async saveCoordinates() { this.mapModal.loading = true; const coords = this.mapModal.marker.getLatLng(); let allSuccess = true; try { const zabbixResponse = await axios.post(`${window.TT_CONFIG.API_URL}?do=updateZabbixCoordinates`, { hostId: this.mapModal.host.hostid, lat: coords.lat, lon: coords.lng }); if (!zabbixResponse.data.success) { allSuccess = false; window.notify('error', 'Fehler beim Speichern der Zabbix-Koordinaten: ' + zabbixResponse.data.message); } } catch (error) { allSuccess = false; window.notify('error', 'Fehler beim Speichern der Zabbix-Koordinaten.'); } if (this.mapModal.updateTheToolCoords && this.mapModal.theToolDevice && allSuccess) { try { const theToolResponse = await axios.post(`${window.TT_CONFIG.API_URL}?do=updateTheToolCoordinates`, { deviceId: this.mapModal.theToolDevice.id, lat: coords.lat, lon: coords.lng }); if (!theToolResponse.data.success) { allSuccess = false; window.notify('error', 'Fehler beim Speichern der TheTool-Koordinaten: ' + theToolResponse.data.message); } } catch (e) { allSuccess = false; window.notify('error', 'Fehler beim Speichern der TheTool-Koordinaten.'); } } if(allSuccess) { window.notify('success', 'Koordinaten erfolgreich gespeichert.'); this.mapModal.show = false; await this.refreshData(); } this.mapModal.loading = false; }, async refreshData() { this.loading = true; try { const response = await axios.post(`${window.TT_CONFIG.API_URL}?do=getZabbixConsolidationData`); this.results = response.data; } catch (error) { window.notify('error', 'Fehler beim Aktualisieren der Daten.'); } finally { this.loading = false; } }, loadScripts() { const scripts = [ { type: 'link', url: 'https://unpkg.com/leaflet@1.9.4/dist/leaflet.css' }, { type: 'link', url: 'https://unpkg.com/leaflet-geosearch@3.0.0/dist/geosearch.css' }, { type: 'script', url: 'https://unpkg.com/leaflet@1.9.4/dist/leaflet.js' }, { type: 'script', url: 'https://unpkg.com/leaflet-geosearch@latest/dist/bundle.min.js' }, ]; const promises = scripts.map(s => new Promise((resolve, reject) => { let el; if (document.querySelector(`[href="${s.url}"], [src="${s.url}"]`)) { resolve(); return; } if (s.type === 'script') { el = document.createElement('script'); el.src = s.url; el.async = false; el.onload = resolve; el.onerror = reject; } else { el = document.createElement('link'); el.rel = 'stylesheet'; el.href = s.url; resolve(); } if (el) document.head.appendChild(el); else reject(); })); return Promise.all(promises); }, } });