Linux'ta bir grubun tüm üyelerini (ve muhtemelen diğer birlikleri) nasıl listeleyebilirim?
Linux'ta bir grubun tüm üyelerini (ve muhtemelen diğer birlikleri) nasıl listeleyebilirim?
Yanıtlar:
Ne yazık ki, bunu yapmanın iyi, taşınabilir bir yolu yok. / Etc / group öğelerini ayrıştırmaya çalışırsanız, başkalarının önerdiği gibi, bu grubu birincil grubu olarak kullanan kullanıcıları ve bu gruba UNIX düz dosyaları (LDAP, NIS, pam-pgsql, vb.).
Bunu kesinlikle kendim yapmak zorunda kalsaydım, muhtemelen tersine yapardım: id
sistemdeki her kullanıcının gruplarını almak için kullanın (ki bu, NSS tarafından görülebilir tüm kaynakları çekecektir) ve Perl veya bir hash sağlamak için benzer bir şey kullanın her bir grup için o kullanıcının üyeliğine dikkat çeken bir tablo.
Düzenleme: Tabii ki, bu benzer bir sorun bırakır: sistemdeki her kullanıcının bir listesini almak için nasıl. Konumum yalnızca düz dosyalar ve LDAP kullandığından, her iki konumdan da bir liste alabilirim, ancak bu ortamınız için doğru olabilir veya olmayabilir.
Edit 2: Birisi bana getent passwd
LDAP / NIS / vb. Dahil olmak üzere sistemdeki tüm kullanıcıların bir listesini döndüreceğini hatırlattı , ancak getent group
yine de sadece varsayılan grup girişi yoluyla üye olan kullanıcıları özleyecek, böylece bana ilham verdi Bu hızlı kesmek yazın.
#!/usr/bin/perl -T
#
# Lists members of all groups, or optionally just the group
# specified on the command line
#
# Copyright © 2010-2013 by Zed Pobre (zed@debian.org or zed@resonant.org)
#
# Permission to use, copy, modify, and/or distribute this software for any
# purpose with or without fee is hereby granted, provided that the above
# copyright notice and this permission notice appear in all copies.
#
use strict; use warnings;
$ENV{"PATH"} = "/usr/bin:/bin";
my $wantedgroup = shift;
my %groupmembers;
my $usertext = `getent passwd`;
my @users = $usertext =~ /^([a-zA-Z0-9_-]+):/gm;
foreach my $userid (@users)
{
my $usergrouptext = `id -Gn $userid`;
my @grouplist = split(' ',$usergrouptext);
foreach my $group (@grouplist)
{
$groupmembers{$group}->{$userid} = 1;
}
}
if($wantedgroup)
{
print_group_members($wantedgroup);
}
else
{
foreach my $group (sort keys %groupmembers)
{
print "Group ",$group," has the following members:\n";
print_group_members($group);
print "\n";
}
}
sub print_group_members
{
my ($group) = @_;
return unless $group;
foreach my $member (sort keys %{$groupmembers{$group}})
{
print $member,"\n";
}
}
getent passwd
için çalışmayabilir (örneğin, sssd kullanıyorsanız).
getent passwd
sssd'de bir hata olduğunu düşünürdüm.
Grup üyelerini listelemek için Python kullanın:
python -c "içe aktarma grp; yazdır grp.getgrnam ('GROUP_NAME') [3]"
lid -g groupname | cut -f1 -d'('
Aşağıdaki komut, <your_group_name>
yalnızca /etc/group
LDAP, NIS vb. Değil, yalnızca veritabanıyla yönetilen kullanıcıları listeler . Ayrıca yalnızca ikincil gruplar için de çalışır , birincil grup olduğu için bu grubu birincil olarak ayarlanmış kullanıcıları listelemez GID
dosyada (sayısal grup kimliği) olarak saklanır /etc/passwd
.
grep <your_group_name> /etc/group
Aşağıdaki komut, <your_group_name>
yalnızca /etc/group
LDAP, NIS vb. Değil, yalnızca veritabanıyla yönetilen kullanıcıları listeler . Ayrıca yalnızca ikincil gruplar için de çalışır , birincil grup olduğu için bu grubu birincil olarak ayarlanmış kullanıcıları listelemez GID
dosyada (sayısal grup kimliği) olarak saklanır /etc/passwd
.
awk -F: '/^groupname/ {print $4;}' /etc/group
Aşağıdaki kabuk betiği tüm kullanıcılar arasında yinelenir ve yalnızca belirli bir gruba ait olan kullanıcı adlarını yazdırır:
#!/usr/bin/env bash
getent passwd | while IFS=: read name trash
do
groups $name 2>/dev/null | cut -f2 -d: | grep -i -q -w "$1" && echo $name
done
true
Kullanım örneği:
./script 'DOMAIN+Group Name'
Not: Bu çözüm NIS ve LDAP'yi kullanıcılar ve gruplar için kontrol eder (sadece passwd
ve group
dosyalar için değil ). Ayrıca bir gruba eklenmemiş, ancak birincil grup olarak grup ayarlanmış kullanıcıları da dikkate alacaktır.
Düzenleme: Kullanıcının aynı ada sahip gruba ait olmadığı nadir senaryo için düzeltme eklendi.
Düzenleme: kabuk betiği şeklinde yazılmış; @Max Chernyak aka hakunin tarafından önerildiği gibi true
çıkışa eklendi ; bunları atlamak için atılır .0
stderr
groups: cannot find name for group ID xxxxxx
; true
. 0 döndürmek, yapılandırma yönetim sisteminizi (Chef, Ansible, vb.) Devreye sokmamak için iyidir.
Tek bir komut satırında yapabilirsiniz:
cut -d: -f1,4 /etc/passwd | grep $(getent group <groupname> | cut -d: -f3) | cut -d: -f1
Yukarıdaki komut, grup adı olan tüm kullanıcıları birincil grupları olarak listeler
Ayrıca grup adı olan kullanıcıları ikincil grubu olarak listelemek istiyorsanız , aşağıdaki komutu kullanın
getent group <groupname> | cut -d: -f4 | tr ',' '\n'
grep
adı grup numarasını içeren bir kullanıcıyla eşleşir (ör . Grubun bir sc0tt
parçası olarak gösterilir root
). Bu bir sorunsa, normal ifadeyi kullanın :$(getent group <groupname> | cut -d: -f3)\$
(noktalı virgül, grup kimliği ve satırın sonu ile eşleşir). (Normal ifadeye alıntı eklemeyin veya bash şikayet ediyor.)
Zed'in uygulaması büyük olasılıkla diğer büyük UNIX'lerin bazıları üzerinde çalışacak şekilde genişletilmelidir.
Birisi Solaris veya HP-UX donanımına erişebilir mi ?; bu davaları test etmedi.
#!/usr/bin/perl
#
# Lists members of all groups, or optionally just the group
# specified on the command line
#
# Date: 12/30/2013
# Author: William H. McCloskey, Jr.
# Changes: Added logic to detect host type & tailor subset of getent (OSX)
# Attribution:
# The logic for this script was directly lifted from Zed Pobre's work.
# See below for Copyright notice.
# The idea to use dscl to emulate a subset of the now defunct getent on OSX
# came from
# http://zzamboni.org/\
# brt/2008/01/21/how-to-emulate-unix-getent-with-macosxs-dscl/
# with an example implementation lifted from
# https://github.com/petere/getent-osx/blob/master/getent
#
# Copyright © 2010-2013 by Zed Pobre (zed@debian.org or zed@resonant.org)
#
# Permission to use, copy, modify, and/or distribute this software for any
# purpose with or without fee is hereby granted, provided that the above
# copyright notice and this permission notice appear in all copies.
#
use strict; use warnings;
$ENV{"PATH"} = "/usr/bin:/bin";
# Only run on supported $os:
my $os;
($os)=(`uname -a` =~ /^([\w-]+)/);
unless ($os =~ /(HU-UX|SunOS|Linux|Darwin)/)
{die "\$getent or equiv. does not exist: Cannot run on $os\n";}
my $wantedgroup = shift;
my %groupmembers;
my @users;
# Acquire the list of @users based on what is available on this OS:
if ($os =~ /(SunOS|Linux|HP-UX)/) {
#HP-UX & Solaris assumed to be like Linux; they have not been tested.
my $usertext = `getent passwd`;
@users = $usertext =~ /^([a-zA-Z0-9_-]+):/gm;
};
if ($os =~ /Darwin/) {
@users = `dscl . -ls /Users`;
chop @users;
}
# Now just do what Zed did - thanks Zed.
foreach my $userid (@users)
{
my $usergrouptext = `id -Gn $userid`;
my @grouplist = split(' ',$usergrouptext);
foreach my $group (@grouplist)
{
$groupmembers{$group}->{$userid} = 1;
}
}
if($wantedgroup)
{
print_group_members($wantedgroup);
}
else
{
foreach my $group (sort keys %groupmembers)
{
print "Group ",$group," has the following members:\n";
print_group_members($group);
print "\n";
}
}
sub print_group_members
{
my ($group) = @_;
return unless $group;
foreach my $member (sort keys %{$groupmembers{$group}})
{
print $member,"\n";
}
}
Bu öneriyi paylaşmanın daha iyi bir yolu varsa, lütfen bana bildirin; Ben birçok yolu düşündüm ve ben de bunu buldum.
id -Gn
için/usr/xpg4/bin/id -G -n
Bunu yukarıdaki perl koduna benzer yaptım, ancak yerel perl işlevleriyle getent ve id yerine geçtim. Çok daha hızlıdır ve farklı * nix aromaları üzerinde çalışmalıdır.
#!/usr/bin/env perl
use strict;
my $arg=shift;
my %groupMembers; # defining outside of function so that hash is only built once for multiple function calls
sub expandGroupMembers{
my $groupQuery=shift;
unless (%groupMembers){
while (my($name,$pass,$uid,$gid,$quota,$comment,$gcos,$dir,$shell,$expire)=getpwent()) {
my $primaryGroup=getgrgid($gid);
$groupMembers{$primaryGroup}->{$name}=1;
}
while (my($gname,$gpasswd,$gid,$members)=getgrent()) {
foreach my $member (split / /, $members){
$groupMembers{$gname}->{$member}=1;
}
}
}
my $membersConcat=join(",",sort keys %{$groupMembers{$groupQuery}});
return "$membersConcat" || "$groupQuery Does have any members";
}
print &expandGroupMembers($arg)."\n";
Bu işlevselliği sağlayan ' üye ' adında kullanışlı bir Debian ve Ubuntu paketi var :
Açıklama: Bir grubun üyelerini gösterir; varsayılan olarak, tüm üye üyeler grupların tamamlayıcısıdır: gruplar belirtilen bir kullanıcının ait olduğu grupları gösterirken, üyeler belirli bir gruba ait olan kullanıcıları gösterir.
... Birincil üyeler, ikincil üyeler, her ikisinde de ayrı satırlarda isteyebilirsiniz.
getent group insert_group_name_here | awk -F ':' '{print $4}' | sed 's|,| |g'
Bu, dizileri doldurmak için komut dosyalarında kullandığım boşlukla ayrılmış kullanıcıların bir listesini döndürür.
for i in $(getent group ftp | awk -F ':' '{print $4}' | sed 's|,| |g')
do
userarray+=("$i")
done
veya
userarray+=("$(getent group GROUPNAME | awk -F ':' '{print $4}' | sed 's|,| |g')")
Burada, / etc / passwd ve / etc / grubundaki kullanıcıların bir listesini döndüren bir komut dosyasıdır, NIS veya LDAP'yi kontrol etmez, ancak gruba sahip olan kullanıcıları varsayılan grup olarak gösterir Debian 4.7 ve solaris 9
#!/bin/bash
MYGROUP="user"
# get the group ID
MYGID=`grep $MYGROUP /etc/group | cut -d ":" -f3`
if [[ $MYGID != "" ]]
then
# get a newline-separated list of users from /etc/group
MYUSERS=`grep $MYGROUP /etc/group | cut -d ":" -f4| tr "," "\n"`
# add a newline
MYUSERS=$MYUSERS$'\n'
# add the users whose default group is MYGROUP from /etc/passwod
MYUSERS=$MYUSERS`cat /etc/passwd |grep $MYGID | cut -d ":" -f1`
#print the result as a newline-separated list with no duplicates (ready to pass into a bash FOR loop)
printf '%s\n' $MYUSERS | sort | uniq
fi
veya tek katmanlı olarak doğrudan buradan kesip yapıştırabilirsiniz (ilk değişkendeki grup adını değiştirin)
MYGROUP="user";MYGID=`grep $MYGROUP /etc/group | cut -d ":" -f3`;printf '%s\n' `grep $MYGROUP /etc/group | cut -d ":" -f4| tr "," "\n"`$'\n'`cat /etc/passwd |grep $MYGID | cut -d ":" -f1` | sort | uniq
UNIX'te (GNU / Linux'un aksine), listusers komutu var. Listeleyiciler için Solaris kılavuz sayfasına bakınız .
Bu komutun açık kaynaklı Heirloom Project'in bir parçası olduğunu unutmayın . GNU / Linux'ta eksik olduğunu varsayıyorum çünkü RMS gruplara ve izinlere inanmıyor. :-)
NAME listusers - print a list of user logins SYNOPSIS listusers [-g groups] [-l logins] DESCRIPTION Listusers prints the name and the gecos information of all users known to the system, sorted by username. Valid options are: -g groups Only print the names of users that belong to the given group. Multiple groups are accepted if separated by commas. -l logins Print only user names that match logins. Multiple user names are accepted if separated by commas.
Diğer cevaplarda listelenen tüm yaygın tuzakları dikkate alan çok basit bir awk betiği:
getent passwd | awk -F: -v group_name="wheel" '
BEGIN {
"getent group " group_name | getline groupline;
if (!groupline) exit 1;
split(groupline, groupdef, ":");
guid = groupdef[3];
split(groupdef[4], users, ",");
for (k in users) print users[k]
}
$4 == guid {print $1}'
Bunu ldap özellikli kurulumumla kullanıyorum, solaris 8+ ve hpux da dahil olmak üzere standartlara uygun getent & awk ile çalışır.
getent group groupname | awk -F: '{print $4}' | tr , '\n'
Bu 3 bölümden oluşmaktadır:
1 - getent group groupname
"/ etc / group" dosyasındaki grubun satırını gösterir. Alternatif cat /etc/group | grep groupname
.
2 - awk
print yalnızca ',' ile ayrılmış tek bir satırdaki üyelerdir.
3 - tr
',' işaretini yeni bir satırla değiştirin ve her kullanıcıyı arka arkaya yazdırın.
4 - İsteğe bağlı: sort
Kullanıcılar çok fazla ise, ile başka bir boru da kullanabilirsiniz .
Saygılarımızla
Bence en kolay yol aşağıdaki adımlar, herhangi bir paket veya yazılım yüklemenize gerek yok:
İlk olarak, kullanıcıları tanımak istediğiniz grubun GID'sini öğrenirsiniz, bunun için birçok yol vardır: cat / etc / group (son sütun GID'dir) kimlik kullanıcısı (kullanıcı, ait olduğu kişidir. grup)
Şimdi / etc / passwd dosyasındaki tüm kullanıcıları listeleyeceksiniz, ancak yalnızca önceki grubun üyelerini almak için aşağıdaki komut dizisiyle bazı filtreler uygulayacaksınız.
cut -d: -f1,4 / etc / passwd | grep GID (GID, 1. adımdan aldığınız sayıdır)
cut komutu dosyanın sadece bazı "sütunlarını" seçecektir, d parametresi ":" sınırlayıcısını ayarlar, bu durumda, -f parametresi dışarıda (1) ve 4'te gösterilecek "alanları" (veya sütunları) seçer (açık / etc / passwd dosyası, 1º sütunu kullanıcının adı ve 4º, kullanıcının ait olduğu grubun GID'sidir, | grep GID'yi sonlandırmak için yalnızca (4º sütunundaki) grubu filtreleyecektir seçmişti.
Burada, kullanıcının varsayılan grup üyeliğini (kimden /etc/passwd
) ve grup veritabanından ( /etc/group
) dikkate alan başka bir Python tek astarı var
python -c "import grp,pwd; print set(grp.getgrnam('mysupercoolgroup')[3]).union([u[0] for u in pwd.getpwall() if u.pw_gid == grp.getgrnam('mysupercoolgroup')[2]])"
Ben denedim grep 'sample-group-name' /etc/group
bu örneğin dayalı Belirttiğiniz grubun tüm üyelerinin listeler, burada
/etc/group
zaten en az 3 başka cevapta, cevabınız onlara ne değer katıyor ? Ayrıca, tüm bu diğer cevaplar yorumlarınız ikincil gruplar için böyle bir çözüm çalışmaları sadece ve ayrıca yapar vs. LDAP, NIS tarafından yönetilen hesap için değil iş