nmcli Guide: Static IP with NetworkManager Connections - 夜莺博客

nmcli Guide: Static IP with NetworkManager Connections

NetworkManager is the default network stack on RHEL, Fedora, Rocky, AlmaLinux and most desktop distributions, and nmcli is its scriptable command-line front end. Editing /etc/sysconfig/network-scripts by hand is obsolete - the supported workflow is one nmcli connection modify command followed by nmcli connection up, and the profile is written to disk automatically so the change survives reboot. This guide shows how to configure a static IP, gateway, DNS and extra routes with nmcli, following the Red Hat documentation.

Why nmcli Instead of Editing Files

NetworkManager stores every profile as a keyfile under /etc/NetworkManager/system-connections/. When you use nmcli, NetworkManager owns that file: it writes it atomically, keeps it consistent with the running state, and reloads it without you having to remember anything. Three concrete advantages follow from that:

  • No syntax to get wrong. A typo in an ifcfg file is silently ignored at boot; a typo in an nmcli property name is rejected immediately with an error message.
  • Changes apply live. nmcli connection up activates the modified profile now — no reboot, no systemctl restart network, no dropped management session if you are working over SSH and are careful about ordering.
  • Consistent across distributions. The same commands work on RHEL 8/9, Fedora, Rocky, Alma, and NetworkManager-based desktops, while the old ifcfg format is deprecated and in some releases a compatibility shim rather than the real configuration.

The one case where you genuinely need to touch files is when you have already edited them by hand — in which case nmcli connection reload picks up the change, as covered below.

Step 1: Find the Existing Connection Profile

nmcli connection show

NetworkManager creates one profile per NIC (for example Wired connection 1 on enp1s0) that uses DHCP by default. You can modify that profile, but it is cleaner to create a dedicated one:

nmcli connection add con-name Internal-LAN ifname enp1s0 type ethernet

A few neighbouring commands are worth knowing while you are mapping the system out:

# list devices, their state and the profile attached to each
nmcli device status

# show every property of one profile
nmcli connection show "Wired connection 1"

# show only the addressing-related properties
nmcli connection show Internal-LAN | grep -E "ipv4|ipv6"

# confirm the interface name is what you think it is
ip -br link show

The device status output is the quickest way to spot a device that exists but is disconnected or unmanaged — the latter usually means an ifcfg file or an /etc/NetworkManager/conf.d/ rule has excluded it, and no amount of connection modify will bring it up.

Step 2: Switch the Profile to a Static IPv4 Address

nmcli connection modify Internal-LAN \
  ipv4.method manual \
  ipv4.addresses 192.0.2.1/24 \
  ipv4.gateway 192.0.2.254 \
  ipv4.dns "192.0.2.200 8.8.8.8" \
  ipv4.dns-search example.com

ipv4.method manual is what disables DHCP; leaving it at auto while setting an address is the most common nmcli mistake. DNS servers are space-separated - quote the whole list. For IPv6 use the parallel ipv6.method manual ipv6.addresses 2001:db8::1/64 properties.

The properties you will actually use, and what each one does:

  • ipv4.method — manual for static, auto for DHCP, disabled for no IPv4 at all, shared to run a small DHCP server for other hosts on the link.
  • ipv4.addresses — one or more CIDR addresses, comma-separated if you give several in one go.
  • ipv4.gateway — the default route. Only one gateway per profile.
  • ipv4.dns — resolver list, space-separated, quoted.
  • ipv4.dns-search — the search domain placed in /etc/resolv.conf (or handed to systemd-resolved).
  • ipv4.dns-priority — lower numbers win when more than one profile provides DNS.
  • ipv4.route-metric — lower metric wins when more than one interface offers a default route. Set this on multi-homed hosts or the default route will move about unpredictably.
  • connection.autoconnect — whether the profile activates at boot; yes is the default for new profiles, but existing ones may be set to no.
  • connection.autoconnect-priority — higher number activates first when several profiles could apply to the same device.

If you are working over SSH on the very interface you are changing, make the change and then bring the connection up with a timer so you do not lock yourself out if it goes wrong:

nmcli connection modify Internal-LAN ipv4.method manual ipv4.addresses 192.0.2.1/24 ipv4.gateway 192.0.2.254 ipv4.dns "192.0.2.200"
(sleep 60; nmcli connection modify Internal-LAN ipv4.method auto) &
nmcli connection up Internal-LAN

That background job restores DHCP after a minute unless you cancel it — cheap insurance against a mistyped subnet mask on a remote server.

Step 3: Activate and Verify

nmcli connection up Internal-LAN
nmcli connection show Internal-LAN | grep ipv4
ip -4 addr show enp1s0
ip route show

Verification is the step that separates a working host from one that looks fine until it reboots:

# is the profile actually active and reading the address you set?
nmcli -f GENERAL.STATE,IP4.ADDRESS,IP4.GATEWAY,IP4.DNS connection show Internal-LAN

# what the kernel really has
ip -4 addr show enp1s0
ip route show default

# does resolution work through the servers you configured?
resolvectl status enp1s0      # systemd-resolved
cat /etc/resolv.conf

# end-to-end reachability, both by IP and by name
ping -c3 192.0.2.254
ping -c3 example.com

A useful test for whether the configuration is persistent rather than merely live is to bounce the connection and confirm it comes back with the same address:

nmcli connection down Internal-LAN && nmcli connection up Internal-LAN
nmcli device status

Useful Variations

# add an extra IP address to the profile
nmcli connection modify Internal-LAN +ipv4.addresses 192.0.2.101/24

# add a static route
nmcli connection modify Internal-LAN +ipv4.routes "10.0.0.0/8 192.0.2.254"

# switch back to DHCP
nmcli connection modify Internal-LAN ipv4.method auto ipv4.addresses "" ipv4.gateway ""

# make sure it comes up at boot
nmcli connection modify Internal-LAN connection.autoconnect yes

# reload profiles after manual file edits
nmcli connection reload

If you edit files in /etc/NetworkManager/system-connections/ directly, run nmcli connection reload afterwards. For temporary, non-persistent changes use nmcli device modify enp1s0 ipv4.address 192.168.1.23/24.

Multiple Addresses, Aliases and Secondary IPs

The + and - prefixes are the mechanism for adding to or removing from a list property without rewriting the whole value. This matters most for addresses:

# append a second address
nmcli connection modify Internal-LAN +ipv4.addresses 192.0.2.101/24

# remove one, leaving the others untouched
nmcli connection modify Internal-LAN -ipv4.addresses 192.0.2.101/24

# replace the entire list instead
nmcli connection modify Internal-LAN ipv4.addresses "192.0.2.1/24,192.0.2.101/24"

nmcli connection up Internal-LAN
ip -4 addr show enp1s0

Note that a secondary address added this way is a first-class address on the interface, not an old-style eth0:1 alias. It appears in ip addr, it can be used for source-address selection, and it survives reboot with the profile. If you need the alias behaviour for an application that expects it, that is a separate interface configuration rather than a property of this profile.

Static Routes with nmcli

Routes belong to the profile that provides the interface, which is why they live in ipv4.routes rather than in a separate global file:

# network route via a next hop
nmcli connection modify Internal-LAN +ipv4.routes "10.0.0.0/8 192.0.2.254"

# route forced out of a specific interface instead of a next hop
nmcli connection modify Internal-LAN +ipv4.routes "10.5.0.0/16 192.0.2.254,5"

# full property form, which allows metric and table
nmcli connection modify Internal-LAN +ipv4.routes "10.9.0.0/16 192.0.2.254 50"

# routes with a custom routing table (policy routing)
nmcli connection modify Internal-LAN +ipv4.routes "0.0.0.0/0 192.0.2.253 table=100"
nmcli connection modify Internal-LAN +ipv4.routing-rules "priority 100 from 192.0.2.1 table 100"

nmcli connection up Internal-LAN
ip route show
ip rule show

For anything more involved than a handful of destination routes, keep the list readable by storing each route in its own list entry as shown. Verify with ip route show table all — a route added to a non-default table will not appear in a plain ip route show and it is easy to conclude the change did nothing when in fact it landed somewhere else.

DNS: Servers, Search Domains and Priorities

nmcli connection modify Internal-LAN ipv4.dns "192.0.2.200 192.0.2.201"
nmcli connection modify Internal-LAN ipv4.dns-search "example.com,lab.example.com"
nmcli connection modify Internal-LAN ipv4.dns-priority -50
nmcli connection modify Internal-LAN ipv4.ignore-auto-dns yes

On modern distributions DNS is usually handed to systemd-resolved, so /etc/resolv.conf is a stub and reading it proves very little. Use resolvectl status to see which interface contributed which servers, and if a VPN or second interface is quietly winning the DNS race, adjust ipv4.dns-priority — the lower (more negative) value takes precedence. ipv4.ignore-auto-dns yes is what stops a DHCP server from pushing its own resolvers back in on top of your static ones, which is a common source of "I set static DNS and it keeps reverting".

Switching Back to DHCP, and Handling IPv6

# clean return to DHCP
nmcli connection modify Internal-LAN ipv4.method auto
nmcli connection modify Internal-LAN ipv4.addresses "" ipv4.gateway "" ipv4.dns ""
nmcli connection modify Internal-LAN ipv4.ignore-auto-dns no
nmcli connection up Internal-LAN

# IPv6 equivalents
nmcli connection modify Internal-LAN ipv6.method manual ipv6.addresses 2001:db8::1/64 ipv6.gateway 2001:db8::ff
nmcli connection modify Internal-LAN ipv6.method disabled      # no IPv6 at all

Setting ipv4.method auto without clearing the static addresses is a subtle trap: on some versions NetworkManager keeps the manual address and accepts the DHCP lease, leaving the interface with two addresses and an unpredictable default route. Clear the addresses and gateway explicitly, as above.

Common nmcli Mistakes

Modifying the profile but not activating it. connection modify writes the configuration; connection up applies it. On a profile that is already active, many properties take effect only after the second command.

Forgetting ipv4.method manual. The address is set, DHCP is still enabled, and the interface ends up with a lease-assigned address as well. Symptoms look like an intermittent addressing problem.

Two profiles claiming one interface. Both Wired connection 1 and a hand-made profile can exist for the same device. Whichever has the higher autoconnect priority wins, and the other appears as an inactive duplicate. Delete the one you do not want rather than leaving both:

nmcli connection delete "Wired connection 1"

Hand edits that NetworkManager never sees. Changing a keyfile without nmcli connection reload leaves the running state and the file out of sync, and the next connection up may overwrite your edit.

Wrong interface name after a kernel upgrade. Predictable interface names can change when hardware or BIOS settings change; if a profile stops activating, check nmcli device status for the new name and update connection.interface-name accordingly.

Quick Reference

nmcli connection show                      # list profiles
nmcli device status                        # list devices and state
nmcli connection add con-name LAN ifname enp1s0 type ethernet
nmcli connection modify LAN ipv4.method manual ipv4.addresses 192.0.2.1/24
nmcli connection up LAN                    # apply
nmcli connection down LAN                  # deactivate
nmcli connection reload                    # re-read files from disk
nmcli connection delete LAN                # remove entirely
nmcli device modify enp1s0 ipv4.address 192.0.2.5/24   # temporary only

Related Guides on This Site

Compare with the file-based alternative in systemd-networkd configuration, bond the uplinks first with Linux bonding and LACP, then verify neighbors via ip neigh ARP table management. When static addressing is in place and name resolution misbehaves, work through systemd-resolved and resolvectl DNS troubleshooting; for multiple routing tables in depth, see Linux policy routing with ip rule.

原文链接:https://docs.redhat.com/en/documentation/red_hat_enterprise_linux/9/html/configuring_and_managing_networking/configuring-an-ethernet-connection_configuring-and-managing-networking