Files
itflow/agent/post/asset.php
johnnyq 1a613eab7b Files and documents overhaul: rebuilt files list with folder tree (counts, open/close remembered, phone collapse), current folder path and folder menu, All/Documents/Uploads tabs with counts, colour-coded type tiles, shared and portal pills, updated time and author, linked record counts, permission-gated row menus, search across every folder from the top level showing where each result lives, grid view with real previews (image thumbnails, PDF first page, document and text excerpts) and an arrow-key previewer with a Details button, drag and drop files onto the list to upload into the folder on show, bulk move/archive/restore/delete for files and documents together; document page rebuilt like the asset and contact pages with header actions (Edit, Share, PDF, Print, Rename, Move, Link, portal visibility, Archive, Delete), Linked card, folder and portal card and a History card where versions can be viewed, restored (current content kept as a version) or deleted, revision table moved to print only; new file quick look with preview, folder, uploader, share status and links; document quick look and version viewer redone; one link modal for every relation (files, documents, assets, contacts, licenses, vendors) with type tabs and multi-select, offering only the client's own unarchived, not yet linked records, old link modals now open it; upload modal with drop box, file list and size checks; new and edit document share one form with folder and client portal switch; template, rename, move, bulk move, visibility and folder add/rename/delete modals modernized with folder tree pickers; asset and contact pages show the same file and document tiles and open the file quick look; fixes: folder, contact and asset ownership checked on upload, new document, template, move and bulk move, links limited to records of the same client, linking an existing link no longer errors, deleting a folder now moves its files, documents and subfolders up instead of orphaning them, file delete confirmation no longer builds its name into inline JS, permission checks added to the upload, new document, folder, visibility and link modals, upload modal script error that skipped the size check, skipped uploads now reported, mime type read from the uploaded file, per-row link modals that broke grid view, search with quotes double escaped, document search text stored without tags and with words spaced, bulk messages with empty counts, visibility wording, file rename icon, PDF export redirecting after output and needing write access, file and document deletes now remove their links and skip missing files on disk, duplicate asset to file link handler removed; developer: new functions/links.php (relation registry, linkAdd, linkRemove, linkRemoveAll, linkedRecords, linkCandidates, linkGroupsHtml), post/link.php with link_items and unlink_item plus the legacy link and unlink names, functions/files.php gains fileTypeInfo, fileTypeTile, documentTile, folderTree, folderPath, folderSubtree, folderOptionsHtml, folderOwnedId, delete helpers, documentContentRaw and documentHtmlPurify, new agent/js/files.js, modals/link/link.php, modals/file/file.php, modals/folder/folder_delete.php and modals/document/document_form.php, removed unused document_bulk_move.php, document_add_file_relation.php and js/file_delete_modal.js
2026-10-14 20:35:41 -04:00

2035 lines
74 KiB
PHP

<?php
/*
* ITFlow - GET/POST request handler for client assets
*/
defined('FROM_POST_HANDLER') || die("Direct file access is not allowed");
if (isset($_POST['add_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
require_once 'asset_model.php';
$client_id = intval($_POST['client_id']);
enforceClientAccess();
// The picks have to be this client's own
$location = assetClientOwnedId('location', $location, $client_id);
$contact = assetClientOwnedId('contact', $contact, $client_id);
$vendor = assetClientOwnedId('vendor', $vendor, $client_id);
$network = assetClientOwnedId('network', $network, $client_id);
// Only the two credential fields this handler writes - name/description/uri here
// belong to the asset, not the credential, and have their own column widths.
// Checked before the asset is created, so an overlong credential can't leave a
// half-built asset behind. Form maxlength doesn't reach a hand-rolled POST.
if ($credential_field_too_long = checkCredentialLengths([
'username' => $_POST['username'] ?? null,
'password' => $_POST['password'] ?? null,
])) {
flashAlert("Credential <strong>$credential_field_too_long</strong> is too long to store", 'error');
redirect();
exit;
}
$alert_extended = "";
mysqli_query($mysqli,"INSERT INTO assets SET asset_name = '$name', asset_description = '$description', asset_type = '$type', asset_make = '$make', asset_model = '$model', asset_serial = '$serial', asset_os = '$os', asset_uri = '$uri', asset_uri_2 = '$uri_2', asset_uri_client = '$uri_client', asset_location_id = $location, asset_vendor_id = $vendor, asset_contact_id = $contact, asset_status = '$status', asset_purchase_reference = '$purchase_reference', asset_purchase_date = $purchase_date, asset_warranty_expire = $warranty_expire, asset_install_date = $install_date, asset_physical_location = '$physical_location', asset_notes = '$notes', asset_favorite = $favorite, asset_client_id = $client_id");
$asset_id = mysqli_insert_id($mysqli);
// Add Tags
if (isset($_POST['tags'])) {
foreach($_POST['tags'] as $tag) {
$tag = intval($tag);
mysqli_query($mysqli, "INSERT INTO asset_tags SET asset_tag_asset_id = $asset_id, asset_tag_tag_id = $tag");
}
}
// Add Photo
if (isset($_FILES['file']['tmp_name'])) {
if ($new_file_name = checkFileUpload($_FILES['file'], array('jpg', 'jpeg', 'gif', 'png', 'webp'))) {
$file_tmp_path = $_FILES['file']['tmp_name'];
// directory in which the uploaded file will be moved
if (!file_exists("../uploads/clients/$client_id")) {
mkdir("../uploads/clients/$client_id");
}
$upload_file_dir = "../uploads/clients/$client_id/";
$dest_path = $upload_file_dir . $new_file_name;
move_uploaded_file($file_tmp_path, $dest_path);
mysqli_query($mysqli,"UPDATE assets SET asset_photo = '$new_file_name' WHERE asset_id = $asset_id");
}
}
// Add Primary Interface
mysqli_query($mysqli,"INSERT INTO asset_interfaces SET interface_name = '01', interface_mac = '$mac', interface_ip = '$ip', interface_nat_ip = '$nat_ip', interface_ipv6 = '$ipv6', interface_primary = 1, interface_network_id = $network, interface_asset_id = $asset_id");
if (!empty($_POST['password'])) {
$username = trim(mysqli_real_escape_string($mysqli, encryptCredentialEntry($_POST['username'])));
$password = trim(mysqli_real_escape_string($mysqli, encryptCredentialEntry($_POST['password'])));
mysqli_query($mysqli,"INSERT INTO credentials SET credential_name = '$name', credential_username = '$username', credential_password = '$password', credential_asset_id = $asset_id, credential_client_id = $client_id");
$credential_id = mysqli_insert_id($mysqli);
logAudit("Credential", "Create", "$session_name created login credential for asset $name", $client_id, $credential_id);
$alert_extended = " along with login credentials";
}
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = '$status', asset_history_description = '$session_name created $name', asset_history_asset_id = $asset_id");
logAudit("Asset", "Create", "$session_name created asset $name", $client_id, $asset_id);
flashAlert("Asset <strong>$name</strong> created $alert_extended");
redirect();
}
if (isset($_POST['edit_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
require_once 'asset_model.php';
$asset_id = intval($_POST['asset_id']);
// Get Existing Photo and assigned client_id
$sql = mysqli_query($mysqli,"SELECT asset_photo, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$existing_file_name = $row['asset_photo'] ?? '';
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// The picks have to be this client's own
$location = assetClientOwnedId('location', $location, $client_id);
$contact = assetClientOwnedId('contact', $contact, $client_id);
$vendor = assetClientOwnedId('vendor', $vendor, $client_id);
$network = assetClientOwnedId('network', $network, $client_id);
mysqli_query($mysqli,"UPDATE assets SET asset_name = '$name', asset_description = '$description', asset_type = '$type', asset_make = '$make', asset_model = '$model', asset_serial = '$serial', asset_os = '$os', asset_uri = '$uri', asset_uri_2 = '$uri_2', asset_uri_client = '$uri_client', asset_location_id = $location, asset_vendor_id = $vendor, asset_contact_id = $contact, asset_status = '$status', asset_purchase_reference = '$purchase_reference', asset_purchase_date = $purchase_date, asset_warranty_expire = $warranty_expire, asset_install_date = $install_date, asset_physical_location = '$physical_location', asset_notes = '$notes', asset_favorite = $favorite WHERE asset_id = $asset_id");
$sql_interfaces = mysqli_query($mysqli, "SELECT 1 FROM asset_interfaces WHERE interface_asset_id = $asset_id AND interface_primary = 1");
if(mysqli_num_rows($sql_interfaces) == 0 ) {
// Add Primary Interface
mysqli_query($mysqli,"INSERT INTO asset_interfaces SET interface_name = '01', interface_mac = '$mac', interface_ip = '$ip', interface_nat_ip = '$nat_ip', interface_ipv6 = '$ipv6', interface_primary = 1, interface_network_id = $network, interface_asset_id = $asset_id");
} else {
// Update Primary Interface
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_mac = '$mac', interface_ip = '$ip', interface_nat_ip = '$nat_ip', interface_ipv6 = '$ipv6', interface_network_id = $network WHERE interface_asset_id = $asset_id AND interface_primary = 1");
}
// Photo - a new upload replaces the old file; Remove only counts when nothing new came in
$existing_photo_path = $existing_file_name !== '' ? "../uploads/clients/$client_id/" . basename($existing_file_name) : '';
if (isset($_FILES['file']) && $new_file_name = checkFileUpload($_FILES['file'], array('jpg', 'jpeg', 'gif', 'png', 'webp'))) {
if (!is_dir("../uploads/clients/$client_id")) {
mkdir("../uploads/clients/$client_id", 0755, true);
}
move_uploaded_file($_FILES['file']['tmp_name'], "../uploads/clients/$client_id/$new_file_name");
if ($existing_photo_path && is_file($existing_photo_path)) {
unlink($existing_photo_path);
}
mysqli_query($mysqli,"UPDATE assets SET asset_photo = '$new_file_name' WHERE asset_id = $asset_id");
} elseif (!empty($_POST['remove_photo']) && $existing_photo_path) {
if (is_file($existing_photo_path)) {
unlink($existing_photo_path);
}
mysqli_query($mysqli,"UPDATE assets SET asset_photo = NULL WHERE asset_id = $asset_id");
}
// Tags
// Delete existing tags
mysqli_query($mysqli, "DELETE FROM asset_tags WHERE asset_tag_asset_id = $asset_id");
// Add new tags
if (isset($_POST['tags'])) {
foreach($_POST['tags'] as $tag) {
$tag = intval($tag);
mysqli_query($mysqli, "INSERT INTO asset_tags SET asset_tag_asset_id = $asset_id, asset_tag_tag_id = $tag");
}
}
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = '$status', asset_history_description = '$session_name updated $name', asset_history_asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name edited asset $name", $client_id, $asset_id);
flashAlert("Asset <strong>$name</strong> edited");
redirect();
}
if (isset($_GET['archive_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_GET['archive_asset']);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_archived_at = NOW() WHERE asset_id = $asset_id");
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = 'Archived', asset_history_description = '$session_name archived $asset_name', asset_history_asset_id = $asset_id");
logAudit("Asset", "Archive", "$session_name archived asset $asset_name", $client_id, $asset_id);
flashAlert("Asset <strong>$asset_name</strong> archived", 'error');
redirect();
}
if (isset($_GET['restore_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_GET['restore_asset']);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_archived_at = NULL WHERE asset_id = $asset_id");
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = 'Restored', asset_history_description = '$session_name restored $asset_name', asset_history_asset_id = $asset_id");
logAudit("Asset", "Restore", "$session_name restored asset $asset_name", $client_id, $asset_id);
flashAlert("Asset <strong>$asset_name</strong> Restored");
redirect();
}
if (isset($_GET['delete_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 3);
$asset_id = intval($_GET['delete_asset']);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"DELETE FROM assets WHERE asset_id = $asset_id");
// Out of whatever rack it was in - an item pointing at a deleted asset draws as nothing
mysqli_query($mysqli,"DELETE FROM rack_units WHERE unit_asset_id = $asset_id");
logAudit("Asset", "Delete", "$session_name deleted asset $asset_name", $client_id);
flashAlert("Asset <strong>$asset_name</strong> deleted");
redirect();
}
if (isset($_POST['add_asset_note'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_POST['asset_id']);
$type = escapeSql($_POST['type']);
$note = escapeSql($_POST['note']);
// Get Asset details for logging and alerting
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli, "INSERT INTO asset_notes SET asset_note_type = '$type', asset_note = '$note', asset_note_created_by = $session_user_id, asset_note_asset_id = $asset_id");
$asset_note_id = mysqli_insert_id($mysqli);
//Logging
logAudit("Asset", "Edit", "$session_name created a $type note for asset $asset_name", $client_id, $asset_id);
$_SESSION['alert_message'] = "Note <strong>$type</strong> created for <strong>$asset_name</strong>";
redirect();
}
if (isset($_GET['archive_asset_note'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_note_id = intval($_GET['archive_asset_note']);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_note_type, asset_id, asset_name, asset_client_id FROM asset_notes LEFT JOIN assets ON asset_id = asset_note_asset_id WHERE asset_note_id = $asset_note_id");
$row = mysqli_fetch_assoc($sql);
$asset_note_type = escapeSql($row['asset_note_type']);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
$asset_id = intval($row['asset_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE asset_notes SET asset_note_archived_at = NOW() WHERE asset_note_id = $asset_note_id");
logAudit("Asset", "Edit", "$session_name archived note $asset_note_type for $asset_name", $client_id, $asset_id);
flashAlert("Note <strong>$asset_note_type</strong> archived", 'error');
redirect();
}
if (isset($_GET['restore_asset_note'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_note_id = intval($_GET['restore_asset_note']);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_note_type, asset_id, asset_name, asset_client_id FROM asset_notes LEFT JOIN assets ON asset_id = asset_note_asset_id WHERE asset_note_id = $asset_note_id");
$row = mysqli_fetch_assoc($sql);
$asset_note_type = escapeSql($row['asset_note_type']);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
$asset_id = intval($row['asset_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE asset_notes SET asset_note_archived_at = NULL WHERE asset_note_id = $asset_note_id");
logAudit("Asset", "Edit", "$session_name restored note $asset_note_type for $asset_name", $client_id, $asset_id);
flashAlert("Note <strong>$asset_note_type</strong> restored");
redirect();
}
if (isset($_GET['delete_asset_note'])) {
validateCSRFToken();
enforceUserPermission('module_support', 3);
$asset_note_id = intval($_GET['delete_asset_note']);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_note_type, asset_id, asset_name, asset_client_id FROM asset_notes LEFT JOIN assets ON asset_id = asset_note_asset_id WHERE asset_note_id = $asset_note_id");
$row = mysqli_fetch_assoc($sql);
$asset_note_type = escapeSql($row['asset_note_type']);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
$asset_id = intval($row['asset_id']);
enforceClientAccess();
mysqli_query($mysqli,"DELETE FROM asset_notes WHERE asset_note_id = $asset_note_id");
logAudit("Asset", "Edit", "$session_name deleted $asset_note_type note for $asset_name", $client_id, $asset_id);
flashAlert("Note <strong>$asset_note_type</strong> deleted.", 'error');
redirect();
}
if (isset($_POST['bulk_assign_asset_location'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$location_id = intval($_POST['bulk_location_id']);
// Get Location name and client id for logging and alert
$sql = mysqli_query($mysqli,"SELECT location_name, location_client_id FROM locations WHERE location_id = $location_id");
$row = mysqli_fetch_assoc($sql);
$location_name = escapeSql($row['location_name']);
$client_id = intval($row['location_client_id']);
$location_client_id = $client_id;
enforceClientAccess();
// Assign Location to Selected Assets
if (isset($_POST['asset_ids'])) {
// Only the assets of the location's client are moved
$asset_count = 0;
foreach($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Details for Logging
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name'] ?? '');
$client_id = intval($row['asset_client_id'] ?? 0);
if (!$row || $client_id !== $location_client_id) {
continue;
}
enforceClientAccess();
$asset_count++;
mysqli_query($mysqli,"UPDATE assets SET asset_location_id = $location_id WHERE asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name assigned asset $asset_name to location $location_name", $client_id, $asset_id);
} // End Assign Location Loop
logAudit("Asset", "Bulk Edit", "$session_name assigned $asset_count assets to location $location_name", $location_client_id);
flashAlert("You assigned <strong>$asset_count</strong> assets to location <strong>$location_name</strong>");
}
redirect();
}
if (isset($_POST['bulk_assign_asset_physical_location'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$physical_location = escapeSql($_POST['physical_location']);
// Assign Physical Location to Selected Assets
if (isset($_POST['asset_ids'])) {
// Get Selected Assets Count
$asset_count = count($_POST['asset_ids']);
foreach($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Details for Logging
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_physical_location = '$physical_location' WHERE asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name set asset $asset_name to physical location $physical_location", $client_id, $asset_id);
} // End Assign Location Loop
logAudit("Asset", "Bulk Edit", "$session_name set $asset_count assets to physical location $physical_location", $client_id);
flashAlert("You moved <strong>$asset_count</strong> assets to location <strong>$physical_location</strong>");
}
redirect();
}
if (isset($_POST['bulk_transfer_client_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$new_client_id = intval($_POST['bulk_client_id']);
enforceClientAccess($new_client_id);
// Transfer selected asset to new client
if (isset($_POST['asset_ids'])) {
// Get Count
$asset_count = count($_POST['asset_ids']);
foreach($_POST['asset_ids'] as $current_asset_id) {
$current_asset_id = intval($current_asset_id);
// Get Asset details and current client ID/Name for logging
$row = mysqli_fetch_assoc(mysqli_query($mysqli,"SELECT asset_name, asset_notes, asset_client_id, client_name
FROM assets
LEFT JOIN clients ON client_id = asset_client_id
WHERE asset_id = $current_asset_id")
);
$asset_name = escapeSql($row['asset_name']);
$asset_notes = escapeSql($row['asset_notes']);
$current_client_id = intval($row['asset_client_id']);
$current_client_name = escapeSql($row['client_name']);
enforceClientAccess($current_client_id);
// Get new client name for logging
$new_client_name = escapeSql(getFieldById('clients', $new_client_id, 'client_name'));
// Create new asset
mysqli_query($mysqli, "
INSERT INTO assets (asset_type, asset_name, asset_description, asset_make, asset_model, asset_serial, asset_os, asset_status, asset_purchase_date, asset_warranty_expire, asset_install_date, asset_notes, asset_favorite)
SELECT asset_type, asset_name, asset_description, asset_make, asset_model, asset_serial, asset_os, asset_status, asset_purchase_date, asset_warranty_expire, asset_install_date, asset_notes, asset_favorite
FROM assets
WHERE asset_id = $current_asset_id
");
$new_asset_id = mysqli_insert_id($mysqli);
// Transfer all Interfaces over too
$sql_interfaces = mysqli_query($mysqli, "SELECT interface_mac, interface_name, interface_primary FROM asset_interfaces WHERE interface_asset_id = $current_asset_id");
while ($row = mysqli_fetch_assoc($sql_interfaces)) {
$interface_name = escapeSql($row['interface_name']);
$interface_mac = escapeSql($row['interface_mac']);
$interface_primary = intval($row['interface_primary']);
mysqli_query($mysqli,"INSERT INTO asset_interfaces SET interface_name = '$interface_name', interface_mac = '$interface_mac', interface_primary = $interface_primary, interface_asset_id = $new_asset_id");
}
mysqli_query($mysqli, "UPDATE assets SET asset_client_id = $new_client_id WHERE asset_id = $new_asset_id");
// Archive/log the current asset
$notes = $asset_notes . "\r\n\r\n---\r\n* " . date('Y-m-d H:i:s') . ": Transferred asset $asset_name (old asset ID: $current_asset_id) from $current_client_name to $new_client_name (new asset ID: $new_asset_id)";
mysqli_query($mysqli,"UPDATE assets SET asset_archived_at = NOW() WHERE asset_id = $current_asset_id");
// It belongs to another client now, so it is no longer in this client's rack
mysqli_query($mysqli,"DELETE FROM rack_units WHERE unit_asset_id = $current_asset_id");
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = 'Transferred', asset_history_description = '$session_name transferred $asset_name to $new_client_name', asset_history_asset_id = $current_asset_id");
// Log Archive
logAudit("Asset", "Archive", "$session_name archived asset $asset_name (via transfer)", $current_client_id, $current_asset_id);
// Log Transfer
logAudit("Asset", "Transfer", "$session_name Transferred asset $asset_name (old asset ID: $current_asset_id) from $current_client_name to $new_client_name (new asset ID: $new_asset_id)", $current_client_id, $current_asset_id);
mysqli_query($mysqli, "UPDATE assets SET asset_notes = '$notes' WHERE asset_id = $current_asset_id");
// Log the new asset
$notes = $asset_notes . "\r\n\r\n---\r\n* " . date('Y-m-d H:i:s') . ": Transferred asset $asset_name (old asset ID: $current_asset_id) from $current_client_name to $new_client_name (new asset ID: $new_asset_id)";
logAudit("Asset", "Create", "$session_name created asset $name (via transfer)", $new_client_id, $new_asset_id);
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = 'Transferred', asset_history_description = '$session_name created asset via transfer from $current_client_name', asset_history_asset_id = $new_asset_id");
logAudit("Asset", "Transfer", "$session_name Transferred asset $asset_name (old asset ID: $current_asset_id) from $current_client_name to $new_client_name (new asset ID: $new_asset_id)", $new_client_id, $new_asset_id);
mysqli_query($mysqli, "UPDATE assets SET asset_notes = '$notes' WHERE asset_id = $new_asset_id");
} // End Transfer to Client Loop
logAudit("Asset", "Bulk Transfer", "$session_name transferred $asset_count assets to $new_client_name", $new_client_id);
flashAlert("Transferred <strong>$asset_count</strong> assets to <strong>$new_client_name</strong>.");
}
redirect();
}
if (isset($_POST['bulk_assign_asset_contact'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$contact_id = intval($_POST['bulk_contact_id']);
// Get Contact name and client id for logging and Notification
$sql = mysqli_query($mysqli,"SELECT contact_name, contact_client_id FROM contacts WHERE contact_id = $contact_id");
$row = mysqli_fetch_assoc($sql);
$contact_name = escapeSql($row['contact_name']);
$client_id = intval($row['contact_client_id']);
enforceClientAccess();
// Assign Contact to Selected Assets
if (isset($_POST['asset_ids'])) {
// Only the assets of the contact's client are assigned
$asset_count = 0;
foreach($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Details for Logging
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name'] ?? '');
if (!$row || intval($row['asset_client_id']) !== $client_id) {
continue;
}
$asset_count++;
mysqli_query($mysqli,"UPDATE assets SET asset_contact_id = $contact_id WHERE asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name assigned asset $asset_name to contact $contact_name", $client_id, $asset_id);
} // End Assign Contact Loop
logAudit("Asset", "Bulk Edit", "$session_name assigned $asset_count assets to contact $contact_name", $client_id);
flashAlert("You assigned <strong>$asset_count</strong> assets to contact <strong>$contact_name</strong>");
}
redirect();
}
if (isset($_POST['bulk_edit_asset_status'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$status = escapeSql($_POST['bulk_status']);
if (isset($_POST['asset_ids'])) {
$asset_count = count($_POST['asset_ids']);
foreach($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Details for Logging
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_status = '$status' WHERE asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name set status to $status on $asset_name", $client_id, $asset_id);
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = '$status', asset_history_description = '$session_name updated $asset_name', asset_history_asset_id = $asset_id");
}
logAudit("Asset", "Bulk Edit", "$session_name set status to $status on $asset_count assets", $client_id);
flashAlert("You set the status <strong>$status</strong> on <strong>$asset_count</strong> assets.");
}
redirect();
}
if (isset($_POST['bulk_favorite_assets'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
if (isset($_POST['asset_ids'])) {
$count = count($_POST['asset_ids']);
foreach ($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_favorite = 1 WHERE asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name marked asset $asset_name a favorite", $client_id, $asset_id);
}
logAudit("Asset", "Bulk Edit", "$session_name favorited $count assets", $client_id);
flashAlert("Favorited <strong>$count</strong> asset(s)");
}
redirect();
}
if (isset($_POST['bulk_unfavorite_assets'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
if (isset($_POST['asset_ids'])) {
$count = count($_POST['asset_ids']);
foreach ($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_favorite = 0 WHERE asset_id = $asset_id");
logAudit("Asset", "Edit", "$session_name unfavorited asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset", "Bulk Edit", "$session_name unfavorited $count assets", $client_id);
flashAlert("Unfavorited <strong>$count</strong> asset(s)");
}
redirect();
}
if (isset($_POST['bulk_archive_assets'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
if (isset($_POST['asset_ids'])) {
$count = count($_POST['asset_ids']);
foreach ($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_archived_at = NOW() WHERE asset_id = $asset_id");
logAudit("Asset", "Archive", "$session_name archived asset $asset_name", $client_id, $asset_id);
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = 'Archived', asset_history_description = '$session_name archived $asset_name', asset_history_asset_id = $asset_id");
}
logAudit("Asset", "Bulk Archive", "$session_name archived $count assets", $client_id);
flashAlert("Archived <strong>$count</strong> asset(s)", 'error');
}
redirect();
}
if (isset($_POST['bulk_restore_assets'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
if (isset($_POST['asset_ids'])) {
$count = count($_POST['asset_ids']);
foreach ($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"UPDATE assets SET asset_archived_at = NULL WHERE asset_id = $asset_id");
// Individual Asset logging
logAudit("Asset", "Restore", "$session_name restored asset $asset_name", $client_id, $asset_id);
// Add to History
mysqli_query($mysqli,"INSERT INTO asset_history SET asset_history_status = 'Restored', asset_history_description = '$session_name restored $asset_name', asset_history_asset_id = $asset_id");
}
logAudit("Asset", "Bulk Restore", "$session_name restored $count assets");
flashAlert("Restored $count asset(s)");
}
redirect();
}
if (isset($_POST['bulk_delete_assets'])) {
validateCSRFToken();
enforceUserPermission('module_support', 3);
if (isset($_POST['asset_ids'])) {
$count = count($_POST['asset_ids']);
foreach ($_POST['asset_ids'] as $asset_id) {
$asset_id = intval($asset_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli,"DELETE FROM assets WHERE asset_id = $asset_id");
mysqli_query($mysqli,"DELETE FROM rack_units WHERE unit_asset_id = $asset_id");
logAudit("Asset", "Delete", "$session_name deleted asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset", "Bulk Delete", "$session_name deleted $count assets");
flashAlert("Deleted <strong>$count</strong> asset(s)", 'error');
}
redirect();
}
// BEGIN LINKING
if (isset($_POST['link_software_to_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$software_id = intval($_POST['software_id']);
$asset_id = intval($_POST['asset_id']);
// Get software Name and Client ID for logging
$sql_software = mysqli_query($mysqli,"SELECT software_name, software_client_id FROM software WHERE software_id = $software_id");
$row = mysqli_fetch_assoc($sql_software);
$software_name = escapeSql($row['software_name']);
$client_id = intval($row['software_client_id']);
enforceClientAccess();
// Get Asset Name for logging
$asset_name = escapeSql(getFieldById('assets', $asset_id, 'asset_name'));
mysqli_query($mysqli,"INSERT INTO software_assets SET asset_id = $asset_id, software_id = $software_id");
logAudit("Software", "Link", "$session_name added software license $software_name to asset $asset_name", $client_id, $software_id);
flashAlert("Software <strong>$software_name</strong> licensed for asset <strong>$asset_name</strong>");
redirect();
}
if (isset($_GET['unlink_software_from_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_GET['asset_id']);
$software_id = intval($_GET['software_id']);
// Get software Name and Client ID for logging
$sql_software = mysqli_query($mysqli,"SELECT software_name, software_client_id FROM software WHERE software_id = $software_id");
$row = mysqli_fetch_assoc($sql_software);
$software_name = escapeSql($row['software_name']);
$client_id = intval($row['software_client_id']);
enforceClientAccess();
// Get Asset Name for logging
$asset_name = escapeSql(getFieldById('assets', $asset_id, 'asset_name'));
mysqli_query($mysqli,"DELETE FROM software_assets WHERE asset_id = $asset_id AND software_id = $software_id");
logAudit("software", "Unlink", "$session_name removed software license $software_name from asset $asset_name", $client_id, $software_id);
flashAlert("Removed Software License <strong>$software_name</strong> for Asset <strong>$asset_name</strong>", 'error');
redirect();
}
// Right now 1 login and have many assets but not many to many
if (isset($_POST['link_asset_to_credential'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$credential_id = intval($_POST['credential_id']);
$asset_id = intval($_POST['asset_id']);
// Get credential Name and Client ID for logging
$sql_credential = mysqli_query($mysqli,"SELECT credential_name, credential_client_id FROM credentials WHERE credential_id = $credential_id");
$row = mysqli_fetch_assoc($sql_credential);
$credential_name = escapeSql($row['credential_name']);
$client_id = intval($row['credential_client_id']);
enforceClientAccess();
// Get Asset Name for logging
$asset_name = escapeSql(getFieldById('assets', $asset_id, 'asset_name'));
mysqli_query($mysqli,"UPDATE credentials SET credential_asset_id = $asset_id WHERE credential_id = $credential_id");
logAudit("Credential", "Link", "$session_name linked credential $credential_name to asset $asset_name", $client_id, $credential_id);
flashAlert("Asset <strong>$asset_name</strong> linked with credential <strong>$credential_name</strong>");
redirect();
}
if (isset($_GET['unlink_credential_from_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_GET['asset_id']);
$credential_id = intval($_GET['credential_id']);
// Get credential Name and Client ID for logging
$sql_credential = mysqli_query($mysqli,"SELECT credential_name, credential_client_id FROM credentials WHERE credential_id = $credential_id");
$row = mysqli_fetch_assoc($sql_credential);
$credential_name = escapeSql($row['credential_name']);
$client_id = intval($row['credential_client_id']);
enforceClientAccess();
// Get Asset Name for logging
$asset_name = escapeSql(getFieldById('assets', $asset_id, 'asset_name'));
mysqli_query($mysqli,"UPDATE credentials SET credential_asset_id = 0 WHERE credential_id = $credential_id");
logAudit("Credential", "Unlink", "$session_name unlinked asset $asset_name from credential $credential_name", $client_id, $credential_id);
flashAlert("Credential <strong>$credential_name</strong> unlinked from Asset <strong>$asset_name</strong>", 'errpr');
redirect();
}
if (isset($_POST['link_service_to_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$service_id = intval($_POST['service_id']);
$asset_id = intval($_POST['asset_id']);
// Get service Name and Client ID for logging
$sql_service = mysqli_query($mysqli,"SELECT service_name, service_client_id FROM services WHERE service_id = $service_id");
$row = mysqli_fetch_assoc($sql_service);
$service_name = escapeSql($row['service_name']);
$client_id = intval($row['service_client_id']);
enforceClientAccess();
// Get Asset Name for logging
$asset_name = escapeSql(getFieldById('assets', $asset_id, 'asset_name'));
mysqli_query($mysqli,"INSERT INTO service_assets SET asset_id = $asset_id, service_id = $service_id");
logAudit("Service", "Link", "$session_name linked asset $asset_name to service $service_name", $client_id, $service_id);
flashAlert("Service <strong>$service_name</strong> linked with asset <strong>$asset_name</strong>");
redirect();
}
if (isset($_GET['unlink_service_from_asset'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_GET['asset_id']);
$service_id = intval($_GET['service_id']);
// Get service Name and Client ID for logging
$sql_service = mysqli_query($mysqli,"SELECT service_name, service_client_id FROM services WHERE service_id = $service_id");
$row = mysqli_fetch_assoc($sql_service);
$service_name = escapeSql($row['service_name']);
$client_id = intval($row['service_client_id']);
enforceClientAccess();
// Get Asset Name for logging
$asset_name = escapeSql(getFieldById('assets', $asset_id, 'asset_name'));
mysqli_query($mysqli,"DELETE FROM service_assets WHERE asset_id = $asset_id AND service_id = $service_id");
logAudit("Service", "Unlink", "$session_name unlinked asset $asset_name from service $service_name", $client_id, $service_id);
flashAlert("Asset <strong>$asset_name</strong> unlinked from service <strong>$service_name</strong>", 'error');
redirect();
}
// END LINKING
if (isset($_POST["import_assets_csv"])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$client_id = intval($_POST['client_id']);
enforceClientAccess();
$file_name = $_FILES["file"]["tmp_name"];
$error = false;
if (!empty($_FILES["file"]["tmp_name"])) {
$file_name = $_FILES["file"]["tmp_name"];
} else {
flashAlert("Please select a file to upload.", 'error');
redirect();
}
//Check file is CSV
$file_extension = strtolower(end(explode('.',$_FILES['file']['name'])));
$allowed_file_extensions = array('csv');
if (in_array($file_extension,$allowed_file_extensions) === false) {
$error = true;
flashAlert("Bad file extension", 'error');
}
//Check file isn't empty
elseif ($_FILES["file"]["size"] < 1) {
$error = true;
flashAlert("Bad file size (empty?)", 'error');
}
//(Else)Check column count (name, desc, type, make, model, serial, os, purchase date, assigned to, location, notes)
$f = fopen($file_name, "r");
$f_columns = fgetcsv($f, 1000, ",");
if (!$error & count($f_columns) != 12) {
$error = true;
flashAlert("Invalid column count.", 'error');
}
//Else, parse the file
if (!$error) {
$file = fopen($file_name, "r");
fgetcsv($file, 1000, ","); // Skip first line
$row_count = 0;
$duplicate_count = 0;
while(($column = fgetcsv($file, 1000, ",")) !== false) {
// Default variables (if undefined)
$description = $type = $make = $model = $serial = $os = '';
$contact_id = $location_id = 0;
$purchase_date = '0000-00-00';
$duplicate_detect = 0;
// Name
if (isset($column[0])) {
$name = escapeSql($column[0]);
if (mysqli_num_rows(mysqli_query($mysqli,"SELECT 1 FROM assets WHERE asset_name = '$name' AND asset_client_id = $client_id")) > 0) {
$duplicate_detect = 1;
}
}
// Desc
if (!empty($column[1])) {
$description = escapeSql($column[1]);
}
// Type
if (!empty($column[2])) {
$type = escapeSql($column[2]);
}
// Make
if (!empty($column[3])) {
$make = escapeSql($column[3]);
}
// Model
if (!empty($column[4])) {
$model = escapeSql($column[4]);
}
// Serial
if (!empty($column[5])) {
$serial = escapeSql($column[5]);
}
// OS
if (!empty($column[6])) {
$os = escapeSql($column[6]);
}
// Purchase date
if (!empty($column[7])) {
$purchase_date = escapeSql($column[7]);
if (!preg_match('/^\d{4}-\d{2}-\d{2}$/', $purchase_date) || empty($purchase_date)) {
$purchase_date = "NULL";
} else {
$purchase_date = "'" . $purchase_date . "'";
}
}
// Assigned to (contact)
if (!empty($column[8])) {
$contact = escapeSql($column[8]);
if ($contact) {
$sql_contact = mysqli_query($mysqli,"SELECT contact_id FROM contacts WHERE contact_name = '$contact' AND contact_client_id = $client_id");
$row = mysqli_fetch_assoc($sql_contact);
$contact_id = intval($row['contact_id']);
}
}
// Location (lookup)
if (!empty($column[9])) {
$location = escapeSql($column[9]);
if ($location) {
$sql_location = mysqli_query($mysqli,"SELECT location_id FROM locations WHERE location_name = '$location' AND location_client_id = $client_id");
$row = mysqli_fetch_assoc($sql_location);
$location_id = intval($row['location_id']);
}
}
// Physical location (varchar)
if (!empty($column[10])) {
$physical_location = escapeSql($column[10]);
}
// Notes (varchar)
if (!empty($column[11])) {
$notes = escapeSql($column[11]);
}
// Check if duplicate was detected
if ($duplicate_detect == 0) {
//Add
mysqli_query($mysqli,"INSERT INTO assets SET asset_name = '$name', asset_description = '$description', asset_type = '$type', asset_make = '$make', asset_model = '$model', asset_serial = '$serial', asset_os = '$os', asset_purchase_date = $purchase_date, asset_physical_location = '$physical_location', asset_notes = '$notes', asset_contact_id = $contact_id, asset_location_id = $location_id, asset_client_id = $client_id");
$asset_id = mysqli_insert_id($mysqli);
// Add Primary Interface
mysqli_query($mysqli,"INSERT INTO asset_interfaces SET interface_name = '1', interface_primary = 1, interface_asset_id = $asset_id");
$row_count = $row_count + 1;
} else {
$duplicate_count = $duplicate_count + 1;
}
}
fclose($file);
logAudit("Asset", "Import", "$session_name imported $row_count asset(s) via CSV file", $client_id);
flashAlert("$row_count Asset(s) added, $duplicate_count duplicate(s) detected");
redirect();
}
//Check for any errors, if there are notify user and redirect
if ($error) {
redirect();
}
}
if (isset($_GET['download_assets_csv_template'])) {
$client_id = intval($_GET['download_assets_csv_template']);
//get records from database
$sql = mysqli_query($mysqli,"SELECT client_name FROM clients WHERE client_id = $client_id");
$row = mysqli_fetch_assoc($sql);
$client_name = $row['client_name'];
$delimiter = ",";
$enclosure = '"';
$escape = '\\';
$filename = toAlphanumeric($client_name) . "-Assets-Template.csv";
//create a file pointer
$f = fopen('php://memory', 'w');
//set column headers
$fields = array('Name', 'Description', 'Type', 'Make', 'Model', 'Serial', 'OS', 'Purchase Date', 'Assigned To', 'Location', 'Physical Location', 'Notes');
fputcsv($f, $fields, $delimiter, $enclosure, $escape);
//move back to beginning of file
fseek($f, 0);
//set headers to download file rather than displayed
header('Content-Type: text/csv');
header('Content-Disposition: attachment; filename="' . $filename . '";');
//output all remaining data on a file pointer
fpassthru($f);
exit;
}
if (isExportRequest('export_assets')) {
validateCSRFToken();
enforceUserPermission('module_support');
$format = resolveExportFormat($_POST['export_assets']);
// Filters inherited from the assets page - mirrors agent/assets.php
$filter_summary = [];
if (!empty($_POST['client_id'])) {
$client_id = intval($_POST['client_id']);
$client_query = "AND asset_client_id = $client_id";
$client_row = mysqli_fetch_assoc(mysqli_query($mysqli, "SELECT client_name FROM clients WHERE client_id = $client_id"));
$client_name = $client_row['client_name'];
$file_name_prepend = "$client_name-";
$filter_summary['Client'] = $client_name;
enforceClientAccess();
} else {
$client_query = '';
$client_id = 0; // for Logging
$file_name_prepend = "$session_company_name-";
// Client Filter
if (!empty($_POST['client'])) {
$filter_client_id = intval($_POST['client']);
$client_query = "AND (asset_client_id = $filter_client_id)";
$client_row = mysqli_fetch_assoc(mysqli_query($mysqli, "SELECT client_name FROM clients WHERE client_id = $filter_client_id"));
$filter_summary['Client'] = $client_row['client_name'] ?? '';
}
}
// Archived Filter
if (isset($_POST['archived']) && $_POST['archived'] == 1) {
$archive_query = $client_id ? "asset_archived_at IS NOT NULL" : "(client_archived_at IS NOT NULL OR asset_archived_at IS NOT NULL)";
$filter_summary['Archived'] = 'Archived only';
} else {
$archive_query = $client_id ? "asset_archived_at IS NULL" : "(client_archived_at IS NULL AND asset_archived_at IS NULL)";
}
// Type Filter
$type = $_POST['type'] ?? '';
if ($type == 'workstation') {
$type_query = "asset_type = 'desktop' OR asset_type = 'laptop'";
} elseif ($type == 'server') {
$type_query = "asset_type = 'server'";
} elseif ($type == 'virtual') {
$type_query = "asset_type = 'Virtual Machine'";
} elseif ($type == 'network') {
$type_query = "asset_type = 'Firewall/Router' OR asset_type = 'Switch' OR asset_type = 'Access Point'";
} elseif ($type == 'printer') {
$type_query = "asset_type = 'Printer'";
} elseif ($type == 'other') {
$type_query = "asset_type NOT LIKE 'laptop' AND asset_type NOT LIKE 'desktop' AND asset_type NOT LIKE 'server' AND asset_type NOT LIKE 'virtual machine' AND asset_type NOT LIKE 'firewall/router' AND asset_type NOT LIKE 'switch' AND asset_type NOT LIKE 'access point' AND asset_type NOT LIKE 'printer'";
} else {
// Default - any
$type = '';
$type_query = "asset_type LIKE '%'";
}
if ($type) {
$filter_summary['Type'] = ucwords($type);
}
// Location Filter
if (!empty($_POST['location'])) {
$filter_location_id = intval($_POST['location']);
$location_query = "AND (asset_location_id = $filter_location_id)";
$location_row = mysqli_fetch_assoc(mysqli_query($mysqli, "SELECT location_name FROM locations WHERE location_id = $filter_location_id"));
$filter_summary['Location'] = $location_row['location_name'] ?? '';
} else {
// Default - any
$location_query = '';
}
// Tags Filter
if (isset($_POST['tags']) && is_array($_POST['tags']) && !empty($_POST['tags'])) {
$tag_filter = implode(",", array_map('intval', $_POST['tags']));
$tag_query = "AND tag_id IN ($tag_filter)";
$tag_names = [];
$sql_tags = mysqli_query($mysqli, "SELECT tag_name FROM tags WHERE tag_id IN ($tag_filter) ORDER BY tag_name ASC");
while ($tag_row = mysqli_fetch_assoc($sql_tags)) {
$tag_names[] = $tag_row['tag_name'];
}
$filter_summary['Tags'] = implode(', ', $tag_names);
} else {
// Default - any
$tag_query = '';
}
// Expiring In Filter
if (!empty($_POST['expire_days'])) {
if ($_POST['expire_days'] == "expired") {
$expire_query = "AND (asset_warranty_expire IS NOT NULL AND asset_warranty_expire != '0000-00-00' AND asset_warranty_expire < CURDATE())";
$filter_summary['Warranty'] = 'Expired';
} else {
$expire_days = intval($_POST['expire_days']);
$expire_query = "AND (asset_warranty_expire IS NOT NULL AND asset_warranty_expire != '0000-00-00' AND asset_warranty_expire BETWEEN CURDATE() AND DATE_ADD(CURDATE(), INTERVAL $expire_days DAY))";
$filter_summary['Warranty'] = "Expiring within $expire_days days";
}
} else {
// Default - any
$expire_query = '';
}
// Search Filter
$q = escapeSql($_POST['q'] ?? '');
if (!empty($q)) {
$filter_summary['Search'] = $_POST['q'];
}
// Get records from database - same shape as the assets page list query
$sql = mysqli_query(
$mysqli,
"SELECT * FROM assets
LEFT JOIN clients ON asset_client_id = client_id
LEFT JOIN contacts ON asset_contact_id = contact_id
LEFT JOIN locations ON asset_location_id = location_id
LEFT JOIN asset_interfaces ON interface_asset_id = asset_id AND interface_primary = 1
LEFT JOIN asset_tags ON asset_tag_asset_id = asset_id
LEFT JOIN tags ON tag_id = asset_tag_tag_id
WHERE $archive_query
$tag_query
AND (asset_name LIKE '%$q%' OR asset_description LIKE '%$q%' OR asset_type LIKE '%$q%' OR interface_ip LIKE '%$q%' OR interface_ipv6 LIKE '%$q%' OR interface_mac LIKE '%$q%' OR asset_make LIKE '%$q%' OR asset_model LIKE '%$q%' OR asset_serial LIKE '%$q%' OR asset_os LIKE '%$q%' OR contact_name LIKE '%$q%' OR location_name LIKE '%$q%' OR client_name LIKE '%$q%' OR tag_name LIKE '%$q%')
AND ($type_query)
" . clientScopeSql('asset_client_id') . "
$location_query
$expire_query
$client_query
GROUP BY asset_id
ORDER BY asset_name ASC"
);
$num_rows = mysqli_num_rows($sql);
if ($num_rows > 0) {
guardExportPdfRowCount($format, $num_rows);
$export = beginExport('assets', $format, $file_name_prepend . 'Assets', 'Assets', summarizeExportFilters($filter_summary));
while ($row = mysqli_fetch_assoc($sql)) {
addExportRow($export, $row);
}
finishExport($export);
}
logAudit("Asset", "Export", "$session_name exported $num_rows asset(s) to a " . strtoupper($format) . " file", $client_id);
exit;
}
if (isset($_POST['add_asset_interface'])) {
// 1) Permissions & CSRF
validateCSRFToken();
enforceUserPermission('module_support', 2);
// 2) Gather posted values
$interface_id = intval($_POST['interface_id']);
$asset_id = intval($_POST['asset_id']);
// Defines $name, $mac, $ip, $ipv6, $port, $notes, $network, $connected_to, etc.
require_once 'asset_interface_model.php';
// 3) Fetch asset info for logging and alert
$sql = mysqli_query($mysqli, "
SELECT asset_name, asset_client_id
FROM assets
WHERE asset_id = $asset_id
");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// 4) Insert new interface into asset_interfaces (using SET syntax)
$sql_insert = "
INSERT INTO asset_interfaces SET
interface_name = '$name',
interface_description= '$description',
interface_type = '$type',
interface_mac = '$mac',
interface_ip = '$ip',
interface_nat_ip = '$nat_ip',
interface_ipv6 = '$ipv6',
interface_notes = '$notes',
interface_network_id = $network,
interface_asset_id = $asset_id
";
mysqli_query($mysqli, $sql_insert);
$new_interface_id = mysqli_insert_id($mysqli);
// If Primary Interface Checked set all interfaces primary to 0 then set the new interface as primary with a 1
if ($primary_interface) {
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_primary = 0 WHERE interface_asset_id = $asset_id");
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_primary = 1 WHERE interface_id = $new_interface_id");
}
// 5) If user selected a connected interface, insert row in asset_interface_links
if (!empty($connected_to) && intval($connected_to) > 0) {
$sql_link = "
INSERT INTO asset_interface_links SET
interface_a_id = $new_interface_id,
interface_b_id = $connected_to
";
mysqli_query($mysqli, $sql_link);
}
// 6) Logging
logAudit(
"Asset Interface",
"Create",
"$session_name created interface $name for asset $asset_name",
$client_id,
$asset_id
);
// 7) Alert message + redirect
flashAlert("Interface <strong>$name</strong> created");
redirect();
}
if (isset($_POST['add_asset_multiple_interfaces'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_POST['asset_id']);
$interface_start = intval($_POST['interface_start']);
$interfaces = intval($_POST['interfaces']);
$type = escapeSql($_POST['type']);
$name_prefix = escapeSql($_POST['name_prefix']);
$network = intval($_POST['network']);
$notes = escapeSql($_POST['notes']);
$sql = mysqli_query($mysqli, "SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
for ($interface_number = $interface_start; $interface_number < $interface_start + $interfaces; $interface_number++) {
// Format $interface_number as a 2-digit number
$formatted_interface_number = str_pad($interface_number, 2, '0', STR_PAD_LEFT);
$sql_insert = "
INSERT INTO asset_interfaces SET
interface_name = '$name_prefix$formatted_interface_number',
interface_type = '$type',
interface_notes = '$notes',
interface_network_id = $network,
interface_asset_id = $asset_id
";
mysqli_query($mysqli, $sql_insert);
logAudit("Asset Interface", "Create", "$session_name created interface $name for asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset Interface", "Bulk Create", "$session_name created $interfaces for asset $asset_name", $client_id, $asset_id);
flashAlert("Created <strong>$interfaces</strong> Interface(s) for asset <strong>$asset_name</strong>");
redirect();
}
if (isset($_POST['edit_asset_interface'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
// Interface info
$interface_id = intval($_POST['interface_id']);
require_once 'asset_interface_model.php';
// sets: $name, $mac, $ip, $ipv6, $port, $notes, $network, $connected_to, etc.
// 1) Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli, "
SELECT asset_name, asset_client_id, asset_id
FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
WHERE interface_id = $interface_id
");
$row = mysqli_fetch_assoc($sql);
$asset_id = intval($row['asset_id']);
$asset_name= escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// 2) Update the interface details in asset_interfaces
$sql_update = "
UPDATE asset_interfaces SET
interface_name = '$name',
interface_description= '$description',
interface_type = '$type',
interface_mac = '$mac',
interface_ip = '$ip',
interface_nat_ip = '$nat_ip',
interface_ipv6 = '$ipv6',
interface_notes = '$notes',
interface_network_id = $network
WHERE interface_id = $interface_id
";
mysqli_query($mysqli, $sql_update);
// If Primary Interface Checked set all interfaces primary to 0 then set the new interface as primary with a 1
if ($primary_interface) {
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_primary = 0 WHERE interface_asset_id = $asset_id");
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_primary = 1 WHERE interface_id = $interface_id");
}
// 3) Remove any existing link for this interface (one-to-one)
$sql_delete_link = "
DELETE FROM asset_interface_links
WHERE interface_a_id = $interface_id
OR interface_b_id = $interface_id
";
mysqli_query($mysqli, $sql_delete_link);
// 4) If user selected a connected interface, create a new link
if (!empty($connected_to) && intval($connected_to) > 0) {
$sql_link = "
INSERT INTO asset_interface_links SET
interface_a_id = $interface_id,
interface_b_id = $connected_to
";
mysqli_query($mysqli, $sql_link);
}
// 5) Logging
logAudit(
"Asset Interface",
"Edit",
"$session_name edited interface $name for asset $asset_name",
$client_id,
$asset_id
);
// 6) Alert and redirect
flashAlert("Interface <strong>$name</strong> edited");
redirect();
}
if (isset($_GET['delete_asset_interface'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$interface_id = intval($_GET['delete_asset_interface']);
// 1) Fetch details for logging / alerts
$sql = mysqli_query($mysqli, "
SELECT asset_name, interface_name, asset_client_id, asset_id
FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
WHERE interface_id = $interface_id
");
$row = mysqli_fetch_assoc($sql);
$asset_id = intval($row['asset_id']);
$interface_name = escapeSql($row['interface_name']);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// 2) Delete the interface this cascadingly delete asset_interface_links
mysqli_query($mysqli, "
DELETE FROM asset_interfaces
WHERE interface_id = $interface_id
");
// 3) Logging
logAudit(
"Asset Interface",
"Delete",
"$session_name deleted interface $interface_name from asset $asset_name",
$client_id,
$asset_id
);
// 4) Alert and redirect
flashAlert("Interface <strong>$interface_name</strong> deleted", 'error');
redirect();
}
if (isset($_POST['bulk_edit_asset_interface_type'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$type = escapeSql($_POST['bulk_type']);
if (isset($_POST['interface_ids'])) {
// Get Count
$interface_count = count($_POST['interface_ids']);
foreach($_POST['interface_ids'] as $interface_id) {
$interface_id = intval($interface_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli, "
SELECT asset_name, asset_client_id, asset_id
FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
WHERE interface_id = $interface_id
");
$row = mysqli_fetch_assoc($sql);
$asset_id = intval($row['asset_id']);
$asset_name= escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// Update inteface type
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_type = '$type' WHERE interface_id = $interface_id");
logAudit("Asset Interface", "Edit", "$session_name set interface type to $type for asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset Interface", "Bulk Edit", "$session_name set interface type to $type on $interface_count interfaces for asset $asset_name", $client_id);
flashAlert("Type set to <strong>$type</strong> on <strong>$interface_count</strong> interfaces.");
}
redirect();
}
if (isset($_POST['bulk_edit_asset_interface_network'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$network_id = intval($_POST['bulk_network']);
// Get Network Name for logging
$network_name = escapeSql(getFieldById('networks', $network_id, 'network_name'));
if (isset($_POST['interface_ids'])) {
// Get Count
$interface_count = count($_POST['interface_ids']);
foreach($_POST['interface_ids'] as $interface_id) {
$interface_id = intval($interface_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli, "
SELECT asset_name, asset_client_id, asset_id
FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
WHERE interface_id = $interface_id
");
$row = mysqli_fetch_assoc($sql);
$asset_id = intval($row['asset_id']);
$asset_name= escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// Update inteface type
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_network_id = $network_id WHERE interface_id = $interface_id");
logAudit("Asset Interface", "Edit", "$session_name set network to $network_name for asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset Interface", "Bulk Edit", "$session_name set network to $network_name on $interface_count interfaces for asset $asset_name", $client_id);
flashAlert("Network set to <strong>$network_name</strong> on <strong>$interface_count</strong> interfaces.");
}
redirect();
}
if (isset($_POST['bulk_edit_asset_interface_ip_dhcp'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
if (isset($_POST['interface_ids'])) {
// Get Count
$interface_count = count($_POST['interface_ids']);
foreach($_POST['interface_ids'] as $interface_id) {
$interface_id = intval($interface_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli, "
SELECT asset_name, asset_client_id, asset_id
FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
WHERE interface_id = $interface_id
");
$row = mysqli_fetch_assoc($sql);
$asset_id = intval($row['asset_id']);
$asset_name= escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
// Update inteface type
mysqli_query($mysqli,"UPDATE asset_interfaces SET interface_ip = 'DHCP' WHERE interface_id = $interface_id");
logAudit("Asset Interface", "Edit", "$session_name set interface IP to DHCP for asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset Interface", "Bulk Edit", "$session_name set interface IP to DHCP on $interface_count interfaces for asset $asset_name", $client_id);
flashAlert("Interface IP set to <strong>DHCP</strong> on <strong>$interface_count</strong> interfaces.");
}
redirect();
}
if (isset($_POST['bulk_delete_asset_interfaces'])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
if (isset($_POST['interface_ids'])) {
// Get Count
$interface_count = count($_POST['interface_ids']);
foreach($_POST['interface_ids'] as $interface_id) {
$interface_id = intval($interface_id);
// Get Asset Name and Client ID for logging and alert message
$sql = mysqli_query($mysqli, "
SELECT asset_name, interface_name, asset_client_id, asset_id
FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
WHERE interface_id = $interface_id
");
$row = mysqli_fetch_assoc($sql);
$asset_id = intval($row['asset_id']);
$interface_name = escapeSql($row['interface_name']);
$asset_name = escapeSql($row['asset_name']);
$client_id = intval($row['asset_client_id']);
enforceClientAccess();
mysqli_query($mysqli, "DELETE FROM asset_interfaces WHERE interface_id = $interface_id");
logAudit("Asset Interface", "Delete", "$session_name deleted interface $interface_name from asset $asset_name", $client_id, $asset_id);
}
logAudit("Asset Interface", "Bulk Delete", "$session_name deleted $interface_count interfaces for asset $asset_name", $client_id);
flashAlert("<strong>$interface_count</strong> interfaces deleted.", 'error');
}
redirect();
}
if (isset($_POST["import_client_asset_interfaces_csv"])) {
validateCSRFToken();
enforceUserPermission('module_support', 2);
$asset_id = intval($_POST['asset_id']);
$file_name = $_FILES["file"]["tmp_name"];
// Get Asset Details for logging
$sql_asset = mysqli_query($mysqli,"SELECT asset_client_id, asset_name FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql_asset);
$client_id = intval($row['asset_client_id']);
$asset_name = escapeSql($row['asset_name']);
enforceClientAccess();
$error = false;
if (!empty($_FILES["file"]["tmp_name"])) {
$file_name = $_FILES["file"]["tmp_name"];
} else {
flashAlert("Please select a file to upload.", 'error');
redirect();
}
//Check file is CSV
$file_extension = strtolower(end(explode('.',$_FILES['file']['name'])));
$allowed_file_extensions = array('csv');
if (in_array($file_extension,$allowed_file_extensions) === false) {
$error = true;
flashAlert("Bad file extension", 'error');
}
//Check file isn't empty
elseif ($_FILES["file"]["size"] < 1) {
$error = true;
flashAlert("Bad file size (empty?)", 'error');
}
//(Else)Check column count (Name, Description, Type, MAC, IP, NAT IP, IPv6, Network)
$f = fopen($file_name, "r");
$f_columns = fgetcsv($f, 1000, ",");
if (!$error & count($f_columns) != 8) {
$error = true;
flashAlert("Bad column count.", 'error');
}
//Else, parse the file
if (!$error) {
$file = fopen($file_name, "r");
fgetcsv($file, 1000, ","); // Skip first line
$row_count = 0;
$duplicate_count = 0;
while(($column = fgetcsv($file, 1000, ",")) !== false) {
// Default variables (if undefined)
$description = $type = $mac = $ip = $nat_ip = $ipv6 = $network = '';
$network_id = 0;
$duplicate_detect = 0;
if (isset($column[0])) {
$name = escapeSql($column[0]);
if (mysqli_num_rows(mysqli_query($mysqli,"SELECT interface_name FROM asset_interfaces WHERE interface_asset_id = $asset_id AND interface_name = '$name'")) > 0) {
$duplicate_detect = 1;
}
}
if (!empty($column[1])) {
$description = escapeSql($column[1]);
}
if (!empty($column[2])) {
$type = escapeSql($column[2]);
}
if (!empty($column[3])) {
$mac = escapeSql($column[3]);
}
if (!empty($column[4])) {
$ip = escapeSql($column[4]);
}
if (!empty($column[5])) {
$nat_ip = escapeSql($column[5]);
}
if (!empty($column[6])) {
$ipv6 = escapeSql($column[6]);
}
if (!empty($column[7])) {
$network = escapeSql($column[7]);
if ($network) {
$sql_network = mysqli_query($mysqli,"SELECT network_id FROM networks WHERE network_name = '$network' AND network_archived_at IS NULL AND network_client_id = $client_id");
$row = mysqli_fetch_assoc($sql_network);
$network_id = intval($row['network_id']);
}
}
// Check if duplicate was detected
if ($duplicate_detect == 0) {
//Add
mysqli_query($mysqli,"INSERT INTO asset_interfaces SET interface_name = '$name', interface_description = '$description', interface_type = '$type', interface_mac = '$mac', interface_ip = '$ip', interface_nat_ip = '$nat_ip', interface_ipv6 = '$ipv6', interface_network_id = $network_id, interface_asset_id = $asset_id");
$row_count = $row_count + 1;
} else {
$duplicate_count = $duplicate_count + 1;
}
}
fclose($file);
logAudit("Asset", "Import", "$session_name imported $row_count interfaces(s) to asset $asset_name via CSV file", $client_id);
flashAlert("<strong>$row_count</strong> Interfaces(s) added to asset <strong>$asset_name</strong>, <strong>$duplicate_count</strong> duplicate(s) detected");
redirect();
}
//Check for any errors, if there are notify user and redirect
if ($error) {
redirect();
}
}
if (isset($_GET['download_client_asset_interfaces_csv_template'])) {
$asset_id = intval($_GET['download_client_asset_interfaces_csv_template']);
//get records from database
$sql = mysqli_query($mysqli,"SELECT asset_name, asset_client_id FROM assets WHERE asset_id = $asset_id");
$row = mysqli_fetch_assoc($sql);
$asset_name = $row['asset_name'];
$delimiter = ",";
$enclosure = '"';
$escape = '\\';
$filename = toAlphanumeric($asset_name) . "-Asset-Interfaces-Template.csv";
//create a file pointer
$f = fopen('php://memory', 'w');
//set column headers
$fields = array('Name', 'Description', 'Type', 'MAC', 'IP', 'NAT IP', 'IPv6', 'Network');
fputcsv($f, $fields, $delimiter, $enclosure, $escape);
//move back to beginning of file
fseek($f, 0);
//set headers to download file rather than displayed
header('Content-Type: text/csv');
header('Content-Disposition: attachment; filename="' . $filename . '";');
//output all remaining data on a file pointer
fpassthru($f);
exit;
}
if (isExportRequest('export_asset_interfaces')) {
validateCSRFToken();
enforceUserPermission('module_support');
$format = resolveExportFormat($_POST['export_asset_interfaces']);
$asset_id = intval($_POST['asset_id']);
$client_id = intval(getFieldById('assets', $asset_id, 'asset_client_id'));
enforceClientAccess();
$asset_name = getFieldById('assets', $asset_id, 'asset_name');
// Get records from database - scoped to the one asset, so no page filters apply
$sql = mysqli_query(
$mysqli,
"SELECT * FROM asset_interfaces
LEFT JOIN assets ON asset_id = interface_asset_id
LEFT JOIN networks ON interface_network_id = network_id
LEFT JOIN clients ON asset_client_id = client_id
WHERE asset_id = $asset_id
AND interface_archived_at IS NULL
ORDER BY interface_name ASC"
);
$num_rows = mysqli_num_rows($sql);
if ($num_rows > 0) {
guardExportPdfRowCount($format, $num_rows);
$export = beginExport('asset_interfaces', $format, toAlphanumeric($asset_name) . '-Interfaces', "$asset_name - Interfaces", '');
while ($row = mysqli_fetch_assoc($sql)) {
addExportRow($export, $row);
}
finishExport($export);
}
logAudit("Asset Interface", "Export", "$session_name exported $num_rows interface(s) to a " . strtoupper($format) . " file", $client_id);
exit;
}