tool per ticket automatici

This commit is contained in:
2026-07-05 23:33:52 +02:00
parent fb67a277e5
commit e55cccbaa5
7 changed files with 400 additions and 10 deletions
+54 -2
View File
@@ -5,6 +5,8 @@
const TicketBulkView = {
rowCount: 0,
activeRequests: false,
savedRows: null,
rowAttachments: {},
async render() {
const container = document.getElementById('view-container');
@@ -196,6 +198,10 @@ const TicketBulkView = {
</td>
<td style="text-align:center;">
<div class="row-actions">
<button type="button" class="btn btn-ghost btn-xs" id="bulk-attach-btn-${id}" title="Allega file" style="position:relative; display:inline-flex; align-items:center; gap:2px; height:24px; padding:0 6px;">
📎 <span class="badge-attachments-count" id="bulk-attach-badge-${id}" style="display:none; font-size:10px;">0</span>
</button>
<input type="file" id="bulk-file-input-${id}" multiple style="display:none;" />
<button class="btn btn-ghost btn-xs" id="bulk-expand-btn-${id}" title="Opzioni avanzate">
<svg viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" style="width:14px;height:14px;">
<path d="M12 5v14M5 12h14"/>
@@ -238,6 +244,48 @@ const TicketBulkView = {
container.appendChild(tr);
container.appendChild(trExp);
// Initialize attachments for this row
this.rowAttachments[id] = savedData ? (savedData.attachments || []) : [];
// Bind attachment click and input change
const attachBtn = tr.querySelector(`#bulk-attach-btn-${id}`);
const fileInput = tr.querySelector(`#bulk-file-input-${id}`);
const attachBadge = tr.querySelector(`#bulk-attach-badge-${id}`);
const updateBadge = () => {
const count = (this.rowAttachments[id] || []).length;
if (attachBadge) {
attachBadge.textContent = count;
attachBadge.style.display = count > 0 ? 'inline-block' : 'none';
}
};
if (attachBtn && fileInput) {
attachBtn.addEventListener('click', () => fileInput.click());
fileInput.addEventListener('change', (e) => {
const files = Array.from(e.target.files);
for (const file of files) {
const reader = new FileReader();
reader.onload = () => {
const base64Data = reader.result.split(',')[1];
if (!this.rowAttachments[id]) {
this.rowAttachments[id] = [];
}
this.rowAttachments[id].push({
filename: file.name,
content: base64Data,
content_type: file.type
});
updateBadge();
this.saveState();
};
reader.readAsDataURL(file);
}
fileInput.value = '';
});
}
// Populate with savedData if available, otherwise set default values
if (savedData) {
tr.querySelector(`#bulk-state-${id}`).value = savedData.state_id;
@@ -367,6 +415,7 @@ const TicketBulkView = {
input.addEventListener('change', () => this.saveState());
});
updateBadge();
this.saveState();
},
@@ -430,7 +479,8 @@ const TicketBulkView = {
company_display,
isExpanded,
statusDotClass,
statusDotTitle
statusDotTitle,
attachments: this.rowAttachments[id] || []
});
});
this.savedRows = data;
@@ -658,7 +708,8 @@ const TicketBulkView = {
customer_id: customerId || undefined,
customer_user_id: customerUserId || undefined,
subject: subject || undefined,
body: body || undefined
body: body || undefined,
attachments: (this.rowAttachments[id] || []).length > 0 ? this.rowAttachments[id] : undefined
}
});
});
@@ -707,6 +758,7 @@ const TicketBulkView = {
if (failCount === 0) {
Toast.success(`Tutti i ${successCount} ticket sono stati creati con successo!`);
this.savedRows = [];
this.rowAttachments = {};
setTimeout(() => {
window.location.hash = '#/tickets';
}, 1500);