Soluzione 1:
Sceglierei un approccio coerente in tutto l'ambiente. Entrambe le soluzioni funzionano correttamente e rimarranno compatibili con la maggior parte delle applicazioni. C'è una differenza nella gestibilità, però.
Vado con il nome breve come impostazione HOSTNAME e imposto FQDN come prima colonna in /etc/hosts
per l'IP del server, seguito dal nome breve.
Non ho incontrato molti pacchetti software che impongono o visualizzano una preferenza tra i due. Trovo che il nome breve sia più pulito per alcune applicazioni, in particolare la registrazione. Forse sono stato sfortunato nel vedere domini interni come server.northside.chicago.rizzomanufacturing.com
. Chi vuole vederlo nei log o in un prompt della shell ?
A volte, sono coinvolto in acquisizioni o ristrutturazioni aziendali in cui cambiano i domini interni e/oi sottodomini. Mi piace usare il nome host breve in questi casi perché registrazione, kickstart, stampa, monitoraggio dei sistemi, ecc. non richiedono una riconfigurazione completa per tenere conto dei nuovi nomi di dominio.
Una tipica configurazione del server RHEL/CentOS per un server denominato "rizzo" con dominio interno "ifp.com", sarebbe simile a:
/etc/sysconfig/network:
HOSTNAME=rizzo
...
-
/etc/hosts:
127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4
::1 localhost localhost.localdomain localhost6 localhost6.localdomain6
172.16.100.13 rizzo.ifp.com rizzo
-
[[email protected] ~]# hostname
rizzo
-
/var/log/messages snippet:
Dec 15 10:10:13 rizzo proftpd[19675]: 172.16.100.13 (::ffff:206.15.236.182[::ffff:206.15.236.182]) - Preparing to
chroot to directory '/app/upload/GREEK'
Dec 15 10:10:51 rizzo proftpd[20660]: 172.16.100.13 (::ffff:12.28.170.2[::ffff:12.28.170.2]) - FTP session opened.
Dec 15 10:10:51 rizzo proftpd[20660]: 172.16.100.13 (::ffff:12.28.170.2[::ffff:12.28.170.2]) - Preparing to chroot
to directory '/app/upload/ftp/SRRID'
Soluzione 2:
Praticamente tutto il software è sensibile all'impostazione corretta del nome host. Mentre lavoravo a Digg, una volta ho bloccato l'intero sito per 2 ore a causa di una modifica apparentemente innocente in /etc/hosts
che ha influenzato la nozione di nome host del sistema. Vacci piano. Detto questo, potresti essere leggermente confuso qui. Non credo che il HOSTNAME=
è direttamente equivalente a come le distribuzioni basate su Debian usano /etc/hostname
.
Ciò che funziona per me in un ambiente eterogeneo è:
- Imposta il nome host nel modo consigliato dal fornitore, utilizzando un condizionale nel tuo software di gestione della configurazione.
- Usa il
hostname
comando per impostare il nome host utilizzato dal kernel, ecc. -
Nel
/etc/hosts
:127.0.0.1 localhost 10.0.0.1 hostname.example.com hostname
Questa configurazione non mi ha ancora deluso.
Soluzione 3:
Sicuramente non avrai problemi a trovare riferimenti online che ti diranno di farlo sicuramente in un modo o nell'altro. Mi sembra tuttavia che avere un nome breve come nome host e avere il nome completo in /etc/hosts sia sicuramente molto più diffuso. Sembra il modo più sensato, in quanto i servizi che richiedono un nome completo possono essere adattati per chiamare hostname --fqdn
invece.
Di recente mi sono imbattuto in un solo software che richiede rigidamente che un fqdn venga restituito da hostname
, che era ganeti. Lo documentano qui. Non vedo alcun motivo per cui non possano adattarsi a hostname --fqdn
, tuttavia.
Soluzione 4:
In qualche modo tangenzialmente, durante la ricerca di questa domanda, sono diventato abbastanza pazzo da controllare il codice sorgente di "hostname" e scrivere uno script per stampare i risultati investigativi (Fedora 19). Ciò che manca è uno sguardo a "/etc/hosts", che a mio modesto parere dovrebbe essere tenuto fuori da tutto questo in primo luogo.
#!/bin/bash
function pad {
if [[ $1 == '?' ]]; then
printf "%-23s" "?"
else
printf "%-23s" "'$1'"
fi
}
# ----- Kernel -----
# Two ways to configure the kernel values:
# 1) Put FQDN into "kernel.hostname" and nothing into "kernel.domainname"
# 2) Put machine name into "kernel.hostname" and DNS domain name into "kernel.domainname" (makes more sense)
echo "== Kernel values =="
echo
H=`/sbin/sysctl -n kernel.hostname`
D=`/sbin/sysctl -n kernel.domainname`
echo "Kernel hostname: '$H'"
echo "Kernel domainname: '$D'"
# ----- What does bash say -----
echo
echo "== According to bash =="
echo
echo "HOSTNAME = '$HOSTNAME'"
# ----- Hostname config file ------
echo
echo "== Hostname config file =="
echo
ETCH="/etc/hostname"
if [[ -f $ETCH ]]; then
CONTENTS=`cat $ETCH`
echo "File '$ETCH' contains: '$CONTENTS'"
else
echo "File '$ETCH' does not exist"
fi
# ----- Network config file ------
echo
echo "== Network config file =="
echo
SYSN="/etc/sysconfig/network"
if [[ -f $SYSN ]]; then
LINE=`grep -e "^HOSTNAME=" $SYSN`
if [[ -n $LINE ]]; then
echo "File '$SYSN' contains: '$LINE'"
else
echo "File '$SYSN' exists but does not contain a line for 'HOSTNAME'"
fi
else
echo "File '$SYSN' does not exist"
fi
# ----- Nodename -------
echo
echo "== Nodename =="
echo
UNAME=`uname --nodename` # On Linux, this is the hostname
echo "The 'nodename' given by 'uname --nodename' is: '$UNAME'"
# ----- The 'hostname' mess ------
THE_HOSTNAME=`hostname`
SHORT_NAME=`hostname --short`
NIS_DNAME=`domainname`
YP_DNAME=`hostname --yp` # Same as `nisdomainname` ; this may fail with "hostname: Local domain name not set"
if [[ $? != 0 ]]; then
YP_DNAME="?"
fi
echo
echo "== 'hostname' directly obtained values =="
echo
echo "The result of gethostname();"
echo "...obtained by running 'hostname'"
echo "Hostname: $(pad $THE_HOSTNAME)"
echo
echo "The part before the first '.' of the value returned by gethostname();"
echo "...obtained by running 'hostname --short'"
echo "Short name: $(pad $SHORT_NAME)"
echo
echo "The result of getdomainname(); the code of 'hostname' seems to call this the 'NIS domain name';"
echo "...on Linux, this is the kernel-configured domainname;"
echo "...obtained by running 'domainname'"
echo "NIS domain name: $(pad $NIS_DNAME)"
echo
echo "The result of yp_get_default_domain(), which may fail;"
echo "...obtained by running 'ĥostname --yp'"
echo "YP default domain: $(pad $YP_DNAME)"
DNS_DNAME=`hostname --domain` # Same as `dnsdomainname`'
FQDN_NAME=`hostname --fqdn`
ALIAS_NAME=`hostname --alias`
echo
echo "== 'hostname' values obtained via DNS =="
echo
echo "The part after the first '.' of the 'canonical name' value returned by getaddrinfo(gethostname());"
echo "...obtained by running 'hostname --domain'"
echo "DNS domain name: $(pad $DNS_DNAME)"
echo
echo "The 'canonical name' value returned by getaddrinfo(gethostname());"
echo "...obtained by running 'hostname --fqdn'"
echo "Fully qualified hostname: $(pad $FQDN_NAME)"
echo
echo "Alias obtained by gethostbyname(gethostname());"
echo "...obtained by running 'hostname --alias'"
echo "Hostname alias: $(pad $ALIAS_NAME)"
BY_IP_ADDR=`hostname --ip-address`
ALL_IP_ADDR=`hostname --all-ip-addresses`
ALL_FQDN_NAMES=`hostname --all-fqdn`
echo
echo "== 'hostname' values obtained by collecting configured network addresses =="
echo
echo "Collect the IP addresses from getaddrinfo(gethostname()), apply getnameinfo(ip) to all those addresses;"
echo "...obtained by running 'hostname --ip-address'"
echo "By IP address: $BY_IP_ADDR"
echo
echo "Call getnameinfo(NI_NUMERICHOST) on all addresses snarfed from active interfaces;"
echo "...obtained by running 'hostname --all-ip-addresses'"
echo "All IP addresses: $ALL_IP_ADDR"
echo
echo "Call getnameinfo(NI_NAMEREQD) on all addresses snarfed from active interfaces (involves lookup in /etc/hosts);"
echo "...obtained by running 'hostname --all-fqdn'"
echo "All fully qualified hostnames: $ALL_FQDN_NAMES"
L'output su una VM Amazon EC2 che esegue Fedora 19 , dopo aver impostato manualmente i valori del kernel e riempito /etc/hostname
, ma senza modifiche a /etc/hosts
potrebbe quindi essere così:
== Kernel values ==
Kernel hostname: 'kyubee'
Kernel domainname: 'homelinux.org'
== According to bash ==
HOSTNAME = 'ip-172-31-24-249.localdomain'
== Hostname config file ==
File '/etc/hostname' contains: 'kyubee.homelinux.org'
== Network config file ==
File '/etc/sysconfig/network' exists but does not contain a line for 'HOSTNAME'
== Nodename ==
The 'nodename' given by 'uname --nodename' is: 'kyubee'
== 'hostname' directly obtained values ==
The result of gethostname();
...obtained by running 'hostname'
Hostname: 'kyubee'
The part before the first '.' of the value returned by gethostname();
...obtained by running 'hostname --short'
Short name: 'kyubee'
The result of getdomainname(); the code of 'hostname' seems to call this the 'NIS domain name';
...on Linux, this is the kernel-configured domainname;
...obtained by running 'domainname'
NIS domain name: 'homelinux.org'
The result of yp_get_default_domain(), which may fail;
...obtained by running 'ĥostname --yp'
YP default domain: 'homelinux.org'
== 'hostname' values obtained via DNS ==
The part after the first '.' of the 'canonical name' value returned by getaddrinfo(gethostname());
...obtained by running 'hostname --domain'
DNS domain name: ''
The 'canonical name' value returned by getaddrinfo(gethostname());
...obtained by running 'hostname --fqdn'
Fully qualified hostname: 'kyubee'
Alias obtained by gethostbyname(gethostname());
...obtained by running 'hostname --alias'
Hostname alias: ''
== 'hostname' values obtained by collecting configured network addresses ==
Collect the IP addresses from getaddrinfo(gethostname()), apply getnameinfo(ip) to all those addresses;
...obtained by running 'hostname --ip-address'
By IP address: fe80::8f6:8eff:fe49:9e21%eth0 172.31.24.249
Call getnameinfo(NI_NUMERICHOST) on all addresses snarfed from active interfaces;
...obtained by running 'hostname --all-ip-addresses'
All IP addresses: 172.31.24.249
Call getnameinfo(NI_NAMEREQD) on all addresses snarfed from active interfaces (involves lookup in /etc/hosts);
...obtained by running 'hostname --all-fqdn'
All fully qualified hostnames: ip-172-31-24-249.eu-west-1.compute.internal
Il modo resiliente per ottenere il nome host completo in perl sarebbe quindi:
sub getHostname {
my $hostname_short = `/bin/hostname --short`;
if ($? != 0) { print STDERR "Could not execute 'hostname --short' -- exiting\n"; exit 1 }
chomp $hostname_short;
my $hostname_long = `/bin/hostname`;
if ($? != 0) { print STDERR "Could not execute 'hostname' -- exiting\n"; exit 1 }
chomp $hostname_long;
if ($hostname_long =~ /^${hostname_short}\..+$/) {
# "hostname_long" is a qualified version of "hostname_short"
return $hostname_long
}
else {
# both hostnames are "short" (and are equal)
die unless ($hostname_long eq $hostname_short);
my $domainname = `/bin/domainname`;
if ($? != 0) { print STDERR "Could not execute 'domainname' -- exiting\n"; exit 1 }
chomp $domainname;
if ($domainname eq "(none)") {
# Change according to taste
return "${hostname_short}.localdomain"
}
else {
return "${hostname_short}.${domainname}"
}
}
}
e in bash sarebbe:
function getHostname {
local hostname_short=`/bin/hostname --short`
if [ $? -ne 0 ]; then
echo "Could not execute 'hostname --short' -- exiting" >&2; exit 1
fi
local hostname_long=`/bin/hostname`
if [ $? -ne 0 ]; then
echo "Could not execute 'hostname' -- exiting" >&2; exit 1
fi
if [[ $hostname_long =~ ^"$hostname_short"\..+$ ]]; then
# "hostname_long" is a qualified version of "hostname_short"
echo $hostname_long
else
# both hostnames are "short" (and are equal)
if [[ $hostname_long != $hostname_short ]]; then
echo "Cannot happen: '$hostname_long' <> '$hostname_short' -- exiting" >&2; exit 1
fi
local domainname=`/bin/domainname`
if [ $? -ne 0 ]; then
echo "Could not execute 'domainname' -- exiting" >&2; exit 1
fi
if [[ domainname == '(none)' ]]; then
# Change according to taste
echo "${hostname_short}.localdomain"
else
echo "${hostname_short}.${domainname}"
fi
fi
}
Note
Nota 1:HOSTNAME è una variabile di shell fornita da bash ("Impostata automaticamente sul nome dell'host corrente.") ma non vi è alcuna indicazione sul fatto che bash arrivi a quel valore.
Nota 2:non dimenticare mai /etc/hostname in /boot/initrams-FOO.img ...