encrypting/decrypting password stored in config file - bash

I have a simple Bash script automating tasks which require password-based authentication.
Currently I store the credentials in plain text:
$ cat ~/.myconfig
username=foo
password=bar
Obviously that's bad - so I wonder whether there's a simple way to encrypt/decrypt the password using my public/private key pair. Using Yet Another Password for the encryption wouldn't gain much, so I want it to happen pretty much automatically.
I've done some research (around here and elsewhere), but am way out of my depth on this one...

You can store password into md5 sum, add some salt before.
create:
\#!/bin/bash
salt=12345_
protocol=sha1sum
read -p "Enter login: " username
read -p -s "Password: " pass1
read -p -s "Repeat: pass2
if [ "pass1 != pass2" ]; then echo "Pass missmatch"; exit 1; else password=pass1; fi
echo -en "$username " >> ./mypasswd
echo -e "${salt}${password} | $protocol | awk '{print $1}'" >> ./mypqsswd
read:
\#!/bin/bash
salt=12345_ #(samesalt)
protocol=sha1sum
read -p "Enter username: " username
read -p -s "Enter password: " password
if [ `grep $username ./mypasswd | awk '{print $2}' != `echo -e "`echo ${salt}${password} | $protocol | awk '{print $2}'`" ]; then echo -e "wrong username or password"; exit 127; else echo -e "login successfull"; fi
There's your code.

To automate your task means providing the password; it won't make a difference is you encrypt/obfuscate the password, you'll need to provide the decrypting too.
The only way around this dilemma is an agent-like program, as for example ssh-agent, which stores your passwords for you.
(edit: corrected link)

If you simply want to hide the password then store its SHA1 hash. The compare the hash of the entered password with your stored hash.

Related

How to generate password for users and send them email?

I have a file with the list of users, I found a way how to generate for each user random password, but didn't know how to select each user their username and password and send them via email (email example username#example.com)
the script sends each user an email with each password from the file, that is, if there are 5 users, then each of them will receive 5 emails and 5 different passwords.
Generate Password
#!/bin/bash
file=$(cat /tmp/user_names.txt)
for line in $file
do
passrand=$(openssl rand -base64 12)
echo -e "$line" "$passrand"
done
Send email
#!/bin/bash
for maillogin in $(cut -f1 -d ' ' /tmp/u_p.txt) || pass=$(cut -f2 -d' ' /tmp/u_p.txt)
do
for pass in $(cut -f2 -d' ' /tmp/u_p.txt)
do
echo "Hello your login is" $maillogin "and password is" $pass | mail -s "Test Mail" "${maillogin}#example.com"
done
done
Your first script is ok.
For the second, you need to read line after line. So, do not use nested loops to read login and password. Use read command and decompose line:
#!/bin/bash
UP_FILE="/tmp/u_p.txt"
while read -r
do
# maillogin <- line without any characters *after first* space (space included)
maillogin="${REPLY%% *}"
# pass <- line without any characters *before first* space (space included)
pass="${REPLY#* }"
echo "Hello your login is $maillogin and password is $pass" | mail -s "Test Mail" "${maillogin}#example.com"
done < "${UP_FILE}"

How to set the password for a new created in bash user using awk

Need some help in assigning a password to each newly created user from a text file using awk.
For example:
Text file:
John Doe 12345678
Jane Doe 87654321
Newly created user:
JDoe5678 with password: 12345678
JDoe4321 with password: 87654321
My current code:
#!/bin/bash
PATH_EMPLOYEE_FILE="employeelist"
password=($(awk '{print {print $3}))}' "${PATH_EMPLOYEE_FILE}"))
groupname="group1"
USERS_LIST=($(awk '{print substr($1,1,1) $2 substr($3,length($3)-3,length($3))}' "${PATH_EMPLOYEE_FILE}"))
for USER in "${USERS_LIST[#]}"
do
echo "User account created: ${USER}"
useradd -m -G "${groupname}" "${USER}" -p ${password}
done
You're not indexing $password, so you're always using the first password in the useradd command.
There's no need for awk or arrays, you can use bash's read command, and its parameter expansion operators to extract parts of the first name and password into the username.
while read -r fname lname password; do
username=${fname:0:1}$lname${password: -4} # don't forget the space before -4
echo "User account created: $username"
useradd -m -G "$groupname" "$username" -p "$password"
done < "$PATH_EMPLOYEE_FILE"

If statement matching words separated by special char

I'm new to unix. I have a file with an unknown amount of lines in format: "password, username" and I'm trying to make a function that checks this file against user inputted login.
What I have so far:
Accounts file format:
AAA###, firstname.lastname
echo "Please enter Username:"
read username
if cut -d "," -f2 accounts | grep -w -q $username
then
echo "Success"
fi
This function will return Success for inputs "firstname" "lastname" and "firstname.lastname" when I only want it to return for "firstname.lastname"
Any help would be appreciated.
You could go for an exact match, with ^ and $ anchors, like this:
echo "Please enter Username:"
read username
if cut -d "," -f2 accounts | grep -q "^$username$"; then
echo "Success"
fi
While this would work even when the user gives an empty input, you might want to explicitly check for that.
If you loop over the file within the shell, you can use string equality operators instead of regular expressions:
read -rp "enter Username (first.last): " username
shopt -s extglob
found=false
while IFS=, read -r pass uname _othertext; do
# from your question, it looks like the separator is "comma space"
# so we'll remove leading whitespace from the $uname
if [[ "$username" = "${uname##+([[:blank:]])}" ]]; then
echo "Success"
found=true
break
fi
done < accounts
if ! $found; then
echo "$username not found in accounts file"
fi
while read loops in the shell are very slow compared to grep, but depending on the size of the accounts file you may not notice.
Based on your comment, the issue is that the field separator is a comma then a space, not just a comma. cut can't do multi-character delimiters, but awk can. In your code, replace
cut -d "," -f2
with
awk -F ", " '{print $2}'
By the way, there are a few things needed to guard against user input:
# Use "-r" to avoid backslash escapes.
read -rp "Please enter Username:" username
# Always quote variables ("$username").
# Use "grep -F" for fixed-string mode.
# Use "--" to prevent arguments being interpreted as options.
if awk -F ", " '{print $2}' accounts | grep -wqF -- "$username"; then
echo "Success"
fi

Password protected shell script

I want to make my script password protected. If I use this code it works:
ACTUAL="sam123"
read -s -p "Password: " enteredpass
I also want to protect the script from being read with cat and vi. I tried to use vim -x <script> to encrypt it but then it won't allow me to run it.
I am using a generic user and haven't gotten anywhere.
You can't do this securely without your sysadmin's help, but you can do something sorta-kinda-maybe-not-really-adequate without it.
So, let's say you create your script like so:
cat >myscript <<EOF
echo "Doing something super secret here"
EOF
...but you don't want anyone who doesn't know the password to run it, even if they're using a shared account. You can do this by encrypting it:
gpg -ac <myscript >myscript.asc
...and then embedding that plaintext into a script:
#!/usr/bin/env bash
{ gpg -d | bash -s "$#"; } <<'EOF'
-----BEGIN PGP MESSAGE-----
jA0EBwMCBogTuO9LcuZg0lsB2wqrsPU8Bw2DRzAZr+hiecYTOe//ajXfcjPI4G6c
P3anEYb0N4ng6gsOhKqOYpZU9JzVVkxeL73CD1GSpcQS46YlKWJI8FKcPckR6BE+
7vqkcPWwcS7oy4H2
=gmFu
-----END PGP MESSAGE-----
EOF
That said, other users in the shared account can still collect your password if they connect to and trace your process while it's running -- running strace on the copy of bash -s will show the text being fed into its stdin. In general, you shouldn't rely on shared accounts for anything that needs to remain confidential.
Late answer for posterity, how about using openssl? here's my scriptencrypt.sh
It generates a new .sh file that requires a password
#!/bin/bash
if [ -z "$1" ]; then echo "usage: $(basename $0) script"; exit 1; fi
script=$(cat "$1")
checksum="$(echo "$script" | md5sum | awk '{ print $1 }')"
extension=$([[ "$(basename $1)" =~ .\.. ]] && echo ".${1##*.}" || echo "")
cat << EOF > "${1%.*}.enc${extension}"
#!/bin/bash
read -r -d '' encrypted_script << EOF2
$(openssl aes-256-cbc -a -salt -in /dev/stdin -out /dev/stdout <<< "${script}")
EOF2
read -s -p "Enter script password: " password
echo
unencrypted_script=\$(openssl aes-256-cbc -d -a -salt -in /dev/stdin -out /dev/stdout <<< "\${encrypted_script}" -pass pass:"\${password}" 2>/dev/null | tr -d '\000')
clear
checksum="\$(echo "\$unencrypted_script" | md5sum | awk '{ print \$1 }')"
if [ "\${checksum}" = "${checksum}" ]; then
eval "\${unencrypted_script}"
exit 0
else
echo "Wrong password inserted"
exit 1
fi
EOF

Script to automate kadmin principal

I am trying to write a script to automate kerberos principal and but the script is not working. Not sure what i am missing. Below is the code:
#!/bin/bash
read -p "Please enter space-delimited list of principal to create: " NEW_Principal
clear
echo "password" | kinit adminuser/admin ; echo "password" | kadmin
for i in $NEW_ORGS
do
addprinc ${i}
${i}
echo ""
done
Also tried writing this way:
################### create principal #############
pass="principal_password"
echo "password" | kinit adminuser/admin
printf "%b" "password" | kadmin
printf "%b" "addprinc principal_name\n$pass\n$pass"
But its not working in script.
I have done it. All I have to do is pass the command as a string. Here is the answer:
echo -e "${i}\n${i}" | kadmin -w "$krb_pass" -q "addprinc

Resources