Merge branch 'Cpeprovisioning/add-acs-implementation' into 'master'

Implement debounced MAC address processing and enhance RADIUS user creation...

See merge request fronk/thetool!1912
This commit is contained in:
Luca Haid
2025-12-01 11:11:09 +00:00

View File

@@ -116,14 +116,9 @@ Vue.component('Cpeprovisioning', {
<tt-button text="In Radius anlegen"
@click="createRadiusUser(item)"
:disabled="!isValidMac(item.cpe_data.mac)"
:loading="item.isCreatingRadius"
sm
additional-class="btn-primary" />
<tt-button text="ACS Auto VLAN Zuweisung testen"
@click="testAcsVlan(item)"
:disabled="!isVlanSelected(item) || !isValidMac(item.cpe_data.mac)"
sm
additional-class="btn-info mt-2" />
additional-class="btn-primary"
title="Sendet Kundendaten an Chrome Extension" />
</div>
<div class="finish-wrapper mt-auto">
<label class="col-form-label col-form-label-sm">Konfig abgeschlossen</label>
@@ -180,6 +175,7 @@ Vue.component('Cpeprovisioning', {
page: 1,
pagination: {},
debouncedFetchData: null,
debouncedMacHandlers: {}, // Store debounced handlers per item
extensionId: 'jglijfiddilckddlmbnlojmmlahboffh',
showExtensionIdModal: false,
processingMacItems: new Set() // Track items currently being processed
@@ -261,7 +257,6 @@ Vue.component('Cpeprovisioning', {
...item,
isDirty: false,
isSaving: false,
isCreatingRadius: false,
pop_name: item.pop_name || 'N/A',
owner_address: `${item.owner_street || ''} ${item.owner_housenumber || ''}, ${item.owner_zip || ''} ${item.owner_city || ''}`,
owner_phone: item.owner_phone || '',
@@ -350,8 +345,9 @@ Vue.component('Cpeprovisioning', {
console.log('[MAC Input] Current MAC value:', item.cpe_data.mac);
console.log('[MAC Input] Router type:', item.cpe_data.routertype);
// Check if we're already processing this item to prevent recursion
const itemKey = item.orderproduct_id;
// Check if we're already processing this item to prevent recursion
if (this.processingMacItems.has(itemKey)) {
console.log('[MAC Input] Already processing this item, returning to prevent recursion');
return;
@@ -359,7 +355,18 @@ Vue.component('Cpeprovisioning', {
this.markDirty(item);
this.processMacAddress(item);
// Create a debounced handler for this item if it doesn't exist
if (!this.debouncedMacHandlers[itemKey]) {
console.log('[MAC Input] Creating debounced handler for item:', itemKey);
this.debouncedMacHandlers[itemKey] = _.debounce((itm) => {
console.log('[MAC Input] Debounced handler executing for item:', itemKey);
this.processMacAddress(itm);
}, 300); // 300ms delay to wait for barcode scanner to finish
}
// Call the debounced handler
console.log('[MAC Input] Calling debounced handler');
this.debouncedMacHandlers[itemKey](item);
},
handleRouterTypeChange(item) {
console.log('[Router Type Change] Router type changed, checking if MAC needs processing');
@@ -370,6 +377,10 @@ Vue.component('Cpeprovisioning', {
const routerType = item.cpe_data.routertype;
const itemKey = item.orderproduct_id;
console.log('[MAC Process] === START processMacAddress ===');
console.log('[MAC Process] Input value:', inputValue);
console.log('[MAC Process] Router type:', routerType);
// Only process if it's a QR code format (contains dash, no colons)
// This prevents reprocessing already formatted MAC addresses
if (!inputValue) {
@@ -399,6 +410,13 @@ Vue.component('Cpeprovisioning', {
// Mark this item as being processed
this.processingMacItems.add(itemKey);
console.log('[MAC Process] Added item to processing set:', itemKey);
// Safety timeout to ensure we don't get stuck in processing state
const safetyTimeout = setTimeout(() => {
console.log('[MAC Process] Safety timeout - removing item from processing set:', itemKey);
this.processingMacItems.delete(itemKey);
}, 2000);
try {
// Parse MAC from QR code
@@ -407,6 +425,7 @@ Vue.component('Cpeprovisioning', {
if (!parsedMac) {
console.log('[MAC Process] Failed to parse MAC from QR code');
window.notify('error', 'Konnte MAC-Adresse nicht aus QR-Code parsen');
clearTimeout(safetyTimeout);
this.processingMacItems.delete(itemKey);
return;
}
@@ -431,8 +450,10 @@ Vue.component('Cpeprovisioning', {
// Force Vue to update the DOM
this.$nextTick(() => {
console.log('[MAC Process] After nextTick, MAC value is:', item.cpe_data.mac);
// Remove from processing set after DOM update
// Clear safety timeout and remove from processing set
clearTimeout(safetyTimeout);
this.processingMacItems.delete(itemKey);
console.log('[MAC Process] Removed item from processing set after nextTick:', itemKey);
});
// Show notification
@@ -441,6 +462,7 @@ Vue.component('Cpeprovisioning', {
} catch (error) {
console.error('[MAC Process] Error processing MAC:', error);
clearTimeout(safetyTimeout);
this.processingMacItems.delete(itemKey);
}
@@ -465,55 +487,61 @@ Vue.component('Cpeprovisioning', {
item.cpe_data = { ...item.cpe_data }; // Trigger reactivity
}
},
isVlanSelected(item) {
return item.vlans && Object.values(item.vlans).some(v => v.checked);
},
async createRadiusUser(item) {
// Disable button during request
this.$set(item, 'isCreatingRadius', true);
createRadiusUser(item) {
console.log('[Create Radius User] === START ===');
console.log('[Create Radius User] Item:', item);
try {
const { data } = await axios.post(window.TT_CONFIG.CPE_PROV_API_CREATE_RADIUS_USER_URL, {
mac: item.cpe_data.mac
});
// Prepare the data to send to the Chrome extension
const customerNumber = item.owner_customer_number || 'N/A';
const macAddress = item.cpe_data.mac;
const address = item.owner_full_address || 'N/A';
const customerName = item.customer || 'N/A';
const productName = item.product_name || 'N/A';
if (data.success) {
window.notify('success', `RADIUS User erfolgreich angelegt! Kundennr: ${data.data.customer_number}`);
console.log('RADIUS User created:', data.data);
} else {
window.notify('error', data.message || 'Fehler beim Anlegen des RADIUS Users.');
console.log('[Create Radius User] Customer Number:', customerNumber);
console.log('[Create Radius User] MAC Address:', macAddress);
console.log('[Create Radius User] Address:', address);
console.log('[Create Radius User] Customer Name:', customerName);
console.log('[Create Radius User] Product Name:', productName);
window.notify('info', 'Sende Daten an Chrome Extension...');
const extensionId = this.extensionId;
const message = {
type: "CREATE_RADIUS_USER",
payload: {
customerNumber: customerNumber,
macAddress: macAddress,
address: address,
customerName: customerName,
productName: productName
}
} catch (error) {
const errorMsg = error.response?.data?.message || 'Ein unerwarteter Fehler ist aufgetreten.';
window.notify('error', errorMsg);
console.error('Error creating RADIUS user:', error);
} finally {
this.$set(item, 'isCreatingRadius', false);
}
},
async testAcsVlan(item) {
const button = this.$el.querySelector(`[data-orderproduct-id="${item.orderproduct_id}"] .btn-info`);
if (button) {
button.disabled = true;
};
console.log('[Create Radius User] Extension ID:', extensionId);
console.log('[Create Radius User] Message:', message);
if (window.chrome && chrome.runtime && chrome.runtime.sendMessage) {
try {
chrome.runtime.sendMessage(extensionId, message, (response) => {
if (chrome.runtime.lastError) {
console.warn('[Create Radius User] Senden an Erweiterung fehlgeschlagen:', chrome.runtime.lastError.message);
window.notify('warning', 'Daten konnten nicht an die Erweiterung gesendet werden. (Drücke STRG + ALT + E zum Konfigurieren)');
} else {
console.log('[Create Radius User] Erweiterung hat geantwortet:', response);
window.notify('success', 'Daten erfolgreich an Chrome Extension gesendet!');
}
});
} catch (e) {
console.error('[Create Radius User] Fehler beim Senden an die Erweiterung:', e);
window.notify('error', 'Fehler beim Senden an die Erweiterung.');
}
} else {
console.warn('[Create Radius User] Chrome Extension Messaging API nicht verfügbar.');
window.notify('warning', 'Chrome Messaging API nicht gefunden.');
}
try {
const { data } = await axios.post(window.TT_CONFIG.CPE_PROV_API_TEST_ACS_VLAN_URL, {
mac: item.cpe_data.mac
});
if (data.success) {
window.notify('success', `ACS VLAN Zuweisung erfolgreich: VLAN ${data.vlan_id}`);
} else {
window.notify('error', data.message || 'Fehler bei der ACS VLAN Zuweisung.');
}
} catch (error) {
window.notify('error', 'Ein unerwarteter Fehler ist aufgetreten.');
} finally {
if (button) {
button.disabled = false;
}
}
console.log('[Create Radius User] === END ===');
},
_buildSavePayload(item) {
return {