Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/linux/27.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
使用bash脚本查找linux用户_Linux_Bash - Fatal编程技术网

使用bash脚本查找linux用户

使用bash脚本查找linux用户,linux,bash,Linux,Bash,我是bash脚本和linux的新手。我想编写一个脚本,从终端获取用户名,并说明该用户名是否在passwd上。我写了下面的脚本并尝试了一下,但它不起作用。帮我做我能做的 users = cat /etc/passwd echo User_Name cat users | grep User_Name if [ User_Name in users ]; then echo "User_Name FOUND" else echo "User NOT FOUND!" fi 如何定义变

我是bash脚本和linux的新手。我想编写一个脚本,从终端获取用户名,并说明该用户名是否在passwd上。我写了下面的脚本并尝试了一下,但它不起作用。帮我做我能做的

users = cat /etc/passwd
echo User_Name
cat users | grep User_Name
if [ User_Name in users ];
then
    echo "User_Name FOUND"
else
    echo "User NOT FOUND!"
fi

如何定义变量以从Terminal读取字符串。

您的脚本可能如下所示:

#!/usr/bin/env bash

while read -rp "Enter user name: " user_name
do
    if [ -z "$user_name" ]
    then
        echo "Enter a non-empty username"    
        continue
    fi

    if grep -q "^$user_name:" /etc/passwd
    then
        echo "$user_name FOUND"
        exit 0
    else
        echo "$user_name NOT FOUND!" >&2
        exit 1
    fi
done

要读取值作为用户输入,可以使用“读取”命令

为了方便起见,大多数脚本在shell脚本的变量名上使用ALLCAPS

也考虑将此值作为参数传入脚本中。单个参数的可读性为“$1”

Hint1:您不需要为了这个检查而将整个文件存储在内存中

Hint2:要查找passwd文件中是否存在用户,您应该只检查该文件的第一列,然后尝试匹配

Hint3:如果你想使用grep命令,当有匹配时它会返回success,当没有匹配时它会返回failure

下面的代码也适用于该任务

#!/bin/bash
read WHO; 
grep "^${WHO}:" /etc/passwd 2>/dev/null >/dev/null && echo "found" || echo "not found"

要从终端打印和读取参数,您应该使用echo,然后使用read commane,然后用美元符号调用它,最后脚本知道您想要什么。 例如:

echo "Enter UserName: "
read User_Name
以下是代码的正确形式:

echo "Enter the Username: "
read User_Name
cut -f 1 -d: /etc/passwd | grep -q $User_Name
if [ $? -eq 0 ];
then
    echo "User $User_Name FOUND"
else
    echo "User NOT FOUND!"
fi

提示:

cut -f 1 -d  #cut the first column of the passwd list
grep -q # find username and do  not  write  anything  to  standard   output in terminal.

if [ $? -eq 0 ] #in linux terminal when we want to know whether the previous command is executed correctly we use $? and the output must be 0. and - eq means equal to 0. and when we use that, it means if previos command (grep the username) executed correctly and the username was found, then run next step and print it found.

以下是我对这个问题的看法。使用
getent
在文件
/etc/passwd

如果您只想检查用户是否存在

getent passwd "$username"
如果用户确实存在,则应打印该用户的名称(以及中的所有信息),并返回零
0
状态,即true。否则为非零,请参见手册了解不同状态的含义


既然我们知道了手头的信息,我们就可以使用
if语句了

if getent passwd "$username"; then
  echo "$username found."
else
  echo "$username not found." >&2
fi

如果这不是期望的结果,或者您刚刚处于测试的退出/返回状态,则将输出重定向到
/dev/null

if getent passwd "$username" >/dev/null; then
  echo "$username found."
else
  echo "$username not found." >&2
fi

将其添加到完整的脚本中

#!/bin/sh

check_user() {
  printf '%s' "Enter user name: "
  read -r user_name
  case $user_name in
    '') printf '%s\n' "You have not entered anything!" >&2  ##: If empty input.
     return 1;;
  esac
  if getent passwd "$user_name" >/dev/null; then ##: getent has no -q option unfortunately.
    printf '%s\n' "$user_name FOUND"
    return 0
  else
    printf '%s\n' "$user_name NOT FOUND!" >&2
    return 1
  fi
}

##: Continue the loop until a match in `/etc/passwd` was given.
until check_user; do
  printf 'Please try again!\n' >&2  ##: Send message to stderr and loop again.
done

不必重定向到
/dev/null
,您可以将
getent
的输出保存在一个变量中,并使用该值,再加上一点

  • until
    循环将继续,直到收到
    0
    返回状态
  • 参见
    getent(1)
    aka
    man 1 getent
  • GNU Linux
    FreeBSD

我们使用
read
从终端的用户那里获取输入。 在下面的解决方案中,我们使用(出现在BSD和Linux上)来确定用户是否存在

#!/bin/bash
set -o errexit -o pipefail -o nounset


function interactive_check_if_user_exists {
    local username output

    read -p 'Username to check: ' -r username

    if output="$(id -u "$username" 2>&1)"
    then
        echo "Found \`$username\` (uid: $output)" >&2
    else
        local code=$?
        if [[ $code -eq 1 ]]
        then
            echo "User \`$username\` is not present on this system." >&2
        else
            echo "Unexpected error occurred: $output" >&2
            return "$code"
        fi
    fi
}

interactive_check_if_user_exists

看看当用户按Enter键而不输入非空用户名时会发生什么。@ArkadiuszDrabczyk是的,我知道您的解决方案是正确的。但他根本不要求非空用户名。脚本已损坏,请不要使用它。它无法正确检查完整用户名。只需按
t
,它就会说用户
t
存在,因为
root
中有
t
,即使系统上没有这样的用户。您必须使用
^user:
表单才能正确执行。OP在编写脚本时寻求帮助,您应负责交付在所有情况下都能正常工作的脚本。如果您先使用
cut
,如何确保脚本用户永远不会传递空用户名?或者
^user$
。非常感谢我的努力,效果非常好。但是我不能理解下面的“while true”对不起,我不明白。你能说清楚点吗?你不明白哪一部分?当
为真时可以替换为
;也可以将错误消息发送到
stderr
,例如
echo“$user\u name NOT FOUND!”&2
并在该消息后添加一个
exit 1
,只需我的2美分。使用
grep-q
将阻止从
/etc/passwd
(或重定向到
/dev/nul
)输出整行内容。Jetchisel:ok,我想我明白你的意思了。我稍微修改了你的建议,并在找到用户名时将所有内容移动到一个显式的
exit 0
循环中。关键是——不管你怎么做,你必须区分,等等
“ann”
“anna”
因此您必须与
/etc/passwd
@SiGnoR中的整个第一个字段进行比较:您的第一行运行一个带有三个参数的命令
cat
/etc/passwd
)。请参见如何创建变量。第三个命令要求输出名为
users
的文件。有关如何使用变量的信息,请参见。最后,代码中没有任何语句可以从终端读取用户名。1。为什么要用
大小写检查
用户名是否为空?是否存在未实现
test-z
的shell?提到它。2.
shellcheck
中有3个警告,如果您修复了它们,这将是一件好事。
bash
但是便携性较差,例如默认情况下不会出现在FreeBSD上。如果您不是root用户,则不总是可能出现(尽管在这种特殊情况下,您甚至不必将bash安装到
/bin
,因为您使用
/usr/bin/env
,并且始终可以运行
bash脚本
)。还有一些随Busybox/Toybox提供的Linux系统也不提供Bash,这在嵌入式应用中最为常见。@ArkadiuszDrabczyk对,我认为shellcheck现在对
POSIX sh
语法很满意。感谢您指出这一点。是的,shellcheck很高兴,但您没有回答我的第一个问题。
check_user() {
  printf '%s' "Enter user name: "
  read -r user_name
  case $user_name in
    '') printf '%s\n' "You have not entered anything!" >&2
     return 1;;
  esac
  if user=$(getent passwd "$user_name"); then
    printf '%s\n' "${user%%:*} FOUND"  ##: Print only the username using P.E.
    return 0
  else
    printf '%s\n' "${user:-"$user_name"} NOT FOUND" >&2  ##: If the value of "$user" is empty (No match found by getent)
    return 1
  fi
}

until check_user; do
  printf 'Please try again!\n' >&2
done
#!/bin/bash
set -o errexit -o pipefail -o nounset


function interactive_check_if_user_exists {
    local username output

    read -p 'Username to check: ' -r username

    if output="$(id -u "$username" 2>&1)"
    then
        echo "Found \`$username\` (uid: $output)" >&2
    else
        local code=$?
        if [[ $code -eq 1 ]]
        then
            echo "User \`$username\` is not present on this system." >&2
        else
            echo "Unexpected error occurred: $output" >&2
            return "$code"
        fi
    fi
}

interactive_check_if_user_exists