insert multiple users in mysql database using awk - mysql

Currently, I have a usrpwd.txt file with users and passwords separated by 'space'. I wish to add these users to my mysql server and change their privileges. Since there are 2000 users, it becomes unpractical to add them manually. I tried to use awk in a bash script:
awk '{mysql -u root -proot -e "CREATE USER '\''"$1"'\''#'\''%'\'' IDENTIFIED BY '\''"$2"'\'';"}' ./conf/usrpwd.txt ;
Unfortunately, the users are not being added. No error is reported.
Regards, Andre

My first instinct wouldn't be to solve this in awk, but anyway, here it is:
$ cat tst.awk
{
cmd = sprintf("mysql -u root -p root -h localhost -e \"CREATE USER '%s'#'%' IDENTIFIED BY '%s'\"", $1, $2)
if ((cmd | getline line) > 0)
print line
close(cmd)
}
You can call this like:
$ awk -f tst.awk usrpwd.txt
or you could put this in a bash script, if you wanted to.

Related

Escaping out password variable with special characters for mysqldump

I'm trying to create a shell script to automatically backup my whole database. My script expects the password in a new line because I don't want to store it anywhere. Here is my code:
#!/bin/bash
echo -n Password:
read -s PASS
echo
docker exec db /usr/bin/mysqldump --all-databases -u admin --password='\''$PASS\'' > backup-$(date "+%Y-%m-%d").sql
The problem is, that I need to put the variable into single quotes because of the $ signs in the password, but I can't read variables in single quotes.
I know there are several similar questions out there, but I could not solve is with them.
So if the password is '$ecretPa$$word', then the actual executed program should be something like this:
docker exec db /usr/bin/mysqldump --all-databases -u admin --password='$ecretPa$$word' > backup-2020-03-03.sql
I managed to make this work. Maybe the problem was not with the escaping but with the way I tried to run this.
My final code:
#!/bin/bash
echo -n Password:
read -s PASS
echo
cmd="docker exec db /usr/bin/mysqldump --all-databases -u admin --password='$PASS' > backup-$(date "+%Y-%m-%d").sql"
eval "$cmd";

Why is this bash variable blank when taking output from mysql?

I am trying to take the output from a MySQL query in bash and use it in a bash variable, but it keeps coming up blank when used in the script, but works perfectly from the terminal. What's wrong here?
I've tried changing the way the statement is written and changing the name of the variable just in case it was somehow reserved. I've also done a significant amount of searching but it turns out if you but 'bash', 'blank', and 'variable' in the search it usually comes up with some version of how to test for blank variables which I already know how to do.
tempo=$(mysql -u "$dbuser" -p"$dbpass" -D "$database" -t -s -r -N -B -e "select user from example where user='$temp' > 0;")
printf "the output should be: $tempo" # This is a test statement
The end result should be that the $tempo variable should either contain a user name from the database or be blank if there isn't one.
I think there is some error with your sql statement at user = '$temp' > 0.
But to get the result from MySql you have to redirect the standard error (stderr) to the standard output (stdout), you should use 2>&1.
Most probably you will run into MySql error but try running this on terminal.
tempo=$((mysql -u "$dbuser" -p"$dbpass" -D "$database" -t -s -r -N -B -e "select user from example where user='$temp' > 0;") 2>&1)
The solution was to echo the result of the sql query like this:
tempo=$(echo $(mysql -u "$dbuser" -p"$dbpass" -D "$database" -s -N -B -e "select user from example where user='$username' > 0;"))
Now I'm left with logic issues but I think I can handle that.

connect to mysql db and execute query and export result to variable - bash script

I want to connect to mysql databse and execute some queries and export its result to a varibale, and do all of these need to be done entirely by bash script
I have a snippet code but does not work.
#!/bin/bash
BASEDIR=$(dirname $0)
cd $BASEDIR
mysqlUser=n_userdb
mysqlPass=d2FVR0NA3
mysqlDb=n_datadb
result=$(mysql -u $mysqlUser -p$mysqlPass -D $mysqlDb -e "select * from confs limit 1")
echo "${result}" >> a.txt
whats the problem ?
The issue was resolved in the chat by using the correct password.
If you further want to get only the data, use mysql with -NB (or --skip-column-names and --batch).
Also, the script needs to quote the variable expansions, or there will be issues with usernames/passwords containing characters that are special to the shell. Additionally, uppercase variable names are usually reserved for system variables.
#!/bin/sh
basedir=$(dirname "$0")
mysqlUser='n_userdb'
mysqlPass='d2FVR0NA3'
mysqlDb='n_datadb'
cd "$basedir" &&
mysql -NB -u "$mysqlUser" -p"$mysqlPass" -D "$mysqlDb" \
-e 'select * from confs limit 1' >a.txt 2>a-err.txt
Ideally though, you'd use a my.cnf file to configure the username and password.
See e.g.
MySQL Utilities - ~/.my.cnf option file
mysql .my.cnf not reading credentials properly?
Do this:
result=$(mysql -u $mysqlUser -p$mysqlPass -D $mysqlDb -e "select * from confs limit 1" | grep '^\|' | tail -1)
The $() statement of Bash has trouble handling variables which contain multiple lines so the above hack greps only the interesting part: the data

mysql export tables using wildcard

I want to export a list of tables starting with a certain prefix using a wild card.
Ideally I would do:
mysqldump -uroot -p mydb table_prefix_* > backup.sql
Obviously that doesn’t work. But what is the correct way to do this?
If it has a prefix, make a user with select and lock permissions to the table with GRANT like this
GRANT SELECT, LOCK TABLES ON `table\_prefix\_%` . * TO 'backup-user'#'localhost';
then instead of running mysql dump as root, run it as backup-user with the option --all-databases
as backup user only has select and lock permission on these tables, They are the only ones which will be there.
its also safer using a user like this rather than the root account for everything
Ok. Here is a solution using a Bash script (I've tested it in Linux).
Create a text file named "dumpTablesWithPrefix.script" and put this in it:
tableList=$(mysql -h $1 -u $2 -p$3 $4 -e"show tables" | grep "^$5.*" | sed ':a;N;$!ba;s/\n/ /g')
mysqldump -h $1 -u $2 -p$3 $4 $tableList
Save it, and make it executable:
$ chmod +x dumpTablesWithPrefix.script
Now you can run it:
$ ./dumpTablesWithPrefix.script host user pwd database tblPrefix > output.sql
Now let me explain each piece:
The command-line arguments
Bash scripts store command-line arguments in the variables $1, $2, $3 and so on. So the first thing I need to tell you is the order of the arguments you need:
The host (if the mysql server is in your machine, write localhost)
Your user
Your password
The name of your database
The prefix of the tables you want to export
The first line of the script
I'll split this line in three pieces:
mysql -h $1 -u $2 -p$3 $4 -e"show tables"
This piece retrieves the full table list of your database, one table per line.
| grep "^$5.*"
This piece filters the table list, using the prefix you specified.
| sed ':a;N;$!ba;s/\n/ /g'
This final piece (a gem I found here: How can I replace a newline (\n) using sed? ) replaces all the "new line" characters with spaces.
This three pieces, strung together, throw the filtered table list and store it in the tableList variable.
The second line of the script
mysqldump -h $1 -u $2 -p$3 $4 $tableList
This line is simply the MySQL Dump command that does what you need.
Hope this helps

Mysqldump more than one table?

How can I use mysqldump to dump certain tables that start with common prefix?
Hehe, this is kind of a hack, but it works (using bash):
mysqldump -u USER -p DATABASE $(mysql -u USER -p -D DATABASE -Bse "show tables like 'PREFIX%'") > /tmp/DATABASE.out
Change the ALLCAPS words as needed.
You can create backup.sh script:
BACKUP_DIR="/path/to/backups"
DB_HOST="domain.com"
DB_USER="user"
DB_PASS="pass"
PREFIX="phpbb"
TMP_LIST = mysql --host=$DB_HOST --user=$DB_USER --password=$DB_PASS -e "show databases;" | grep $PREFIX
# just get to database name column (may be $1, don't remember)
TMP_LIST = cat $TMP_LIST | awk '{print $2}'
# Getting dbs
mkdir $BACKUP_DIR/tmp
for db in $TMP_LIST ; do
mysqldump --host=$DB_HOST --user=$DB_USER --password=$DB_PASS --opt $db > $BACKUP_DIR/tmp/$db.sql
zip -mj $BACKUP_DIR/tmp/$db.sql.zip $BACKUP_DIR/tmp/$db.sql 2>&1
done
Hope it help.