Hiding user input on a terminal in a Linux script

I have a bash script as shown below:

#!/bin/bash echo "Please enter your username"; read username; echo "Please enter your password"; read password; 

I want that when the user enters the password on the terminal, it should not be displayed (or something like *******) should be displayed). How to achieve this?

+109
linux scripting bash
Nov 30 '10 at 17:44
source share
8 answers

Just put -s on your read request as follows:

 $ read -s PASSWORD $ echo $PASSWORD 
+245
Nov 30 '10 at 17:46
source share

Update

If you want a fantasy by setting * for each character that they type, you can do something like this (using 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 

No fantasy

 echo "Please enter your username"; read username; echo "Please enter your password"; stty -echo read password; stty echo 
+23
Nov 30 '10 at 17:46
source share

for a solution that works without bash or specific functions from read , you can use stty to disable echo

 stty_orig=$(stty -g) stty -echo read password stty $stty_orig 
+15
Nov 30 '10 at 17:47
source share

Here's a variation on the excellent * -printed @SiegeX solution for bash with backspace support ; this allows the user to correct their entry using the backspace key ( delete on Mac) , which is usually supported by password hints:

 #!/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 

Note:

  • As to why pressing backspace writes the 0x7f character code: "On modern systems, the backspace key element is often mapped to the delete character (0x7f in ASCII or Unicode)" https://en.wikipedia.org/wiki/Backspace
  • \b \b needed to give the style a character to the left; just using \b , moves the cursor to the left, but leaves the character intact (non-destructive inverse space). By printing a space and re-moving, the character seems to have been deleted (thanks, "backspace" escape character "\ b" in C, unexpected behavior? ).



On a POSIX server (for example, sh on Debian and Ubuntu, where sh is dash ), it uses the stty -echo approach (which is suboptimal because it does not print anything), since the built-in read does not support the -s and -n options.

+8
Apr 08 '14 at 14:25
source share

A bit different from (but most often) @lesmana's answer

 stty -echo read password stty echo 

simple: hide echo do your things show echo

+3
Mar 30 '16 at 13:29
source share

Here is a @SiegeX answer that works with the traditional Bourne shell (which does not support += assignments).

 password='' while IFS= read -r -s -n1 pass; do if [ -z "$pass" ]; then echo break else printf '*' password="$password$pass" fi done 
+2
Apr 08 '14 at 11:41 on
source share

I always like Ansi escape characters:

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

8m makes the text invisible, and 0m resets the text to "normal". "-e" makes Ansi possible.

The only caveat is that you can still copy and paste the text you have, so you probably shouldn't use it if you really want to be safe.

It just allows people not to look at your passwords when you enter them. Just don't leave your computer after that. :)




Note:

The above version is platform independent if it supports Ansi escape sequences.

However, for another Unix solution, you can simply tell read not to repeat characters ...

 printf "password: " let pass $(read -s) printf "\nhey everyone, the password the user just entered is $pass\n" 
+2
Sep 21 '14 at 3:29
source share

Get username and password

Make it easier to read, but put it in a better position on the screen.

 #!/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 
+1
Mar 22 '18 at 15:46
source share



All Articles