Skip to content

Ports & firewall

Krypton's public attack surface is only the two P2P ports. JSON-RPC, the Engine API, the CometBFT RPC, and metrics all stay on loopback or a VPN. This page is the canonical port table plus the baremetal (nftables) and AWS (Security Group) rules.

Port table

PortProtoServiceExposure
30303tcp + udpEL devp2p + discoveryPUBLIC (0.0.0.0/0)
26656tcpCL CometBFT p2pPUBLIC (0.0.0.0/0)
8545tcpEL JSON-RPCloopback or VPN only — RPC nodes: VPN/WireGuard; validators/seeds: 127.0.0.1
8551tcpEL engine authrpcCL-only, NEVER publicexposed to the internal network, not published
26657tcpCL CometBFT RPCloopback only (bound 127.0.0.1)
9001tcpEL metricsprivate (loopback/VPN; not in the firewall allow-list)
26660tcpCL CometBFT metricsprivate (on by default; published to loopback, scrape over the internal net)

The CL reaches the EL engine API at http://el:8551 over the internal network — 8551 is never published to the host. CL metrics (26660) are on by default — beacond's baked config forces instrumentation.prometheus = true at :26660, so no config.toml edit is needed. The compose publishes it to loopback only; scrape it privately (see Monitoring).

Rule of thumb

Only 30303/tcp+udp and 26656/tcp are open to the world. Everything else (8545, 8551, 26657, 9001, 26660) is reached via loopback or a VPN.

Baremetal — nftables

Install from-source/deploy/nftables.conf (edit ADMIN_CIDR to your SSH/bastion CIDR first):

sh
sudo cp nftables.conf /etc/nftables.conf
sudo systemctl enable --now nftables

The ruleset is default-drop input; it allows loopback, established/related, SSH from ADMIN_CIDR only, the two P2P ports, and rate-limited ICMP:

sh
define ADMIN_CIDR = 203.0.113.0/24    # REPLACE: the CIDR you SSH from / your bastion

table inet filter {
  chain input {
    type filter hook input priority 0; policy drop;

    iif "lo" accept
    ct state established,related accept
    ct state invalid drop

    ip saddr $ADMIN_CIDR tcp dport 22 accept   # SSH — admin CIDR only

    tcp dport 30303 accept            # bera-reth devp2p
    udp dport 30303 accept            # bera-reth discovery
    tcp dport 26656 accept            # CometBFT p2p

    ip protocol icmp icmp type echo-request limit rate 5/second accept
    ip6 nexthdr icmpv6 accept
    # NOT opened (intentionally): 8545, 8551, 26657, 9001 — loopback/VPN only.
  }
  chain forward { type filter hook forward priority 0; policy drop; }
  chain output  { type filter hook output  priority 0; policy accept; }
}

It intentionally does NOT open 8545, 8551, 26657, or 9001.

AWS — Security Group (mirror of the above)

DirectionPortProtoSource
Inbound30303TCP + UDP0.0.0.0/0
Inbound26656TCP0.0.0.0/0
Inbound22TCPadmin CIDR only
Inbound8545TCPVPN/WireGuard SG or peered subnet only (RPC nodes) — never 0.0.0.0/0
Outboundallallow (peer dialing, image pulls)

Never expose 8545 to the world

Do not add an 8545 rule for 0.0.0.0/0. Put RPC nodes' JSON-RPC behind a WireGuard interface (the RPC_HOST bind address) and a private SG. Metrics (9001) and CometBFT RPC (26657) likewise stay private.

Kubernetes

On Kubernetes the same exposure model is enforced by Service type, not a host firewall: the p2p Service (30303 + 26656) is public (LoadBalancer/NodePort) and the rpc Service (8545 + 26657) is ClusterIP-internal. See Kubernetes (Helm).

See also

Operator docs. Testnet chain-id 473374; mainnet 47337 (gated on external audit). Not financial advice.