ISE Commands
ERS API Commands
Endpoints
# List all endpoints
netapi ise get-endpoints
# Get endpoint by MAC address
netapi ise get-endpoint C8:5B:76:C6:59:62
# JSON output for jq processing
netapi ise --format json get-endpoint C8:5B:76:C6:59:62 | jq
Identity Groups
Identity groups are static user/certificate-based groups for authorization policies. These are different from endpoint identity groups (which group devices by MAC address).
# List all identity groups
netapi ise get-identity-groups
# Create a new identity group
netapi ise create-identity-group "Linux-Research-Workstations" \
--description "Linux research workstations - certificate-based identity for EAP-TLS"
# Create with parent group
netapi ise create-identity-group "Research-Linux" \
--parent "User Identity Groups" \
--description "Research Linux machines"
# Delete identity group
netapi ise delete-identity-group "Test-Group"
# Force delete (no confirmation)
netapi ise delete-identity-group "Test-Group" --force
|
Identity Groups vs Endpoint Groups
For EAP-TLS deployments, you’ll create static identity groups and reference them in authorization policies. |
Network Access Devices
# List all NADs
netapi ise get-nads
# Get specific NAD by name
netapi ise get-nad "SW-CORE-01"
Security Group Tags
# List all SGTs
netapi ise get-sgts
# Get specific SGT by name
netapi ise get-sgt "Employees"
Authorization Profiles
# List all authorization profiles
netapi ise get-authz-profiles
# Get specific profile by name
netapi ise get-authz-profile "PermitAccess"
# Update authorization profile VLAN or DACL
netapi ise update-authz-profile "ProfileName" --vlan ADMIN_VLAN --dacl "PERMIT_ALL"
# Remove dACL from profile (for troubleshooting)
netapi ise update-authz-profile "ProfileName" --no-dacl
Create Authorization Profile
# Create profile with VLAN and DACL
netapi ise create-authz-profile Domus_Admin_Profile --vlan ADMIN_VLAN --dacl DACL_ADMIN_FULL
# Create profile with description
netapi ise create-authz-profile Domus_Guest_Profile \
--vlan GUEST_VLAN \
--dacl DACL_GUEST_INTERNET \
--descr "Guest internet only"
Bulk Create from YAML
Create a YAML file with profile definitions:
# domus-authz-profiles.yaml
profiles:
Domus_Admin_Profile:
description: "Admin full access"
vlan: ADMIN_VLAN
dacl: DACL_ADMIN_FULL
Domus_Secure_Profile:
description: "Trusted users - deny management"
vlan: SECURE_VLAN
dacl: DACL_SECURE_FULL
Domus_Guest_Profile:
description: "Guest - internet only"
vlan: GUEST_VLAN
dacl: DACL_GUEST_INTERNET
Then deploy:
# Create all profiles from YAML
netapi ise create-authz-profiles-from-file examples/domus-authz-profiles.yaml
# Skip existing profiles (default)
netapi ise create-authz-profiles-from-file examples/domus-authz-profiles.yaml --skip-existing
|
VLAN names must match your switch VLAN names exactly! Check your switch: Use the VLAN name (e.g., |
A sample YAML file is included at examples/domus-authz-profiles.yaml.
Downloadable ACLs (dACLs)
# List all DACLs
netapi ise get-dacls
# Get specific DACL by name
netapi ise get-dacl DACL_ADMIN_FULL
Create dACL
# Simple inline ACL
netapi ise create-dacl DACL_ADMIN_FULL --acl "permit ip any any"
# Multi-line ACL (semicolon-separated)
netapi ise create-dacl DACL_IOT --acl "permit udp any any eq 53; deny ip any 10.0.0.0 0.255.255.255; permit ip any any"
# From file
netapi ise create-dacl DACL_SECURE --file /path/to/dacl.txt
# With description
netapi ise create-dacl DACL_GUEST_INTERNET \
--descr "Guest internet only" \
--acl "permit udp any any eq 53; deny ip any 10.0.0.0 0.255.255.255; permit ip any any"
Delete dACL
# Delete with confirmation
netapi ise delete-dacl DACL_TEST
# Force delete (no confirmation)
netapi ise delete-dacl DACL_TEST --force
Bulk Create from YAML
Create a YAML file with dACL definitions:
# domus-dacls.yaml
dacls:
DACL_ADMIN_FULL:
description: "Full admin access including management"
acl: |
remark Full admin access including management
permit ip any any
DACL_SECURE_FULL:
description: "Trusted users - deny management subnet"
acl: |
remark Trusted users - deny management subnet
deny ip any 10.50.1.0 0.0.0.31
permit ip any any
DACL_IOT_RESTRICTED:
description: "IoT devices - internet only"
acl: |
remark IoT devices - internet only
permit udp any any eq 53
permit udp any any eq 67
permit udp any any eq 123
deny ip any 10.0.0.0 0.255.255.255
deny ip any 172.16.0.0 0.15.255.255
deny ip any 192.168.0.0 0.0.255.255
permit ip any any
DACL_GUEST_INTERNET:
description: "Guest - internet only no internal"
acl: |
remark Guest - internet only no internal
permit udp any any eq 53
permit udp any any eq 67
deny ip any 10.0.0.0 0.255.255.255
deny ip any 172.16.0.0 0.15.255.255
deny ip any 192.168.0.0 0.0.255.255
permit ip any any
DACL_VOICE_SIP:
description: "VoIP phones - SIP/RTP"
acl: |
remark VoIP phones - SIP/RTP
permit udp any any eq 53
permit udp any any eq 67
permit udp any any eq 123
permit udp any any eq 5060
permit tcp any any eq 5061
permit udp any any range 16384 32767
permit ip any any
Then deploy:
# Create all DACLs from YAML
netapi ise create-dacls-from-file domus-dacls.yaml
# Skip existing DACLs (default)
netapi ise create-dacls-from-file domus-dacls.yaml --skip-existing
A sample YAML file is included at examples/domus-dacls.yaml.
Policy Sets
# List all network access policy sets (shows conditions)
netapi ise get-policy-sets
# Get specific policy set by name
netapi ise get-policy-set "Corp WIFI"
netapi ise get-policy-set "Wired Dot1X Closed"
Update Policy Set
Rename or update policy set metadata:
# Rename policy set (requires description)
netapi ise update-policy-set "IoT WIFI iPSK" --name "Domus-IoT iPSK" --description "iPSK for IoT devices"
# Update description only
netapi ise update-policy-set "Corp WIFI" --description "Corporate EAP-TLS wireless"
# Change state
netapi ise update-policy-set "Legacy WIFI" --state disabled
Add Policy Set Condition (Safe)
Add a condition to a policy set while preserving existing conditions. This is the recommended command for adding SSID matches to wireless policies.
# Add Domus-Secure SSID to Corp WIFI (keeps existing HomeRF condition)
netapi ise add-policy-set-condition "Corp WIFI" "Domus-Secure"
# Add another SSID to the same policy
netapi ise add-policy-set-condition "Corp WIFI" "CorpNet-5G"
# Use different attribute/operator (e.g., for IoT prefix matching)
netapi ise add-policy-set-condition "IoT WIFI" "IoT_" --operator startsWith
This creates a ConditionOrBlock (OR logic) combining existing and new conditions. Clients matching ANY of the conditions will use this policy set.
|
The |
Replace Policy Set Condition (Destructive)
|
DESTRUCTIVE OPERATION: This command DELETES all existing conditions and replaces them with a single new condition. All clients matching the old condition(s) will LOSE connectivity immediately! Only use this if you truly want to REPLACE, not ADD. Requires |
# DANGEROUS: Replace ALL conditions with just Domus-Secure
# This DELETES the existing HomeRF condition!
netapi ise replace-policy-set-condition "Corp WIFI" "Domus-Secure" --force
If you want to match multiple SSIDs, use add-policy-set-condition instead.
Authentication Rules
# List authentication rules for a policy set
netapi ise get-auth-rules "Corp WIFI"
netapi ise get-auth-rules "Wired Dot1X Closed"
# Add EAP-TLS authentication rule (most common use case)
netapi ise add-auth-rule "Corp WIFI" "EAP_TLS_Cert_Auth" "AD_Cert_Profile"
# Add rule with custom condition
netapi ise add-auth-rule "Guest WIFI" "MAB_Auth" "Internal Endpoints" \
--dict "Radius" --attr "Service-Type" --value "Call-Check"
Authorization Rules
# List authorization rules for a policy set (shows conditions)
netapi ise get-authz-rules "Corp WIFI"
netapi ise get-authz-rules "Wired Dot1X Closed"
# Add EAP-TLS authorization rule (most common use case)
netapi ise add-authz-rule "Corp WIFI" "EAP_TLS_Trusted" "Domus_Secure_Profile"
# Add rule with custom condition (e.g., AD group membership)
netapi ise add-authz-rule "Corp WIFI" "AD_Users" "PermitAccess" \
--dict "AD" --attr "ExternalGroups" --value "domain.com/Users" --operator contains
The get-authz-rules output now shows the Condition column:
# Rule Name Condition Profile(s) State
0 Domus-IoT Access iPSKManager:ExternalGroups equals iPSK-Auth enabled
'Domus-IoT'
1 Default (default) iPSK-Auth enabled
|
Every ISE policy set using EAP-TLS needs BOTH rules:
This applies to wired AND wireless policy sets independently. Missing either rule causes authentication failures (22045 for missing auth rule, 15039 for missing authz rule). |
ODBC Identity Sources
Query external ODBC identity sources like iPSKManager for group membership.
# Fetch groups from iPSKManager ODBC source
netapi ise get-odbc-groups iPSKManager
# With explicit browser session (if auto-login fails)
netapi ise get-odbc-groups iPSKManager --session "APPSESSIONID=..." --csrf "..."
|
The Groups must be saved to ISE’s ODBC configuration via GUI for use in authorization rule conditions. |
Certificate Authentication Profiles
Certificate authentication profiles define how ISE extracts identity from X.509 certificates during EAP-TLS authentication.
# List all certificate authentication profiles
netapi ise get-cert-profiles
# Get specific profile details
netapi ise get-cert-profile AD_Cert_Profile
# Create new certificate profile
netapi ise create-cert-profile Windows_Cert_Profile \
--desc "Windows EAP-TLS/TEAP authentication" \
--attr SUBJECT_COMMON_NAME
# Create profile using SAN (Subject Alternative Name)
netapi ise create-cert-profile Linux_SAN_Profile \
--desc "Linux with SAN-based identity" \
--attr SUBJECT_ALTERNATIVE_NAME_DNS
Certificate attributes for identity extraction:
| Attribute | Use Case |
|---|---|
|
Most common - extracts CN from certificate subject |
|
SAN field (preferred for modern certs) |
|
DNS name from SAN (e.g., |
|
Email from SAN (user certificates) |
|
Device serial number (hardware-bound certs) |
Allowed Protocols (EAP Configuration)
View and understand the EAP methods enabled in ISE. This is critical for security - avoid MSCHAPv2.
# List allowed protocol services
netapi ise get-allowed-protocols
# Get EAP method details for a protocol service
netapi ise get-allowed-protocol "Default Network Access"
Example output:
EAP-TLS enabled # Certificate-based - GOOD
EAP-TEAP enabled # Tunneled EAP - check inner methods
PEAP enabled # Legacy - check inner methods
TEAP-EAP-TLS enabled # Cert in tunnel - GOOD
TEAP-MSCHAPv2 enabled # PASSWORD - DISABLE THIS
|
MSCHAPv2 is fundamentally broken. It uses NTLM hashes which can be cracked offline. For EAP-TEAP deployments:
Pure EAP-TLS or EAP-TEAP with EAP-TLS inner method only. No exceptions. |
Policy Audit
Full audit of all policy sets with authentication and authorization rules. Essential for brownfield assessments.
# Run full policy audit (console output)
netapi ise audit
# Save audit to JSON file
netapi ise audit --output /tmp/ise-audit.json
# Audit with JSON output for processing
netapi ise audit --format json | jq '.[] | select(.policy_set == "Wired Dot1X Closed")'
The audit command loops through all policy sets and displays:
-
Authentication rules (identity source mappings)
-
Authorization rules (profile assignments)
This replaces manual GUI inspection for policy review.
Rejected Endpoints (Anti-RADIUS-Spray)
ISE protects against RADIUS spray attacks by temporarily blocking endpoints after repeated authentication failures. Use these commands to manage rejected endpoints:
# List all rejected endpoints
netapi ise get-rejected-endpoints
# Release a rejected endpoint (allow new auth attempts)
netapi ise release-rejected 14:F6:D8:7B:31:80
|
If an endpoint shows |
Endpoint Management
# Move endpoint to different identity group
netapi ise update-endpoint-group C8:5B:76:C6:59:62 Blacklist
# Move with non-static assignment (allows re-profiling)
netapi ise update-endpoint-group C8:5B:76:C6:59:62 Profiled --no-static
ANC (Adaptive Network Control)
# List all ANC policies
netapi ise get-anc-policies
# List endpoints with ANC policies applied
netapi ise get-anc-endpoints
# Apply ANC policy (quarantine, shutdown, port bounce)
netapi ise anc-apply C8:5B:76:C6:59:62 Quarantine
# Clear ANC policy from endpoint
netapi ise anc-clear C8:5B:76:C6:59:62
MnT API Commands
Active Sessions
# List all active RADIUS sessions
netapi ise mnt sessions
# Get session count
netapi ise mnt count
Session Lookup
# Get session by MAC address
netapi ise mnt session C8:5B:76:C6:59:62
# Get session by IP address
netapi ise mnt session-ip 10.50.40.100
# Get session by username
netapi ise mnt session-user jsmith
Authentication Logs
# Get recent authentication attempts
netapi ise mnt auth-logs
# Get authentication status for a MAC
netapi ise mnt auth-status C8:5B:76:C6:59:62
# Get failed authentication attempts
netapi ise mnt failed
# List failure reason codes
netapi ise mnt failure-reasons
DataConnect API Commands
Endpoint Queries
# List endpoints from DataConnect
netapi ise dc endpoints
# Get endpoint details
netapi ise dc endpoint C8:5B:76:C6:59:62
Live RADIUS Authentication Log
# Get recent authentications (last hour, all statuses)
netapi ise dc recent
# Get recent authentications (last 4 hours)
netapi ise dc recent --hours 4
# Get only successful authentications
netapi ise dc recent --status passed
# Get only failures (same as dc failed)
netapi ise dc recent --status failed
# Get failed authentications (last 24 hours, detailed)
netapi ise dc failed
netapi ise dc failed --hours 48 --limit 200
|
Use |
Output Formats
All commands support multiple output formats:
| Format | Description |
|---|---|
|
YAML output (default) |
|
JSON output (for jq) |
|
Rich table output |
Advanced Examples
Sessions by VLAN
netapi ise mnt --format json sessions | \
jq -r '.[] | select(.vlan=="40") | [.calling_station_id, .framed_ip_address] | @tsv'
Count by NAD
netapi ise mnt --format json sessions | \
jq -r 'group_by(.nas_ip_address) | map({nad: .[0].nas_ip_address, count: length}) | .[]'
Auth Stats One-liner
netapi ise dc --format json stats | \
jq -r '"Auth: \(.total) total, \(.passed) passed, \(.failed) failed"'
Validation Loops
Use these bash loops to quickly validate ISE API connectivity and explore available data.
MnT API Validation
for cmd in version count sessions; do
echo "=== ise mnt $cmd ==="
uv run netapi ise mnt $cmd 2>&1 | head -20
echo
done
DataConnect Validation
for cmd in test stats profiler device-types; do
echo "=== ise dc $cmd ==="
uv run netapi ise dc $cmd 2>&1 | head -20
echo
done
ERS API Validation
for cmd in get-endpoints get-endpoint-groups get-nads get-sgts get-authz-profiles get-dacls get-nodes get-policy-sets; do
echo "=== ise $cmd ==="
uv run netapi ise $cmd 2>&1 | head -20
echo
done
Policy Set Deep Dive
for ps in 'Corp WIFI' 'HomeRF WPA2PSK' 'Corp LAN MAB' 'Wired Dot1X Closed' 'IoT WIFI iPSK' 'Guest WIFI'; do
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
echo "Policy Set: $ps"
echo "━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━━"
uv run netapi ise get-policy-set "$ps" 2>&1 | head -30
echo
echo "--- Authentication Rules ---"
uv run netapi ise get-auth-rules "$ps" 2>&1 | head -15
echo
echo "--- Authorization Rules ---"
uv run netapi ise get-authz-rules "$ps" 2>&1 | head -15
echo
done
Full ISE Recon
Comprehensive ISE reconnaissance loop for auditing:
echo "╔════════════════════════════════════════════════════════════════════╗"
echo "║ ISE RECONNAISSANCE REPORT ║"
echo "╚════════════════════════════════════════════════════════════════════╝"
echo
echo "=== MnT Version ==="
uv run netapi ise mnt version
echo
echo "=== Active Sessions ==="
uv run netapi ise mnt count
echo
echo "=== DataConnect Stats ==="
uv run netapi ise dc stats
echo
echo "=== Policy Sets ==="
uv run netapi ise get-policy-sets
echo
echo "=== Authorization Profiles ==="
uv run netapi ise get-authz-profiles
echo
echo "=== Downloadable ACLs ==="
uv run netapi ise get-dacls
echo
echo "=== Deployment Nodes ==="
uv run netapi ise get-nodes
echo
echo "=== Profiler Summary ==="
uv run netapi ise dc profiler
echo
echo "=== Device Types ==="
uv run netapi ise dc device-types
|
Save these loops as shell scripts in
Then run with: |
Troubleshooting Workflows
Real-world troubleshooting patterns for 802.1X/MAB connectivity issues.
ISE-Only Investigation (No Switch Access)
When you don’t have switch access, you can still gather significant information from ISE.
MAC="00:50:C2:39:F0:F7"
# [CHECK] Get current session status
netapi ise mnt session $MAC
# Look at: Status (PASSED/FAILED), NAD Name, Port, VLAN assigned
# [CHECK] If FAILED, check authentication history
netapi ise mnt auth-status $MAC
# [CHECK] Get the dACL rules being applied
# Note: Switch shows "xACSACLx-IP-TEST_Medical_Temp_Monitor-697290bb"
# The actual dACL name in ISE is just "TEST_Medical_Temp_Monitor"
netapi ise get-dacl TEST_Medical_Temp_Monitor
# [CHECK] See if endpoint is rejected (anti-RADIUS-spray)
netapi ise get-rejected-endpoints
# [FIX] If rejected, release it
netapi ise release-rejected $MAC
# [CHECK] Recent auth attempts from DataConnect
netapi ise dc recent --hours 1 | grep -i "$MAC"
What you CAN’T see from ISE alone:
-
Switch physical port status (up/down)
-
Switch MAC address table
-
Actual ACL deployed on switch interface
-
Physical layer issues (cable, SFP, etc.)
ISE + Switch Investigation (Full Access)
Complete troubleshooting workflow with both ISE and switch access.
# === PHASE 1: ISE Investigation ===
MAC="00:50:C2:39:F0:F7"
# [CHECK] Get last known session
netapi ise mnt session $MAC
# Note the NAD IP and Port from output
# [CHECK] If no active session, check auth history
netapi ise mnt auth-status $MAC
# === PHASE 2: Switch Investigation ===
# SSH to the NAD shown in ISE session output
sudo ssh admin@<NAD_IP>
# [MAC Table] Check if endpoint is in CAM table
show mac address address 00:50:C2:39:F0:F7
# [NAS PORT] Check port status
show interfaces GigabitEthernet4/0/11 status
# [ACCESS SESSION] Check 802.1X/MAB session
show access-session interface GigabitEthernet4/0/11 detail
# [PORT CONFIG] Check interface configuration
show run interface GigabitEthernet4/0/11
# === PHASE 3: Remediation ===
# [FIX] If VLAN mismatch (device in wrong VLAN)
conf t
interface GigabitEthernet4/0/11
switchport access vlan 751
exit
exit
# [WAIT] Wait for MAB auth (30-45s if dot1x times out first)
show access-session interface GigabitEthernet4/0/11 detail
# === PHASE 4: Validation ===
# [DONE] Ping from your workstation
ping -c 3 <endpoint_ip>
# [DONE] Confirm via netapi
netapi ise mnt session $MAC
Common Patterns
Pattern: Device in Wrong VLAN
Symptoms:
-
Device not reachable
-
ISE session shows "PASSED" but wrong VLAN
-
Switch port shows static VLAN instead of dynamic
Root Cause:
-
Port
switchport access vlanoverrides ISE-assigned VLAN -
Or ISE authorization profile configured with wrong VLAN name
Fix:
# Check what VLAN ISE is assigning
netapi ise mnt session $MAC | grep -i vlan
# If ISE shows correct VLAN but switch has different:
conf t
interface GigabitEthernet4/0/11
switchport access vlan 751 # Match ISE's assigned VLAN
exit
Pattern: dot1x Timeout Before MAB
Symptoms:
-
30-45 second delay before device gets network access
-
Switch shows
dot1x: Runningthen eventuallymab: Authc Success -
Device doesn’t support 802.1X (IoT, medical devices, etc.)
Root Cause:
-
Interface template runs dot1x first, waits for timeout, then falls back to MAB
-
Template:
source template DefaultWiredDot1xClosedAuth
Visibility:
# Watch the access session transition
show access-session interface GigabitEthernet4/0/11 detail
# Initially shows:
# Status: Unauthorized
# Method status: dot1x Running
# After 30-45s shows:
# Status: Authorized
# Method status: dot1x Stopped, mab Authc Success
dACL Mapping Reference
When viewing ACLs on switch vs ISE:
| Switch Shows | ISE dACL Name |
|---|---|
|
|
|
|
|
|
The xACSACLx-IP- prefix and -<hash> suffix are added by the switch. To view the ACL rules:
# From ISE
netapi ise get-dacl TEST_Medical_Temp_Monitor
# From switch (shows runtime ACL)
show ip access-list xACSACLx-IP-TEST_Medical_Temp_Monitor-697290bb
Quick Reference: Troubleshooting Tags
Use consistent inline tags in your terminal logs:
# [CHECK] - verification/investigation step
# [FIX] - remediation action
# [WAIT] - async step (waiting for dot1x timeout, etc.)
# [DONE] - validation that fix worked
Example session:
# [CHECK] Get session from ISE
netapi ise mnt session 00:50:C2:39:F0:F7
# [CHECK] SSH to switch
sudo ssh admin@10.193.144.124
# [CHECK] View access session
show access-session interface GigabitEthernet4/0/11 detail
# [FIX] Correct VLAN assignment
conf t
interface GigabitEthernet4/0/11
switchport access vlan 751
exit
# [WAIT] Wait for MAB re-auth (~30-45s)
show access-session interface GigabitEthernet4/0/11 detail
# [DONE] Validate connectivity
ping -c 3 10.238.1.28