1. Introduction: Why NSX-T Firewall Audits Matter
In the world of network virtualization, NSX-T is the gold standard for secure, scalable, and automated firewalling. But as rule sets grow in complexity, so do the risks of misconfiguration, redundancy, and policy drift. Manual audits are no longer sufficient for compliance, troubleshooting, or proactive risk management. Automated audits using Python and PowerShell can help you rapidly identify risky rules, unused entries, and policy gaps, even across multi-site environments.
In this guide, you’ll learn how to build robust firewall audit pipelines for NSX-T 4.x using end-to-end scripts, exporting, and reporting at scale. You’ll also get visual aids (diagrams) for architecture and rule flows, plus ready-to-use code.
2. Key Audit Risks in NSX-T
Firewalls are only as effective as their least restrictive rule. Here are the most critical risks in NSX-T firewall rule sets:
- Any/Any Rules: Rules that allow all sources and destinations. These are security anti-patterns.
- Unused Rules: Rules that never match traffic, often due to changes in topology or application decommissions.
- Shadowed Rules: Rules rendered ineffective by preceding rules with broader matches.
- Overly Broad Objects: Groups or services that contain too many members, reducing the precision of controls.
- Configuration Drift & Change History: Differences between intended and actual state over time.
Pro Tip: Automated audits should flag these issues and help prioritize remediation.
3. Architectural Overview
High-Level Firewall Audit Flow

4. API Authentication and Access Setup
Both Python and PowerShell scripts require secure NSX-T Manager API access. Create an API service account with read permissions for firewall policies. Note the NSX Manager FQDN/IP, username, and password or API token.
Best Practice:
Store credentials in environment variables or use secure vaults (never hardcode).
Python Authentication Example:
import requests
NSX_MANAGER = "nsx-manager.company.local"
USERNAME = "svc_api"
PASSWORD = "your_password"
session = requests.Session()
session.verify = False # For self-signed, consider proper CA in production
session.auth = (USERNAME, PASSWORD)
PowerShell Authentication Example:
$NSXManager = "nsx-manager.company.local"
$Username = "svc_api"
$Password = "your_password" | ConvertTo-SecureString -AsPlainText -Force
$Credential = New-Object System.Management.Automation.PSCredential ($Username, $Password)
5. Python Script: End-to-End Firewall Rule Audit
Below is a complete Python script to connect to NSX-T Manager, retrieve all DFW and GFW rules, and audit for common risks.
import requests
import csv
NSX_MANAGER = "nsx-manager.company.local"
USERNAME = "svc_api"
PASSWORD = "your_password"
session = requests.Session()
session.verify = False
session.auth = (USERNAME, PASSWORD)
base_url = f"https://{NSX_MANAGER}/policy/api/v1/infra"
def get_firewall_sections(fw_type):
if fw_type == "DFW":
url = f"{base_url}/domains/default/security-policies"
else: # GFW
url = f"{base_url}/gateways"
return session.get(url).json()
def get_rules(section_id, fw_type):
if fw_type == "DFW":
url = f"{base_url}/domains/default/security-policies/{section_id}/rules"
else:
url = f"{base_url}/gateways/{section_id}/firewall/security-policies"
return session.get(url).json()
def audit_rule(rule):
findings = []
if rule.get("source_groups") == ["ANY"] and rule.get("destination_groups") == ["ANY"]:
findings.append("ANY-ANY Rule")
if rule.get("disabled", False):
findings.append("Disabled Rule")
# Add shadow/unused detection here (advanced)
return findings
def export_to_csv(rules, filename):
with open(filename, mode='w', newline='') as file:
writer = csv.writer(file)
writer.writerow(["ID", "Name", "Source", "Destination", "Service", "Action", "Findings"])
for rule in rules:
findings = audit_rule(rule)
writer.writerow([
rule.get("id"),
rule.get("display_name"),
rule.get("source_groups"),
rule.get("destination_groups"),
rule.get("services"),
rule.get("action"),
"; ".join(findings)
])
def main():
all_rules = []
for fw_type in ["DFW", "GFW"]:
sections = get_firewall_sections(fw_type)
for section in sections.get("results", []):
rules = get_rules(section.get("id"), fw_type)
for rule in rules.get("results", []):
all_rules.append(rule)
export_to_csv(all_rules, "nsxt_firewall_audit.csv")
print("Audit complete. See nsxt_firewall_audit.csv.")
if __name__ == "__main__":
main()
Features:
- Connects directly to NSX-T Manager.
- Audits DFW and GFW rules.
- Exports findings to CSV.
6. PowerShell Script: End-to-End Firewall Rule Audit
$NSXManager = "nsx-manager.company.local"
$Username = "svc_api"
$Password = "your_password"
$BaseUri = "https://$NSXManager/policy/api/v1/infra"
$pair = "$Username`:$Password"
$encodedCreds = [Convert]::ToBase64String([Text.Encoding]::ASCII.GetBytes($pair))
$headers = @{ Authorization = "Basic $encodedCreds" }
function Get-FWSections {
param($fwType)
if ($fwType -eq "DFW") {
$url = "$BaseUri/domains/default/security-policies"
} else {
$url = "$BaseUri/gateways"
}
Invoke-RestMethod -Uri $url -Headers $headers -Method Get -SkipCertificateCheck
}
function Get-Rules {
param($sectionId, $fwType)
if ($fwType -eq "DFW") {
$url = "$BaseUri/domains/default/security-policies/$sectionId/rules"
} else {
$url = "$BaseUri/gateways/$sectionId/firewall/security-policies"
}
Invoke-RestMethod -Uri $url -Headers $headers -Method Get -SkipCertificateCheck
}
function Audit-Rule {
param($rule)
$findings = @()
if ($rule.source_groups -contains "ANY" -and $rule.destination_groups -contains "ANY") {
$findings += "ANY-ANY Rule"
}
if ($rule.disabled) {
$findings += "Disabled Rule"
}
return ($findings -join "; ")
}
$allRules = @()
foreach ($fwType in @("DFW", "GFW")) {
$sections = Get-FWSections $fwType
foreach ($section in $sections.results) {
$rules = Get-Rules $section.id $fwType
foreach ($rule in $rules.results) {
$findings = Audit-Rule $rule
$allRules += [PSCustomObject]@{
ID = $rule.id
Name = $rule.display_name
Source = $rule.source_groups -join ","
Destination = $rule.destination_groups -join ","
Service = $rule.services -join ","
Action = $rule.action
Findings = $findings
}
}
}
}
$allRules | Export-Csv -Path "nsxt_firewall_audit.csv" -NoTypeInformation
Write-Host "Audit complete. See nsxt_firewall_audit.csv."
7. Identifying Risky and Ineffective Rules
Risky rules are those that permit excessive access or are not used. Use the following logic in your scripts:
- ANY-ANY Rule: Flag any rule with source and destination as “ANY.”
- Unused Rule: Requires log analysis or hit counters (available via NSX-T monitoring APIs).
- Shadowed Rule: More advanced; compare rule order and matching criteria.
- Overly Broad: If source/destination groups include a high count of objects.
Example: Shadowed Rule Flow

Rule 2 is shadowed by Rule 1.
8. Reporting Strategies: CSV, HTML, and Markdown
CSV:
Direct export via Python or PowerShell, as shown above.
HTML Example:
def export_html(rules, filename):
with open(filename, "w") as f:
f.write("<html><body><h1>NSX-T Firewall Audit Report</h1><table border='1'>")
f.write("<tr><th>ID</th><th>Name</th><th>Source</th><th>Destination</th><th>Service</th><th>Action</th><th>Findings</th></tr>")
for rule in rules:
findings = audit_rule(rule)
f.write(f"<tr><td>{rule['id']}</td><td>{rule['display_name']}</td><td>{rule['source_groups']}</td><td>{rule['destination_groups']}</td><td>{rule['services']}</td><td>{rule['action']}</td><td>{'; '.join(findings)}</td></tr>")
f.write("</table></body></html>")
Markdown Example:
def export_md(rules, filename):
with open(filename, "w") as f:
f.write("| ID | Name | Source | Destination | Service | Action | Findings |\n")
f.write("|----|------|--------|-------------|---------|--------|----------|\n")
for rule in rules:
findings = audit_rule(rule)
f.write(f"| {rule['id']} | {rule['display_name']} | {rule['source_groups']} | {rule['destination_groups']} | {rule['services']} | {rule['action']} | {'; '.join(findings)} |\n")
9. Automating Scheduled Audits
- Linux:
Usecronjobs. t0 2 * * * /usr/bin/python3 /path/to/nsxt_audit.py - Windows:
Use Task Scheduler withpowershell.exeor the Python interpreter, depending on the script. - Email Alerts:
Add logic to send the report via SMTP after completion (optional).
10. Best Practices, Troubleshooting, and Real-World Tips
- Always run audits in a test environment before production.
- Use API tokens or service accounts with least-privilege access.
- Regularly update scripts for API changes in new NSX-T releases.
- Monitor API rate limits to avoid throttling in large environments.
- For multi-site, iterate over each NSX-T Manager cluster.
- Enable and query hit counters in NSX-T to detect unused rules (requires NSX Intelligence or similar feature).
11. Summary and Next Steps
Automating your NSX-T firewall rule audits with Python and PowerShell unlocks rapid, repeatable risk assessment for even the most complex environments. With detailed scripts, reporting, and visual architecture, you’re empowered to maintain compliance and security at scale. Extend these examples to integrate with SIEMs, ticketing, or orchestration pipelines for end-to-end policy lifecycle management.
Disclaimer: The views expressed in this article are those of the author and do not represent the opinions of VMware, my employer or any affiliated organization. Always refer to the official VMware documentation before production deployment.
Table of Contents 1. Introduction NSX-T 4.x overlay networking is the backbone of modern, software-defined data centers. By using technologies like GENEVE...