Скрытие пользовательского ввода на терминале в скрипте Linux - PullRequest
108 голосов
/ 30 ноября 2010

У меня есть скрипт bash, подобный следующему:

#!/bin/bash

echo "Please enter your username";
read username;

echo "Please enter your password";
read password;

Я хочу, чтобы при вводе пользователем пароля на терминале он не отображался (или что-то вроде *******).должен отображаться).Как мне этого добиться?

Ответы [ 8 ]

242 голосов
/ 30 ноября 2010

Просто добавьте -s к вашему вызову для чтения следующим образом:

$ read -s PASSWORD
$ echo $PASSWORD
23 голосов
/ 30 ноября 2010

Обновление

Если вы хотите получить фантазию, выводя * для каждого символа, который они вводят, вы можете сделать что-то вроде этого (используя andreas 'read -s solution):

unset password;
while IFS= read -r -s -n1 pass; do
  if [[ -z $pass ]]; then
     echo
     break
  else
     echo -n '*'
     password+=$pass
  fi
done

Без фантазии

echo "Please enter your username";
read username;

echo "Please enter your password";
stty -echo
read password;
stty echo
14 голосов
/ 30 ноября 2010

для решения, которое работает без bash или определенных функций из read, вы можете использовать stty, чтобы отключить эхо

stty_orig=`stty -g`
stty -echo
read password
stty $stty_orig
8 голосов
/ 08 апреля 2014

Вот вариант превосходного * решения для печати @ SiegeX для bash с добавленной поддержкой backspace ; это позволяет пользователю исправить свою запись с помощью клавиши backspace (клавиша delete на Mac) , что обычно поддерживается запросами пароля:

#!/usr/bin/env bash

password=''
while IFS= read -r -s -n1 char; do
  [[ -z $char ]] && { printf '\n'; break; } # ENTER pressed; output \n and break.
  if [[ $char == $'\x7f' ]]; then # backspace was pressed
      # Remove last char from output variable.
      [[ -n $password ]] && password=${password%?}
      # Erase '*' to the left.
      printf '\b \b' 
  else
    # Add typed char to output variable.
    password+=$char
    # Print '*' in its stead.
    printf '*'
  fi
done

Примечание:

  • Что касается того, почему нажатие клавиши Backspace записывает код символа 0x7f: «В современных системах клавиша Backspace часто отображается на символ удаления (0x7f в ASCII или Unicode)» https://en.wikipedia.org/wiki/Backspace
  • \b \b необходимо, чтобы выглядело как , удаляя символ слева; простое использование \b перемещает курсор влево, но оставляет символ нетронутым ( неразрушающий backspace). После печати пробела и повторного перемещения назад символ, кажется, был стерт (спасибо, Экранирующий символ «\ backspace» «\ b» в C, неожиданное поведение? ).

В оболочке только для POSIX (например, sh в Debian и Ubuntu, где sh равно dash), использует stty -echo подход (который является неоптимальным, потому что он печатает ничего ), потому что встроенный read не будет поддерживать опции -s и -n.

3 голосов
/ 30 марта 2016

Немного отличается от (но чаще всего нравится) @ lesmana's answer

stty -echo
read password
stty echo

просто: скрыть эхо делай свои вещи show echo

2 голосов
/ 21 сентября 2014

Мне всегда нравятся экранирующие символы Ansi:

echo -e "Enter your password: \x1B[8m"
echo -e "\x1B[0m"

8m делает текст невидимым, а 0m сбрасывает текст в «обычный».-E делает возможными побеги Анси.

Единственное предостережение в том, что вы все еще можете копировать и вставлять текст, который там находится, поэтому вам, вероятно, не следует использовать его, если вы действительно хотите обеспечить безопасность.

Это просто позволяет людям не смотреть на ваши пароли, когда вы их вводите. Просто не оставляйте компьютер включенным впоследствии.:)


ПРИМЕЧАНИЕ:

Вышеприведенное не зависит от платформы, если оно поддерживает escape-последовательности Ansi.

Однако для другого решения Unix можно просто сказатьread чтобы не повторять символы ...

printf "password: "
let pass $(read -s)
printf "\nhey everyone, the password the user just entered is $pass\n"
2 голосов
/ 08 апреля 2014

Вот вариант ответа @ SiegeX, который работает с традиционной оболочкой Bourne (которая не поддерживает += назначения).

password=''
while IFS= read -r -s -n1 pass; do
  if [ -z "$pass" ]; then
     echo
     break
  else
     printf '*'
     password="$password$pass"
  fi
done
1 голос
/ 22 марта 2018

Получить логин и пароль

Сделайте его более понятным для чтения, но поместите его в лучшее положение над экраном

#!/bin/bash
clear
echo 
echo 
echo
counter=0
unset username
prompt="  Enter Username:"
while IFS= read -p "$prompt" -r -s -n 1 char
do
    if [[ $char == $'\0' ]]; then
        break
    elif [ $char == $'\x08' ] && [ $counter -gt 0 ]; then
        prompt=$'\b \b'
        username="${username%?}"
        counter=$((counter-1))
    elif [ $char == $'\x08' ] && [ $counter -lt 1 ]; then
        prompt=''
        continue
    else
        counter=$((counter+1))
        prompt="$char"
        username+="$char"
    fi
done
echo
unset password
prompt="  Enter Password:"
while IFS= read -p "$prompt" -r -s -n 1 char
do
    if [[ $char == $'\0' ]]; then
        break
    elif [ $char == $'\x08' ] && [ $counter -gt 0 ]; then
        prompt=$'\b \b'
        password="${password%?}"
        counter=$((counter-1))
    elif [ $char == $'\x08' ] && [ $counter -lt 1 ]; then
        echo
        prompt="  Enter Password:"
        continue
    else
        counter=$((counter+1))
        prompt='*'
        password+="$char"
    fi
done
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...