// Name: List Utilized Ports // Description: Lists all utilized ports (on Windows) and associated executables. // Author: JosXa interface PortEntry { protocol: string; localAddress: string; port: string; pid: string; } interface ProcessChoice { name: string; description: string; value: PortEntry; } // Execute netstat command to get network statistics const output = await exec(`netstat -ano`); // Split the output into lines and skip header lines const lines = output.stdout.split('\n').slice(4); // Map each line to a PortEntry object const ports: PortEntry[] = lines.map(line => { const parts = line.trim().split(/\s+/); const localAddress = parts[1]; const pid = parts[4]; let port = ''; if (localAddress) { const addressParts = localAddress.split(':'); port = addressParts[addressParts.length - 1]; } return { protocol: parts[0], localAddress, port, pid, }; }).filter(entry => entry.port); // Filter out entries with empty port // Create choices for the arg prompt based on utilized ports const choices: Choice<ProcessChoice>[] = await Promise.all(ports.map(async p => { let exeName = ''; try { // Execute tasklist command to get executable name for the PID const taskOutput = await exec(`tasklist /FI "PID eq ${p.pid}"`); const taskLines = taskOutput.stdout.split('\n'); if (taskLines.length > 2) { const taskParts = taskLines[2].trim().split(/\s+/); exeName = taskParts[0]; // Special case for System process if (exeName === "System" && p.pid === "4") { exeName = "[System Process]"; } } } catch (error: any) { // Handle errors when getting process info exeName = 'Error getting process info'; console.error(`Error fetching process info for PID ${p.pid}:`, error.message); } return { name: `${p.protocol} ${p.localAddress} ${exeName}`, description: `PID: ${p.pid}`, value: p as ProcessChoice // Type assertion for value }; })); // Display utilized ports in a list using arg prompt await arg<ProcessChoice>("Utilized Ports", choices);