Linux stat
命令
stat
是 Linux 系统中一个功能强大的命令行工具,用于显示文件或文件系统的详细信息。它能够提供文件的元数据,如文件大小、权限、时间戳等,是系统管理员、开发者和高级用户的必备工具。
目录
什么是 stat
命令
stat
命令是 GNU coreutils 软件包的一部分,通常预装在大多数 Linux 发行版中。它用于检索并显示存储在文件 inode 中的元数据,例如文件的所有者、权限、时间戳和文件类型。与 ls
等命令提供文件属性的摘要信息不同,stat
提供更细粒度的信息,非常适合脚本编写、调试和系统分析。
为什么使用 stat
?
- 详细的元数据:访问 inode 级别的详细信息,包括访问、修改和元数据更改时间。
- 可定制输出:支持格式化输出,提取特定字段,便于脚本处理。
- 文件系统信息:显示文件系统类型和设备信息。
- 多功能性:适用于文件、目录、符号链接等多种文件类型。
可用性
stat
命令在 Linux、macOS(实现略有不同)和其他类 Unix 系统中均可用。本文主要聚焦于 Linux 系统上常见的 GNU 版本 stat
。
语法与基本用法
stat
命令的基本语法如下:
stat [选项]... 文件...
- 选项:用于修改命令行为或输出的标志。
- 文件:一个或多个需要检查的文件或目录。
基本示例
假设有一个名为 example.txt
的文件,运行以下命令:
stat example.txt
输出示例:
文件:example.txt
大小:1024 块:8 IO 块:4096 普通文件
设备:803h/2051d Inode:123456 链接:1
权限:(0644/-rw-r--r--) Uid:( 1000/ user) Gid:( 1000/ user)
访问时间:2025-04-28 10:15:30.123456789 +0800
修改时间:2025-04-27 15:20:45.987654321 +0800
元数据更改:2025-04-27 15:20:45.987654321 +0800
创建时间:2025-04-27 15:20:45.987654321 +0800
输出内容解析:
- 文件:文件名。
- 大小:文件大小(字节)。
- 块:分配的磁盘块数量。
- IO 块:文件系统块大小。
- 设备:设备编号(十六进制和十进制)。
- Inode:Inode 编号。
- 链接:硬链接数量。
- 权限:文件权限(八进制和符号表示)。
- Uid/Gid:用户和组 ID(包含用户名和组名)。
- 访问/修改/元数据更改/创建时间:最后访问、修改、元数据更改和文件创建的时间戳(如果文件系统支持)。
- 时区:时间戳的时区偏移。
主要选项与标志
stat
命令支持多种选项,用于控制其行为和输出。以下是主要选项的详细说明:
通用选项
-f
,--file-system
:显示文件系统信息,而非文件元数据。-L
,--dereference
:跟随符号链接,显示目标文件的元数据。-c
,--format=FORMAT
:指定自定义输出格式(详见自定义输出格式)。--printf=FORMAT
:与--format
类似,但支持解析反斜杠转义字符(如\n
表示换行)。-t
,--terse
:输出简洁的单行格式,适合脚本使用。
输出控制
--cached=MODE
:控制文件属性缓存方式(Linux 特有)。可选值:always
、never
、default
。-Z
:显示 SELinux 安全上下文(需启用 SELinux)。
帮助与版本
-h
,--help
:显示帮助信息。-V
,--version
:显示命令版本。
选项示例
-
查看文件系统信息:
stat -f /home
输出:
文件:"/home" ID:803h 名称长度:255 类型:ext4 块大小:4096 基本块大小:4096 块:总计:5242880 空闲:1234567 可用:987654 Inodes:总计:1310720 空闲:987654
-
简洁输出:
stat -t example.txt
输出:
example.txt 1024 8 81a4 1000 1000 803 123456 1 0 0 1619777730 1619695245 1619695245 1619695245
自定义输出格式
stat
命令的 --format
和 --printf
选项允许用户自定义输出内容,提取特定字段。这种功能在脚本中尤其有用。以下是常用的格式化占位符:
常用格式占位符
%a
:八进制权限(例如0644
)。%A
:符号权限(例如-rw-r--r--
)。%s
:文件大小(字节)。%u
:用户 ID。%U
:用户名。%g
:组 ID。%G
:组名。%y
:修改时间(人类可读格式)。%Y
:修改时间(Unix 时间戳)。%n
:文件名。%F
:文件类型(例如regular file
、directory
)。
示例
-
仅输出文件名和大小:
stat --format="%n %s" example.txt
输出:
example.txt 1024
-
格式化时间戳:
stat --format="File: %n, Modified: %y" example.txt
输出:
File: example.txt, Modified: 2025-04-27 15:20:45.987654321 +0800
-
使用
--printf
添加换行:stat --printf="Name: %n\nSize: %s bytes\n" example.txt
输出:
Name: example.txt Size: 1024 bytes
实用示例
以下是一些常见的 stat
使用场景,涵盖从基础到复杂的任务。
示例 1:检查文件权限
stat --format="Permissions: %A (%a)" example.txt
输出:
Permissions: -rw-r--r-- (0644)
示例 2:批量检查多个文件
stat --format="%n: %s bytes" *.txt
输出:
file1.txt: 1024 bytes
file2.txt: 2048 bytes
示例 3:检查符号链接
对于符号链接,默认情况下 stat
显示链接本身的元数据:
stat link_to_example.txt
使用 -L
跟随链接:
stat -L link_to_example.txt
示例 4:监控文件时间戳
检查文件的访问和修改时间:
stat --format="Access: %x\nModify: %y" example.txt
输出:
Access: 2025-04-28 10:15:30.123456789 +0800
Modify: 2025-04-27 15:20:45.987654321 +0800
示例 5:文件系统容量检查
查看挂载点 /
的文件系统信息:
stat -f /
输出:
文件:"/"
ID:802h 名称长度:255 类型:ext4
块大小:4096 基本块大小:4096
块:总计:10485760 空闲:5432109 可用:5123456
Inodes:总计:2621440 空闲:1987654
高级用法
stat
命令在高级场景中表现出色,尤其是在脚本自动化、系统监控和调试中。以下是一些高级用例。
高级示例 1:脚本中提取特定字段
在 Bash 脚本中,提取文件的修改时间并进行比较:
#!/bin/bash
file="example.txt"
mod_time=$(stat --format="%Y" "$file")
current_time=$(date +%s)
if [ $((current_time - mod_time)) -gt 86400 ]; then
echo "$file was modified more than 24 hours ago."
else
echo "$file was modified recently."
fi
高级示例 2:监控文件更改
使用 stat
检查文件是否被修改(通过比较 Inode 或修改时间):
#!/bin/bash
file="example.txt"
last_inode=$(stat --format="%i" "$file")
last_mtime=$(stat --format="%Y" "$file")
while true; do
current_inode=$(stat --format="%i" "$file")
current_mtime=$(stat --format="%Y" "$file")
if [ "$current_inode" != "$last_inode" ] || [ "$current_mtime" != "$last_mtime" ]; then
echo "$file has changed!"
last_inode="$current_inode"
last_mtime="$current_mtime"
fi
sleep 5
done
高级示例 3:批量处理文件
查找所有 .log
文件并提取大小和修改时间:
find /var/log -type f -name "*.log" -exec stat --format="%n %s %y" {} \;
输出:
/var/log/syslog 524288 2025-04-28 09:00:00.000000000 +0800
/var/log/auth.log 1048576 2025-04-28 08:45:00.000000000 +0800
高级示例 4:SELinux 上下文
在启用了 SELinux 的系统上,查看文件的 SELinux 上下文:
stat -Z example.txt
输出:
文件:example.txt
大小:1024 块:8 IO 块:4096 普通文件
设备:803h/2051d Inode:123456 链接:1
权限:(0644/-rw-r--r--) Uid:( 1000/ user) Gid:( 1000/ user)
上下文:unconfined_u:object_r:user_home_t:s0
访问时间:2025-04-28 10:15:30.123456789 +0800
修改时间:2025-04-27 15:20:45.987654321 +0800
元数据更改:2025-04-27 15:20:45.987654321 +0800
创建时间:2025-04-27 15:20:45.987654321 +0800
与其他命令的对比
stat
命令与其他工具(如 ls
、find
和 getfacl
)在功能上有重叠,但也有独特优势。
对比 ls
-
ls
:提供文件列表和基本属性(如权限、大小、修改时间),适合快速查看。 -
stat
:提供更详细的元数据(如 Inode、设备号、创建时间),支持自定义输出,适合脚本和深入分析。 -
示例:
ls -l example.txt stat example.txt
ls
输出简洁,stat
提供更多字段。
对比 find
-
find
:用于搜索文件并执行操作,支持基于时间、权限等条件的过滤。 -
stat
:专注于单个文件的详细元数据查看。 -
示例:
find . -name "*.txt" -exec stat --format="%n %s" {} \;
结合两者可实现复杂任务。
对比 getfacl
-
getfacl
:显示文件的访问控制列表(ACL)。 -
stat
:显示基本权限和 SELinux 上下文,但不深入支持 ACL。 -
示例:
getfacl example.txt stat -Z example.txt
常见问题与故障排查
问题 1:stat
输出缺少创建时间
原因:某些文件系统(如 ext3)不支持创建时间(Birth
字段)。
解决方法:检查文件系统类型(stat -f
),或使用支持创建时间的文件系统(如 ext4、XFS)。
问题 2:符号链接未正确解析
原因:默认情况下,stat
显示符号链接本身的元数据。
解决方法:使用 -L
选项跟随链接:
stat -L link_to_example.txt
问题 3:格式化输出错误
原因:格式化字符串中使用了无效占位符。
解决方法:检查 man stat
中的格式化占位符列表,确保正确使用。
问题 4:权限不足
原因:用户无权访问目标文件或目录。
解决方法:以 sudo
或适当权限运行命令:
sudo stat /root/secret.txt
总结
stat
命令是 Linux 系统中一个功能强大且灵活的工具,能够提供文件的详细元数据和文件系统信息。通过其丰富的选项和自定义输出功能,stat
在文件管理、脚本编写和系统调试中发挥了重要作用。本文从基本用法到高级场景,结合大量示例,全面介绍了 stat
的功能和应用。