Is it bad practice to listen on 0.0.0.0? Why?

Solution 1:

I decide then to deploy it configuring the address 0.0.0.0 to bind to the service configured port and job done.

Will network administrators frown upon it?

It would be bad practice if it's not necessary.

For some networks it may be necessary. And you won't know. It's not your decision to make.

Give the network administrators the option on what IP to bind it on.

Added note to clarify

It's not for you to make the decision of what IP to bind onto and not give the network admin the option to change it (which is what it sounds like you're talking about). It's fine for you to offer a default.

Solution 2:

Tradeoffs between (1) good support for dynamic network configuration, (2) security and firewall rule stability and (3) code complexity (e.g. when network configuration event handling is needed) have already been mentioned. I’d like to point out a completely different issue though:

Yes, listening on address 0.0.0.0 is bad practice. Because it explicitly limits the listening daemon to IPv4 for no good reason.

Depending on where the 0.0.0.0 “museum address” occurs (hardwired in code or set in configuration), it yields either broken software or at least broken server setups, unusable on IPv6-only networks and causing connection delays and other malfunction on dual-stack networks (due to the need for IPv4 fallback).

To listen on “all available IP addresses” (when needed and when appropriate), simply listen on ::, which really covers all IP addresses, common IPv6 as well as IPv4-mapped IPv6 for legacy IPv4 support (if needed).

In most cases, system libraries make dual-stack support the easiest and default option that works out-of-the-box, unless an explicit effort is made to prevent one of the IP versions from functioning (such as listening on 0.0.0.0).

As for getaddrinfo(), AI_V4MAPPED | AI_ALL will rerurn both address types in a unified (IPv6) format and one and the same (IPv6) socket type can be used for both of them. This is especially relevant for the client side.

As for socket() and related calls, a single IPv6 socket will serve both IPv6 and IPv4 (unless IPV6_V6ONLY is set, and it is not set by default). This is especially relevant for the server side.

A known limitation of default (i.e. dual-stack) IPv6 sockets is port space sharing between IPv6 and IPv4. Separate sockets are needed to listen on different ports for IPv6 and IPv4. However, in most common cases, IPv6 sockets listening on :: behave in a predictable, backward-compatible way.