hostnamectl 命令是 systemd 系统和服务管理器的一部分,用于控制和查看系统主机名及相关设置。它提供了统一的方式来管理三种类型的主机名:静态主机名(static)、瞬态主机名(transient)和灵活主机名(pretty)。
hostnamectl 是 systemd 的一部分,通常随系统默认安装:
which hostnamectl
如果未安装,说明你的系统可能没有使用 systemd,或者 systemd 版本过旧。在大多数现代 Linux 发行版中,hostnamectl 已经默认安装。
hostnamectl --version
hostnamectl [选项] [命令]
| 选项 | 说明 |
|---|---|
-h 或 --help |
显示帮助信息 |
--version |
显示版本信息 |
--no-ask-password |
不提示输入密码 |
-H 或 --host= |
在远程主机上操作 |
-M 或 --machine= |
在本地容器上操作 |
--transient |
仅设置瞬态主机名 |
--static |
仅设置静态主机名 |
--pretty |
仅设置灵活主机名 |
--json= |
以JSON格式输出 |
-P 或 --privileged |
获取特权 |
--no-pager |
不将输出通过分页器显示 |
hostnamectl 管理三种类型的主机名:
| 主机名类型 | 存储位置 | 特点 | 用途 |
|---|---|---|---|
| 静态主机名 (Static Hostname) |
/etc/hostname |
永久存储,系统重启后保留 | 内核主机名,用于系统标识 |
| 瞬态主机名 (Transient Hostname) |
内核运行时 | 临时存储,重启后丢失 | DHCP或mDNS设置的临时主机名 |
| 灵活主机名 (Pretty Hostname) |
systemd配置 | 可包含特殊字符和空格 | 用户友好的显示名称 |
# 查看所有主机名信息
hostnamectl
# 以JSON格式查看
hostnamectl --json=pretty
# 查看特定主机名类型
hostnamectl status
输出示例:
Static hostname: ubuntu-server
Icon name: computer-server
Chassis: server
Machine ID: 1234567890abcdef1234567890abcdef
Boot ID: abcdef1234567890abcdef1234567890
Operating System: Ubuntu 20.04.3 LTS
Kernel: Linux 5.4.0-88-generic
Architecture: x86-64
# 设置静态主机名
sudo hostnamectl set-hostname myserver.example.com
# 验证设置
hostnamectl
# 查看/etc/hostname文件
cat /etc/hostname
# 设置灵活主机名(可包含空格和特殊字符)
sudo hostnamectl set-hostname "My Production Server" --pretty
# 查看灵活主机名
hostnamectl | grep "Pretty hostname"
# 只显示灵活主机名
hostnamectl --pretty
# 设置瞬态主机名
sudo hostnamectl set-hostname "temp-hostname" --transient
# 查看瞬态主机名
hostnamectl | grep "Transient hostname"
# 注意:瞬态主机名重启后会丢失
# 同时设置静态和灵活主机名
sudo hostnamectl set-hostname "server1.example.com" --static
sudo hostnamectl set-hostname "Production Server 1" --pretty
# 或者使用一条命令设置所有类型
sudo hostnamectl set-hostname "server1.example.com" \
--static \
--transient \
--pretty "Production Server 1"
# 查看远程服务器的主机名
hostnamectl -H user@remote-server
# 设置远程服务器的主机名
sudo hostnamectl -H user@remote-server set-hostname "remote.example.com"
# 使用root用户
sudo hostnamectl -H root@192.168.1.100 set-hostname "server1"
# 查看容器的主机名
hostnamectl -M mycontainer
# 设置容器的主机名
sudo hostnamectl -M mycontainer set-hostname "container1"
# 使用systemd-nspawn容器的示例
sudo systemd-nspawn -D /path/to/container /bin/hostnamectl set-hostname "container-host"
# 重置灵活主机名
sudo hostnamectl set-hostname "" --pretty
# 重置瞬态主机名
sudo hostnamectl set-hostname "" --transient
# 注意:静态主机名不能设置为空,可以设置为默认值
sudo hostnamectl set-hostname "localhost"
Static hostname: ubuntu-server # 静态主机名
Pretty hostname: Ubuntu Server # 灵活主机名(可包含空格)
Transient hostname: not set # 瞬态主机名
Icon name: computer-server # 系统图标类型
Chassis: server # 设备类型(server, vm, desktop等)
Machine ID: 1234... # 机器唯一ID
Boot ID: abcd... # 启动ID
Operating System: Ubuntu 20.04 # 操作系统
Kernel: Linux 5.4.0 # 内核版本
Architecture: x86-64 # 系统架构
| Chassis类型 | 说明 | Icon name |
|---|---|---|
desktop |
台式机 | computer-desktop |
laptop |
笔记本电脑 | computer-laptop |
server |
服务器 | computer-server |
tablet |
平板电脑 | computer-tablet |
handset |
手机/手持设备 | phone |
vm |
虚拟机 | computer-vm |
container |
容器 | computer-container |
#!/bin/bash
# 获取静态主机名
STATIC_HOSTNAME=$(hostnamectl --static)
echo "静态主机名: $STATIC_HOSTNAME"
# 获取灵活主机名
PRETTY_HOSTNAME=$(hostnamectl --pretty)
echo "灵活主机名: $PRETTY_HOSTNAME"
# 获取机器ID
MACHINE_ID=$(hostnamectl | grep "Machine ID" | awk '{print $3}')
echo "机器ID: $MACHINE_ID"
# 获取操作系统信息
OS_INFO=$(hostnamectl | grep "Operating System" | cut -d: -f2-)
echo "操作系统: $OS_INFO"
#!/bin/bash
# 批量修改服务器主机名
SERVERS=("server1.example.com" "server2.example.com" "server3.example.com")
NEW_HOSTNAME_PREFIX="prod-server"
for i in "${!SERVERS[@]}"; do
SERVER="${SERVERS[$i]}"
NEW_HOSTNAME="${NEW_HOSTNAME_PREFIX}-$((i+1))"
echo "正在修改 $SERVER 的主机名为 $NEW_HOSTNAME"
ssh "$SERVER" "sudo hostnamectl set-hostname '$NEW_HOSTNAME'"
if [ $? -eq 0 ]; then
echo "✓ $SERVER 修改成功"
else
echo "✗ $SERVER 修改失败"
fi
done
#!/bin/bash
# 检查主机名是否合法
check_hostname() {
local hostname="$1"
# 基本规则检查
if [[ -z "$hostname" ]]; then
echo "错误: 主机名不能为空"
return 1
fi
if [[ ${#hostname} -gt 64 ]]; then
echo "错误: 主机名长度不能超过64个字符"
return 1
fi
if [[ ! "$hostname" =~ ^[a-zA-Z0-9]([a-zA-Z0-9-]{0,61}[a-zA-Z0-9])?$ ]]; then
echo "错误: 主机名只能包含字母、数字和连字符,不能以连字符开头或结尾"
return 1
fi
if [[ "$hostname" =~ ^[0-9]+\.[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
echo "警告: 主机名看起来像IP地址,不建议使用"
fi
echo "主机名 '$hostname' 格式正确"
return 0
}
# 使用示例
check_hostname "my-server-01"
check_hostname "-invalid-hostname"
check_hostname "very-long-hostname-that-exceeds-the-maximum-length-of-sixty-four-characters"
#!/bin/bash
# 自动设置主机名和更新hosts文件
DOMAIN="example.com"
SHORT_HOSTNAME="server1"
# 设置静态主机名
FULL_HOSTNAME="${SHORT_HOSTNAME}.${DOMAIN}"
sudo hostnamectl set-hostname "$FULL_HOSTNAME"
# 更新/etc/hosts文件
if ! grep -q "$FULL_HOSTNAME" /etc/hosts; then
# 获取本机IP地址
IP_ADDR=$(hostname -I | awk '{print $1}')
# 备份原hosts文件
sudo cp /etc/hosts /etc/hosts.backup.$(date +%Y%m%d)
# 添加主机名映射
echo "$IP_ADDR $FULL_HOSTNAME $SHORT_HOSTNAME" | sudo tee -a /etc/hosts > /dev/null
echo "已更新/etc/hosts文件"
fi
#!/bin/bash
# 监控主机名变化的脚本
LOG_FILE="/var/log/hostname-changes.log"
CURRENT_HOSTNAME=$(hostnamectl --static)
while true; do
sleep 60 # 每分钟检查一次
NEW_HOSTNAME=$(hostnamectl --static)
if [ "$CURRENT_HOSTNAME" != "$NEW_HOSTNAME" ]; then
echo "$(date): 主机名已更改: $CURRENT_HOSTNAME -> $NEW_HOSTNAME" >> "$LOG_FILE"
CURRENT_HOSTNAME="$NEW_HOSTNAME"
# 发送通知(可选)
# wall "警告: 主机名已被修改为 $NEW_HOSTNAME"
# 或发送邮件通知管理员
fi
done
#!/bin/bash
# 生成系统信息报告
generate_system_report() {
echo "=== 系统信息报告 ==="
echo "生成时间: $(date)"
echo ""
# 主机名信息
echo "--- 主机名信息 ---"
hostnamectl | grep -E "hostname|Icon|Chassis"
echo ""
# 系统信息
echo "--- 系统信息 ---"
hostnamectl | grep -E "Operating System|Kernel|Architecture"
echo ""
# 机器标识
echo "--- 机器标识 ---"
hostnamectl | grep -E "Machine ID|Boot ID"
echo ""
# 网络信息
echo "--- 网络信息 ---"
ip addr show | grep -E "inet |ether " | head -5
}
# 生成报告
generate_system_report > /tmp/system-report.txt
| 工具 | 特点 | 适用场景 | 兼容性 |
|---|---|---|---|
| hostnamectl | systemd集成,统一管理三种主机名,无需重启 | systemd系统,现代Linux发行版 | systemd系统 |
| hostname | 传统工具,简单直接,修改运行时主机名 | 所有Linux系统,脚本兼容性要求 | 所有系统 |
| nmcli | NetworkManager集成,可设置DHCP主机名 | 使用NetworkManager的系统 | NetworkManager系统 |
| sysctl | 修改内核参数kernel.hostname | 低层级主机名设置 | 所有系统 |
| 手动修改文件 | 直接编辑/etc/hostname和/etc/hosts | 需要完全控制,恢复环境 | 所有系统 |
A: 设置静态主机名后,可能需要重启某些服务或重新登录才能看到变化。可以尝试:
exec bash 重新加载shellsudo systemctl restart systemd-hostnamedA: hostnamectl 本身不提供历史记录功能,但可以通过以下方式追踪变化:
# 使用systemd日志
sudo journalctl -u systemd-hostnamed
# 查看/var/log/syslog或/var/log/messages
grep hostname /var/log/syslog
# 创建自定义监控脚本(如前所述)
A: 可能的原因和解决方法:
sudo hostnamectl set-hostname .../etc/hostname是否可写A: 灵活主机名可以包含特殊字符和空格,但静态主机名必须符合RFC 1123标准:
# 使用合法的主机名
sudo hostnamectl set-hostname "webserver-01" # 正确
sudo hostnamectl set-hostname "web server" # 错误(静态主机名不能有空格)
A: 完全应用主机名更改可能需要:
# 1. 设置主机名
sudo hostnamectl set-hostname "new-hostname"
# 2. 更新当前shell
export HOSTNAME="new-hostname"
exec bash
# 3. 重启相关服务
sudo systemctl restart systemd-hostnamed
sudo systemctl restart NetworkManager # 如果使用NetworkManager
sudo systemctl restart sshd # 更新SSH横幅
# 4. 对于某些应用程序,可能需要重启