在Linux / POSIX系统上获取用户全名的最简单方法是什么?

我可以通过/ etc / passwd grep,但似乎繁重。 “手指”没有安装,我想避免这种依赖。 这是一个程序,所以如果有一些让你只访问用户信息的命令就会很好。

你不指定一种编程语言,所以我会假设你想使用shell; 这是Posix shell的答案

这两个步骤:获得适当的记录,然后从该记录获取所需的字段。

首先,通过查询passwd获取帐户记录:

 $ user_name=foo $ getent passwd $user_name foo:x:1023:1025:Fred Nurk,,,:/home/foo:/bin/bash 

对于歇斯底里的葡萄干,用户的全名被记录在称为“GECOS”字段的字段中 ; 使事情复杂化,这个领域往往有自己的结构, 全名只是几个可选的子领域之一 。 所以任何想要从账户记录中获得全名的东西都需要解析这两个级别。

 $ user_record=$(getent passwd $user_name) $ user_gecos_field=$(echo "$user_record" | cut -d ':' -f 5) $ user_full_name=$(echo "$user_gecos_field" | cut -d ',' -f 1) $ echo $user_full_name Fred Nurk 

你的编程语言可能有一个库函数来做这个更少的步骤。 在C中,你将使用“getpwnam”函数,然后解析GECOS字段。

在现代的glibc系统上,使用这个命令:

 getent passwd "username" | cut -d ':' -f 5 

这将得到指定用户的passwd项, passwd依赖于底层的NSS模块。

阅读getent的手册页 。


如果您已经编程,可以使用getpwnam() C函数:

 struct passwd *getpwnam(const char *name); 

passwd结构有一个pw_gecos成员,它应该包含用户的全名。

阅读getpwnam()的手册页 。


请注意,许多系统使用此字段的用户名不止全名。 最常见的惯例是在字段中使用逗号( , )作为分隔符,并首先放置用户真实姓名。

以防万一你想从C做到这一点,尝试这样的事情:

 #include <sys/types.h> #include <pwd.h> #include <errno.h> #include <stdio.h> #include <string.h> /* Get full name of a user, given their username. Return 0 for not found, -1 for error, or 1 for success. Copy name to `fullname`, but only up to max-1 chars (max includes trailing '\0'). Note that if the GECOS field contains commas, only up to to (but not including) the first comma is copied, since the commas are a convention to add more than just the name into the field, eg, room number, phone number, etc. */ static int getfullname(const char *username, char *fullname, size_t max) { struct passwd *p; size_t n; errno = 0; p = getpwnam(username); if (p == NULL && errno == 0) return 0; if (p == NULL) return -1; if (max == 0) return 1; n = strcspn(p->pw_gecos, ","); if (n > max - 1) n = max - 1; memcpy(fullname, p->pw_gecos, n); fullname[n] = '\0'; return 1; } int main(int argc, char **argv) { int i; int ret; char fullname[1024]; for (i = 1; i < argc; ++i) { ret = getfullname(argv[i], fullname, sizeof fullname); if (ret == -1) printf("ERROR: %s: %s\n", argv[i], strerror(errno)); else if (ret == 0) printf("UNKONWN: %s\n", argv[i]); else printf("%s: %s\n", argv[i], fullname); } return 0; } 

尝试这个:

 getent passwd eutl420 | awk -F':' '{gsub(",", "",$5); print $5}' 

其他答案的组合,在最小的Debian / Ubuntu安装上测试:

 getent passwd `whoami` | cut -d ':' -f 5 | cut -d ',' -f 1 

前两个答案可以合并成一行:

 getent passwd <username> | cut -d ':' -f 5 | cut -d ',' -f 1 

我的代码在bash和ksh中工作,但不是破折号或旧的Bourne shell。 它也读取其他领域,以防您可能需要。

 IFS=: read user x uid gid gecos hm sh < <( getent passwd $USER ) name=${gecos%%,*} echo "$name" 

您也可以扫描整个/ etc / passwd文件。 这可以在一个简单的Bourne shell中运行,但是在LDAP或者其他方面并不是那么简单。

 while IFS=: read user x uid gid gecos hm sh; do name=${gecos%%,*} [ $uid -ge 1000 -a $uid -lt 60000 ] && echo "$name" done < /etc/passwd 

另一方面,使用工具是好的。 而且C也不错。

我想到在Linux上把全名变成一个变量的方式是:

 u_id=`id -u` uname=`awk -F: -vid=$u_id '{if ($3 == id) print $5}' /etc/passwd` 

然后只需简单地使用变量,例如: $ echo $uname

以1:

 $ user_name=sshd $ awk -F: "\$1 == \"$user_name\" { print \$5 }" /etc/passwd Secure Shell Daemon 

但是,passwd数据库在gecos中支持特殊字符'&',应该用大写的用户名替换:

 $ user_name=operator $ awk -F: "\$1 == \"$user_name\" { print \$5 }" /etc/passwd System & 

这里的大多数答案(手指解决方案除外)不尊重&。 如果你想支持这种情况,那么你将需要一个更复杂的脚本。

以2:

 $ user_name=operator $ awk -F: "\$1 == \"$user_name\" { u=\$1; sub(/./, toupper(substr(u,1,1)), u); gsub(/&/, u, \$5); print \$5 }" /etc/passwd System Operator 

好老的手指也可以帮助:-)

 finger $USER |head -n1 |cut -d : -f3