{
 "rules": [
  {
   "name": "edl-block-outbound",
   "from": [
    "any"
   ],
   "to": [
    "any"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "panw-bulletproof-ip-list",
    "panw-highrisk-ip-list",
    "panw-known-ip-list"
   ],
   "application": [
    "any"
   ],
   "service": [
    "any"
   ],
   "action": "deny",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "Outbound"
   ],
   "negate_destination": false,
   "description": "Iron Skillet outbound block rule: the predefined known-malicious, high-risk and bulletproof IP lists",
   "set_lines": [
    "set rulebase security rules edl-block-outbound from any",
    "set rulebase security rules edl-block-outbound to any",
    "set rulebase security rules edl-block-outbound source any",
    "set rulebase security rules edl-block-outbound destination [ panw-bulletproof-ip-list panw-highrisk-ip-list panw-known-ip-list ]",
    "set rulebase security rules edl-block-outbound source-user any",
    "set rulebase security rules edl-block-outbound category any",
    "set rulebase security rules edl-block-outbound application any",
    "set rulebase security rules edl-block-outbound service any",
    "set rulebase security rules edl-block-outbound action deny",
    "set rulebase security rules edl-block-outbound log-start no",
    "set rulebase security rules edl-block-outbound log-end yes",
    "set rulebase security rules edl-block-outbound tag Outbound",
    "set rulebase security rules edl-block-outbound description \"Iron Skillet outbound block rule: the predefined known-malicious, high-risk and bulletproof IP lists\""
   ],
   "n": 1,
   "why": "Iron Skillet day-one rule: the predefined threat-intel lists come first.",
   "links": [
    {
     "label": "Iron Skillet",
     "url": "https://github.com/PaloAltoNetworks/iron-skillet"
    },
    {
     "label": "best-practice step 1",
     "url": "https://docs.paloaltonetworks.com/best-practices/internet-gateway-best-practices/best-practice-internet-gateway-security-policy/define-the-initial-internet-gateway-security-policy/step-1-create-rules-based-on-trusted-threat-intelligence-sources"
    }
   ],
   "move_line": "move rulebase security rules edl-block-outbound top"
  },
  {
   "name": "edl-block-inbound",
   "from": [
    "any"
   ],
   "to": [
    "any"
   ],
   "source": [
    "panw-bulletproof-ip-list",
    "panw-highrisk-ip-list",
    "panw-known-ip-list"
   ],
   "destination": [
    "any"
   ],
   "application": [
    "any"
   ],
   "service": [
    "any"
   ],
   "action": "deny",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "Inbound"
   ],
   "negate_destination": false,
   "description": "Iron Skillet inbound block rule: the predefined known-malicious, high-risk and bulletproof IP lists",
   "set_lines": [
    "set rulebase security rules edl-block-inbound from any",
    "set rulebase security rules edl-block-inbound to any",
    "set rulebase security rules edl-block-inbound source [ panw-bulletproof-ip-list panw-highrisk-ip-list panw-known-ip-list ]",
    "set rulebase security rules edl-block-inbound destination any",
    "set rulebase security rules edl-block-inbound source-user any",
    "set rulebase security rules edl-block-inbound category any",
    "set rulebase security rules edl-block-inbound application any",
    "set rulebase security rules edl-block-inbound service any",
    "set rulebase security rules edl-block-inbound action deny",
    "set rulebase security rules edl-block-inbound log-start no",
    "set rulebase security rules edl-block-inbound log-end yes",
    "set rulebase security rules edl-block-inbound tag Inbound",
    "set rulebase security rules edl-block-inbound description \"Iron Skillet inbound block rule: the predefined known-malicious, high-risk and bulletproof IP lists\""
   ],
   "n": 2,
   "why": "The same three lists as a source.",
   "links": [
    {
     "label": "Iron Skillet",
     "url": "https://github.com/PaloAltoNetworks/iron-skillet"
    }
   ],
   "move_line": "move rulebase security rules edl-block-inbound after edl-block-outbound"
  },
  {
   "name": "ai-overlay-lan-direct",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "g-ai-nodes"
   ],
   "destination": [
    "g-overlay-lan-peers"
   ],
   "application": [
    "any"
   ],
   "service": [
    "s-udp-overlay"
   ],
   "action": "allow",
   "profile_group": "Outbound",
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "AI nodes to the two LAN peers on the overlay UDP port only (direct path). What rides inside is governed by the overlay policy",
   "set_lines": [
    "set rulebase security rules ai-overlay-lan-direct from ai",
    "set rulebase security rules ai-overlay-lan-direct to lan",
    "set rulebase security rules ai-overlay-lan-direct source g-ai-nodes",
    "set rulebase security rules ai-overlay-lan-direct destination g-overlay-lan-peers",
    "set rulebase security rules ai-overlay-lan-direct source-user any",
    "set rulebase security rules ai-overlay-lan-direct category any",
    "set rulebase security rules ai-overlay-lan-direct application any",
    "set rulebase security rules ai-overlay-lan-direct service s-udp-overlay",
    "set rulebase security rules ai-overlay-lan-direct action allow",
    "set rulebase security rules ai-overlay-lan-direct log-start no",
    "set rulebase security rules ai-overlay-lan-direct log-end yes",
    "set rulebase security rules ai-overlay-lan-direct profile-setting group Outbound",
    "set rulebase security rules ai-overlay-lan-direct tag ai-zone",
    "set rulebase security rules ai-overlay-lan-direct description \"AI nodes to the two LAN peers on the overlay UDP port only (direct path). What rides inside is governed by the overlay policy\""
   ],
   "n": 3,
   "why": "The overlay's (Tailscale) direct path to two named LAN hosts on its documented UDP port. What rides inside is governed by the overlay's own policy, not the firewall.",
   "links": [
    {
     "label": "overlay firewall ports",
     "url": "https://tailscale.com/docs/reference/faq/firewall-ports"
    }
   ],
   "move_line": "move rulebase security rules ai-overlay-lan-direct after edl-block-inbound"
  },
  {
   "name": "ai-block-private",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "g-not-internet"
   ],
   "application": [
    "any"
   ],
   "service": [
    "any"
   ],
   "action": "drop",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "AI zone may not reach any private, CGNAT, link-local or multicast address beyond the firewall",
   "set_lines": [
    "set rulebase security rules ai-block-private from ai",
    "set rulebase security rules ai-block-private to lan",
    "set rulebase security rules ai-block-private source any",
    "set rulebase security rules ai-block-private destination g-not-internet",
    "set rulebase security rules ai-block-private source-user any",
    "set rulebase security rules ai-block-private category any",
    "set rulebase security rules ai-block-private application any",
    "set rulebase security rules ai-block-private service any",
    "set rulebase security rules ai-block-private action drop",
    "set rulebase security rules ai-block-private log-start no",
    "set rulebase security rules ai-block-private log-end yes",
    "set rulebase security rules ai-block-private tag ai-zone",
    "set rulebase security rules ai-block-private description \"AI zone may not reach any private, CGNAT, link-local or multicast address beyond the firewall\""
   ],
   "n": 4,
   "why": "Nothing private beyond the firewall: RFC 1918, shared address space, link-local, multicast, reserved and this-network.",
   "links": [],
   "move_line": "move rulebase security rules ai-block-private after ai-overlay-lan-direct"
  },
  {
   "name": "ai-dns-sanctioned",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "g-ai-nodes"
   ],
   "destination": [
    "g-dns-sanctioned"
   ],
   "application": [
    "dns",
    "dns-base"
   ],
   "service": [
    "application-default"
   ],
   "action": "allow",
   "profile_group": "Outbound",
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "DNS to the sanctioned resolvers only (internet gateway best practice: allow only sanctioned DNS servers)",
   "set_lines": [
    "set rulebase security rules ai-dns-sanctioned from ai",
    "set rulebase security rules ai-dns-sanctioned to lan",
    "set rulebase security rules ai-dns-sanctioned source g-ai-nodes",
    "set rulebase security rules ai-dns-sanctioned destination g-dns-sanctioned",
    "set rulebase security rules ai-dns-sanctioned source-user any",
    "set rulebase security rules ai-dns-sanctioned category any",
    "set rulebase security rules ai-dns-sanctioned application [ dns dns-base ]",
    "set rulebase security rules ai-dns-sanctioned service application-default",
    "set rulebase security rules ai-dns-sanctioned action allow",
    "set rulebase security rules ai-dns-sanctioned log-start no",
    "set rulebase security rules ai-dns-sanctioned log-end yes",
    "set rulebase security rules ai-dns-sanctioned profile-setting group Outbound",
    "set rulebase security rules ai-dns-sanctioned tag ai-zone",
    "set rulebase security rules ai-dns-sanctioned description \"DNS to the sanctioned resolvers only (internet gateway best practice: allow only sanctioned DNS servers)\""
   ],
   "n": 5,
   "why": "Sanctioned resolvers only.",
   "links": [
    {
     "label": "best-practice step 3",
     "url": "https://docs.paloaltonetworks.com/best-practices/internet-gateway-best-practices/best-practice-internet-gateway-security-policy/define-the-initial-internet-gateway-security-policy/step-3-create-the-application-block-rules"
    }
   ],
   "move_line": "move rulebase security rules ai-dns-sanctioned after ai-block-private"
  },
  {
   "name": "ai-block-dns-other",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "any"
   ],
   "application": [
    "dns",
    "dns-base"
   ],
   "service": [
    "any"
   ],
   "action": "reset-both",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "Plain DNS to any other resolver is reset",
   "set_lines": [
    "set rulebase security rules ai-block-dns-other from ai",
    "set rulebase security rules ai-block-dns-other to lan",
    "set rulebase security rules ai-block-dns-other source any",
    "set rulebase security rules ai-block-dns-other destination any",
    "set rulebase security rules ai-block-dns-other source-user any",
    "set rulebase security rules ai-block-dns-other category any",
    "set rulebase security rules ai-block-dns-other application [ dns dns-base ]",
    "set rulebase security rules ai-block-dns-other service any",
    "set rulebase security rules ai-block-dns-other action reset-both",
    "set rulebase security rules ai-block-dns-other log-start no",
    "set rulebase security rules ai-block-dns-other log-end yes",
    "set rulebase security rules ai-block-dns-other tag ai-zone",
    "set rulebase security rules ai-block-dns-other description \"Plain DNS to any other resolver is reset\""
   ],
   "n": 6,
   "why": "Plain DNS to any other resolver is reset.",
   "links": [
    {
     "label": "best-practice step 3",
     "url": "https://docs.paloaltonetworks.com/best-practices/internet-gateway-best-practices/best-practice-internet-gateway-security-policy/define-the-initial-internet-gateway-security-policy/step-3-create-the-application-block-rules"
    }
   ],
   "move_line": "move rulebase security rules ai-block-dns-other after ai-dns-sanctioned"
  },
  {
   "name": "ai-block-doh-dot",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "any"
   ],
   "application": [
    "dns-over-https",
    "dns-over-tls"
   ],
   "service": [
    "any"
   ],
   "action": "reset-both",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "DoH and DoT hide DNS from the firewall; reset",
   "set_lines": [
    "set rulebase security rules ai-block-doh-dot from ai",
    "set rulebase security rules ai-block-doh-dot to lan",
    "set rulebase security rules ai-block-doh-dot source any",
    "set rulebase security rules ai-block-doh-dot destination any",
    "set rulebase security rules ai-block-doh-dot source-user any",
    "set rulebase security rules ai-block-doh-dot category any",
    "set rulebase security rules ai-block-doh-dot application [ dns-over-https dns-over-tls ]",
    "set rulebase security rules ai-block-doh-dot service any",
    "set rulebase security rules ai-block-doh-dot action reset-both",
    "set rulebase security rules ai-block-doh-dot log-start no",
    "set rulebase security rules ai-block-doh-dot log-end yes",
    "set rulebase security rules ai-block-doh-dot tag ai-zone",
    "set rulebase security rules ai-block-doh-dot description \"DoH and DoT hide DNS from the firewall; reset\""
   ],
   "n": 7,
   "why": "Encrypted DNS would hide queries from the firewall.",
   "links": [],
   "move_line": "move rulebase security rules ai-block-doh-dot after ai-block-dns-other"
  },
  {
   "name": "ai-block-evasive",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "any"
   ],
   "application": [
    "tor",
    "bittorrent",
    "openvpn",
    "ssh",
    "unknown-tcp",
    "unknown-udp",
    "unknown-p2p"
   ],
   "service": [
    "any"
   ],
   "action": "drop",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "No Tor, BitTorrent, OpenVPN, outbound SSH or unidentified traffic from the AI zone",
   "set_lines": [
    "set rulebase security rules ai-block-evasive from ai",
    "set rulebase security rules ai-block-evasive to lan",
    "set rulebase security rules ai-block-evasive source any",
    "set rulebase security rules ai-block-evasive destination any",
    "set rulebase security rules ai-block-evasive source-user any",
    "set rulebase security rules ai-block-evasive category any",
    "set rulebase security rules ai-block-evasive application [ tor bittorrent openvpn ssh unknown-tcp unknown-udp unknown-p2p ]",
    "set rulebase security rules ai-block-evasive service any",
    "set rulebase security rules ai-block-evasive action drop",
    "set rulebase security rules ai-block-evasive log-start no",
    "set rulebase security rules ai-block-evasive log-end yes",
    "set rulebase security rules ai-block-evasive tag ai-zone",
    "set rulebase security rules ai-block-evasive description \"No Tor, BitTorrent, OpenVPN, outbound SSH or unidentified traffic from the AI zone\""
   ],
   "n": 8,
   "why": "Applications with no legitimate use here are dropped on any port.",
   "links": [
    {
     "label": "best-practice step 3",
     "url": "https://docs.paloaltonetworks.com/best-practices/internet-gateway-best-practices/best-practice-internet-gateway-security-policy/define-the-initial-internet-gateway-security-policy/step-3-create-the-application-block-rules"
    }
   ],
   "move_line": "move rulebase security rules ai-block-evasive after ai-block-doh-dot"
  },
  {
   "name": "ai-infra-out",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "g-ai-nodes"
   ],
   "destination": [
    "g-not-internet"
   ],
   "application": [
    "ntp",
    "stun",
    "ping",
    "traceroute"
   ],
   "service": [
    "application-default"
   ],
   "action": "allow",
   "profile_group": "Outbound",
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": true,
   "description": "NTP, STUN (overlay connectivity checks), ping, traceroute on default ports",
   "set_lines": [
    "set rulebase security rules ai-infra-out from ai",
    "set rulebase security rules ai-infra-out to lan",
    "set rulebase security rules ai-infra-out source g-ai-nodes",
    "set rulebase security rules ai-infra-out destination g-not-internet",
    "set rulebase security rules ai-infra-out negate-destination yes",
    "set rulebase security rules ai-infra-out source-user any",
    "set rulebase security rules ai-infra-out category any",
    "set rulebase security rules ai-infra-out application [ ntp stun ping traceroute ]",
    "set rulebase security rules ai-infra-out service application-default",
    "set rulebase security rules ai-infra-out action allow",
    "set rulebase security rules ai-infra-out log-start no",
    "set rulebase security rules ai-infra-out log-end yes",
    "set rulebase security rules ai-infra-out profile-setting group Outbound",
    "set rulebase security rules ai-infra-out tag ai-zone",
    "set rulebase security rules ai-infra-out description \"NTP, STUN (overlay connectivity checks), ping, traceroute on default ports\""
   ],
   "n": 9,
   "why": "Time, overlay connectivity checks (STUN), ping and traceroute on their default ports.",
   "links": [],
   "move_line": "move rulebase security rules ai-infra-out after ai-block-evasive"
  },
  {
   "name": "ai-web-out",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "g-ai-nodes"
   ],
   "destination": [
    "g-not-internet"
   ],
   "application": [
    "any"
   ],
   "service": [
    "s-tcp-80-443"
   ],
   "action": "allow",
   "profile_group": "Outbound",
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": true,
   "description": "AI nodes to the internet on TCP 80/443 only, Iron Skillet Outbound profiles",
   "set_lines": [
    "set rulebase security rules ai-web-out from ai",
    "set rulebase security rules ai-web-out to lan",
    "set rulebase security rules ai-web-out source g-ai-nodes",
    "set rulebase security rules ai-web-out destination g-not-internet",
    "set rulebase security rules ai-web-out negate-destination yes",
    "set rulebase security rules ai-web-out source-user any",
    "set rulebase security rules ai-web-out category any",
    "set rulebase security rules ai-web-out application any",
    "set rulebase security rules ai-web-out service s-tcp-80-443",
    "set rulebase security rules ai-web-out action allow",
    "set rulebase security rules ai-web-out log-start no",
    "set rulebase security rules ai-web-out log-end yes",
    "set rulebase security rules ai-web-out profile-setting group Outbound",
    "set rulebase security rules ai-web-out tag ai-zone",
    "set rulebase security rules ai-web-out description \"AI nodes to the internet on TCP 80/443 only, Iron Skillet Outbound profiles\""
   ],
   "n": 10,
   "why": "Any App-ID, but only TCP 80/443: port-based on purpose for phase 1 (note under the table); Policy Optimizer narrows it to an application list after a logging period.",
   "links": [],
   "move_line": "move rulebase security rules ai-web-out after ai-infra-out"
  },
  {
   "name": "ai-cleanup-deny",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "any"
   ],
   "application": [
    "any"
   ],
   "service": [
    "any"
   ],
   "action": "deny",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "Cleanup: deny and log anything else leaving the AI zone",
   "set_lines": [
    "set rulebase security rules ai-cleanup-deny from ai",
    "set rulebase security rules ai-cleanup-deny to lan",
    "set rulebase security rules ai-cleanup-deny source any",
    "set rulebase security rules ai-cleanup-deny destination any",
    "set rulebase security rules ai-cleanup-deny source-user any",
    "set rulebase security rules ai-cleanup-deny category any",
    "set rulebase security rules ai-cleanup-deny application any",
    "set rulebase security rules ai-cleanup-deny service any",
    "set rulebase security rules ai-cleanup-deny action deny",
    "set rulebase security rules ai-cleanup-deny log-start no",
    "set rulebase security rules ai-cleanup-deny log-end yes",
    "set rulebase security rules ai-cleanup-deny tag ai-zone",
    "set rulebase security rules ai-cleanup-deny description \"Cleanup: deny and log anything else leaving the AI zone\""
   ],
   "n": 11,
   "why": "Explicit cleanup for everything else leaving the zone, logged.",
   "links": [],
   "move_line": "move rulebase security rules ai-cleanup-deny after ai-web-out"
  },
  {
   "name": "lan-to-ai-deny",
   "from": [
    "lan"
   ],
   "to": [
    "ai"
   ],
   "source": [
    "any"
   ],
   "destination": [
    "any"
   ],
   "application": [
    "any"
   ],
   "service": [
    "any"
   ],
   "action": "deny",
   "profile_group": null,
   "log_end": true,
   "tag": [
    "ai-zone"
   ],
   "negate_destination": false,
   "description": "Cleanup: nothing from the LAN side into the AI zone (management rides the overlay)",
   "set_lines": [
    "set rulebase security rules lan-to-ai-deny from lan",
    "set rulebase security rules lan-to-ai-deny to ai",
    "set rulebase security rules lan-to-ai-deny source any",
    "set rulebase security rules lan-to-ai-deny destination any",
    "set rulebase security rules lan-to-ai-deny source-user any",
    "set rulebase security rules lan-to-ai-deny category any",
    "set rulebase security rules lan-to-ai-deny application any",
    "set rulebase security rules lan-to-ai-deny service any",
    "set rulebase security rules lan-to-ai-deny action deny",
    "set rulebase security rules lan-to-ai-deny log-start no",
    "set rulebase security rules lan-to-ai-deny log-end yes",
    "set rulebase security rules lan-to-ai-deny tag ai-zone",
    "set rulebase security rules lan-to-ai-deny description \"Cleanup: nothing from the LAN side into the AI zone (management rides the overlay)\""
   ],
   "n": 12,
   "why": "Explicit cleanup for the other direction, logged; management rides the overlay.",
   "links": [],
   "move_line": "move rulebase security rules lan-to-ai-deny after ai-cleanup-deny"
  }
 ],
 "defaults": [
  {
   "name": "intrazone-default",
   "action": "allow",
   "profile_group": "Inbound",
   "log_end": true,
   "set_lines": [
    "set rulebase default-security-rules rules intrazone-default log-end yes"
   ],
   "note": "Iron Skillet override already on the box; only log-end is re-stated",
   "why": "Allow, logged (Iron Skillet override, profile group Inbound): DHCP and ping to the gateway."
  },
  {
   "name": "interzone-default",
   "action": "drop",
   "profile_group": null,
   "log_end": true,
   "set_lines": [
    "set rulebase default-security-rules rules interzone-default action drop",
    "set rulebase default-security-rules rules interzone-default log-end yes"
   ],
   "why": "Drop, logged: unchanged."
  }
 ],
 "nat": [
  {
   "name": "ai-snat-out",
   "from": [
    "ai"
   ],
   "to": [
    "lan"
   ],
   "source": [
    "n-ai-net"
   ],
   "destination": [
    "any"
   ],
   "service": [
    "any"
   ],
   "translation": "dynamic-ip-and-port interface-address interface ethernet1/1",
   "description": "AI zone to the LAN and the internet, dynamic IP and port to the port-1 address",
   "set_lines": [
    "set rulebase nat rules ai-snat-out from ai",
    "set rulebase nat rules ai-snat-out to lan",
    "set rulebase nat rules ai-snat-out source n-ai-net",
    "set rulebase nat rules ai-snat-out destination any",
    "set rulebase nat rules ai-snat-out service any",
    "set rulebase nat rules ai-snat-out source-translation dynamic-ip-and-port interface-address interface ethernet1/1",
    "set rulebase nat rules ai-snat-out tag ai-zone",
    "set rulebase nat rules ai-snat-out description \"AI zone to the LAN and the internet, dynamic IP and port to the port-1 address\""
   ]
  }
 ]
}