Audit logs stage 1: Admin > Audit Logs rebuilt on the standard list with search, sortable columns and paging, filters for date, who (agent, portal contact or ITFlow itself), client, type and action, and counted views for Changes, Deletions, Sign-ins, Security and Data out; each entry shows who with their avatar, the client, the type and action as a coloured label, the description without the name in front, the IP and device in words, and links to its record while it exists or says No longer here; a quick look with the full entry, the raw user agent, everything from that IP, the record's other entries and what the same person did 15 minutes either side; CSV/PDF export with the page's filters, view and picked columns, itself audited; new functions/audit_log.php, admin/modals/audit_log/audit_log.php and audit_log_export.php, admin/post/audit_log.php and audit_logs export columns; agent/files.php takes ?open= for a file's quick look; database 3.3.1 adds log_client_id and log_entity_id keys on logs, gives each action one name (Unarchive/Restored to Restore, Deleted, Merged, Closed, Reopened, Resolved and Sent to Delete, Merge, Close, Reopen, Resolve and Send, Client Access to Denied, saved card and payment provider Updates to Create or Delete, contract template Update to Edit, type client to Client) and repoints entries at the right record (reply edits and redactions to the ticket, API document edits to the document, reimbursements to the recording expense, API client restores to the client), guarded so it can run again; logAudit call sites in agent, admin, api, client, cron and functions use the same names and record ids

This commit is contained in:
johnnyq
2026-10-18 22:36:25 -04:00
parent ad271aaa87
commit ea23a2bad5
38 changed files with 1169 additions and 316 deletions

View File

@@ -27,7 +27,7 @@ if (!empty($client_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Contact", "Unarchive", "$client_name unarchived via API ($api_key_name)", $client_id);
logAudit("Client", "Restore", "$client_name unarchived via API ($api_key_name)", $client_id, $client_id);
}
}
}

View File

@@ -37,7 +37,7 @@ if (!empty($contact_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Contact", "Unarchive", "$contact_name unarchived via API ($api_key_name)", $client_id, $contact_id);
logAudit("Contact", "Restore", "$contact_name unarchived via API ($api_key_name)", $client_id, $contact_id);
}
}
}

View File

@@ -33,7 +33,7 @@ if (!empty($credential_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Credential", "Unarchive", "$credential_name unarchived via API ($api_key_name)", $client_id, $credential_id);
logAudit("Credential", "Restore", "$credential_name unarchived via API ($api_key_name)", $client_id, $credential_id);
}
}
}

View File

@@ -33,7 +33,7 @@ if (!empty($document_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Document", "Unarchive", "$document_name unarchived via API ($api_key_name)", $client_id, $document_id);
logAudit("Document", "Restore", "$document_name unarchived via API ($api_key_name)", $client_id, $document_id);
logAudit("API", "Success", "Unarchived document $document_name via API ($api_key_name)", $client_id);
}
}

View File

@@ -119,7 +119,7 @@ if (!empty($document_id)) {
}
// Logging
logAudit("Document", "Edit", "$name_db via API ($api_key_name), previous version kept", $client_id, $document_version_id);
logAudit("Document", "Edit", "$name_db via API ($api_key_name), previous version kept", $client_id, $document_id);
logAudit("API", "Success", "Edited document $name_db via API ($api_key_name)", $client_id);
} else {

View File

@@ -15,7 +15,7 @@ if (!empty($domain_id)) {
if ($update_sql) {
$update_count = mysqli_affected_rows($mysqli);
logAudit("Domain", "Unarchive", "$domain_name unarchived via API ($api_key_name)", $client_id, $domain_id);
logAudit("Domain", "Restore", "$domain_name unarchived via API ($api_key_name)", $client_id, $domain_id);
}
}
}

View File

@@ -33,7 +33,7 @@ if (!empty($location_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Location", "Unarchive", "$location_name unarchived via API ($api_key_name)", $client_id, $location_id);
logAudit("Location", "Restore", "$location_name unarchived via API ($api_key_name)", $client_id, $location_id);
logAudit("API", "Success", "Unarchived location $location_name via API ($api_key_name)", $client_id);
}
}

View File

@@ -33,7 +33,7 @@ if (!empty($network_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Network", "Unarchive", "$network_name unarchived via API ($api_key_name)", $client_id, $network_id);
logAudit("Network", "Restore", "$network_name unarchived via API ($api_key_name)", $client_id, $network_id);
logAudit("API", "Success", "Unarchived network $network_name via API ($api_key_name)", $client_id);
}
}

View File

@@ -33,7 +33,7 @@ if (!empty($software_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Software", "Unarchive", "$software_name unarchived via API ($api_key_name)", $client_id, $software_id);
logAudit("Software", "Restore", "$software_name unarchived via API ($api_key_name)", $client_id, $software_id);
}
}
}

View File

@@ -102,7 +102,7 @@ if (!empty($ticket_id) && !empty($reply)) {
logTicketHistory($ticket_id, "Resolved via the API ($api_key_name)");
logAudit("Ticket", "Resolved", "Resolved ticket $ticket_prefix$ticket_number via API ($api_key_name)", $client_id, $ticket_id);
logAudit("Ticket", "Resolve", "Resolved ticket $ticket_prefix$ticket_number via API ($api_key_name)", $client_id, $ticket_id);
triggerCustomAction('ticket_resolve', $ticket_id);
}

View File

@@ -38,7 +38,7 @@ if (!empty($ticket_id)) {
// Logging
logTicketHistory($ticket_id, "Closed via the API ($api_key_name)");
logAudit("Ticket", "Closed", "$ticket_prefix$ticket_number ticket via API ($api_key_name)", $client_id, $ticket_id);
logAudit("Ticket", "Close", "$ticket_prefix$ticket_number ticket via API ($api_key_name)", $client_id, $ticket_id);
logAudit("API", "Success", "Closed ticket $ticket_prefix$ticket_number via API ($api_key_name)", $client_id);
}

View File

@@ -44,7 +44,7 @@ if (!empty($ticket_row)) {
// Logging
logTicketHistory($ticket_id, "Resolved via the API ($api_key_name)");
logAudit("Ticket", "Resolved", "$ticket_prefix$ticket_number ticket via API ($api_key_name)", $client_id, $ticket_id);
logAudit("Ticket", "Resolve", "$ticket_prefix$ticket_number ticket via API ($api_key_name)", $client_id, $ticket_id);
logAudit("API", "Success", "Resolved ticket $ticket_prefix$ticket_number via API ($api_key_name)", $client_id);
}

View File

@@ -24,7 +24,7 @@ if (!empty($vendor_id)) {
$update_count = mysqli_affected_rows($mysqli);
// Logging
logAudit("Vendor", "Unarchive", "$vendor_name unarchived via API ($api_key_name)", $client_id, $vendor_id);
logAudit("Vendor", "Restore", "$vendor_name unarchived via API ($api_key_name)", $client_id, $vendor_id);
}
}
}