1
0
mirror of https://github.com/mail-in-a-box/mailinabox.git synced 2026-03-04 15:54:48 +01:00

Support dual-stack IPv4/IPv6 mail servers

Addresses #3

Added support by adding parallel code wherever `$PUBLIC_IP` was used.
Providing an IPv6 address is completely optional.

Playing around on my IPv6-enabled mail server revealed that — before
this change — mailinabox might try to use an IPv6 address as the value
for `$PUBLIC_IP`, which wouldn't work out well.
This commit is contained in:
Michael Kropat
2014-06-08 18:32:52 -04:00
parent ca34c1b1ae
commit ae67409603
4 changed files with 58 additions and 4 deletions

View File

@@ -39,11 +39,19 @@ function get_default_publicip {
get_publicip_from_web_service || get_publicip_fallback
}
function get_default_publicipv6 {
get_publicipv6_from_web_service || get_publicipv6_fallback
}
function get_publicip_from_web_service {
# This seems to be the most reliable way to determine the
# machine's public IP address: asking a very nice web API
# for how they see us. Thanks go out to icanhazip.com.
curl --fail --silent icanhazip.com 2>/dev/null
curl -4 --fail --silent icanhazip.com 2>/dev/null
}
function get_publicipv6_from_web_service {
curl -6 --fail --silent icanhazip.com 2>/dev/null
}
function get_publicip_fallback {
@@ -53,17 +61,39 @@ function get_publicip_fallback {
# have multiple addresses if it has multiple network adapters.
set -- $(hostname --ip-address 2>/dev/null) \
$(hostname --all-ip-addresses 2>/dev/null)
while (( $# )) && is_loopback_ip "$1"; do
while (( $# )) && { ! is_ipv4 "$1" || is_loopback_ip "$1"; }; do
shift
done
printf '%s\n' "$1" # return this value
}
function get_publicipv6_fallback {
set -- $(hostname --ip-address 2>/dev/null) \
$(hostname --all-ip-addresses 2>/dev/null)
while (( $# )) && { ! is_ipv6 "$1" || is_loopback_ipv6 "$1"; }; do
shift
done
printf '%s\n' "$1" # return this value
}
function is_ipv4 {
# helper for get_publicip_fallback
[[ "$1" == *.*.*.* ]]
}
function is_ipv6 {
[[ "$1" == *:*:* ]]
}
function is_loopback_ip {
# helper for get_publicip_fallback
[[ "$1" == 127.* ]]
}
function is_loopback_ipv6 {
[[ "$1" == ::1 ]]
}
function ufw_allow {
if [ -z "$DISABLE_FIREWALL" ]; then
# ufw has completely unhelpful output

View File

@@ -54,6 +54,19 @@ if [ -z "$PUBLIC_IP" ]; then
read -e -i "$DEFAULT_PUBLIC_IP" -p "Public IP: " PUBLIC_IP
fi
if [ -z "$PUBLIC_IPV6" ]; then
echo
echo "(Optional) Enter the IPv6 address of this machine. Leave blank"
echo " if the machine does not have an IPv6 address."
if [ -z "$DEFAULT_PUBLIC_IPV6" ]; then
# set a default on first run
DEFAULT_PUBLIC_IPV6=`get_default_publicipv6`
fi
read -e -i "$DEFAULT_PUBLIC_IPV6" -p "Public IPv6: " PUBLIC_IPV6
fi
if [ -z "$CSR_COUNTRY" ]; then
echo
echo "Enter the two-letter, uppercase country code for where you"
@@ -70,12 +83,17 @@ if [ -z "$CSR_COUNTRY" ]; then
fi
# Automatic configuration, e.g. as used in our Vagrant configuration.
if [ "$PUBLIC_IP" == "auto" ]; then
if [ "$PUBLIC_IP" = "auto" ]; then
# Use a public API to get our public IP address.
PUBLIC_IP=`get_default_publicip`
echo "IP Address: $PUBLIC_IP"
fi
if [ "$PUBLIC_HOSTNAME" == "auto-easy" ]; then
if [ "$PUBLIC_IPV6" = "auto" ]; then
# Use a public API to get our public IP address.
PUBLIC_IPV6=`get_default_publicipv6`
echo "IPv6 Address: $PUBLIC_IPV6"
fi
if [ "$PUBLIC_HOSTNAME" = "auto-easy" ]; then
# Generate a probably-unique subdomain under our justtesting.email domain.
PUBLIC_HOSTNAME=m`get_default_publicip | sha1sum | cut -c1-5`.justtesting.email
echo "Public Hostname: $PUBLIC_HOSTNAME"
@@ -97,6 +115,7 @@ cat > /etc/mailinabox.conf << EOF;
STORAGE_ROOT=$STORAGE_ROOT
PUBLIC_HOSTNAME=$PUBLIC_HOSTNAME
PUBLIC_IP=$PUBLIC_IP
PUBLIC_IPV6=$PUBLIC_IPV6
CSR_COUNTRY=$CSR_COUNTRY
EOF