2
#! /bin/sh
  
DB_USER='aaa';
DB_PASSWD='aaa1';

DB_NAME='data';
TABLE='datalog';


mysql --local-infile=1 --user=$DB_USER --password=$DB_PASSWD $DB_NAME -e "load data local infile '/home/demo/data1.csv' into table datalog fields terminated by ',' lines terminated by '\n';" -e echo "script executed successfully " | date "+%h %e"

My aim is to print a success message after the above script executes successfully. I have written the above command to do so but it is printing the date, not the echo statement.

John Kugelman
  • 349,597
  • 67
  • 533
  • 578
  • You are feeding the stdout of `echo` into the stdin of `date`, but `date` without any option does not read the stdin, so the output of `echo` is effectively lost. What do you think `date` would do with the message you feeding it with? – user1934428 Mar 16 '21 at 08:53

1 Answers1

3

The arguments to mysql -e should be SQL commands, not shell script.

The solution is much simpler than what you are trying.

#!/bin/sh

# Terminate immediately if a command fails
set -e

# Don't put useless semicolons at the end of each assignment
# Use lower case for your private variables
db_user='aaa'
db_passwd='aaa1'

db_name='data'
table='datalog'

# Quote strings
mysql --local-infile=1 --user="$db_user" --password="$db_passwd" "$db_name" \
     -e "load data local infile '/home/demo/data1.csv' into table $table fields terminated by ',' lines terminated by '\n';"

# Just use date
# Print diagnostics to standard error, not standard output
date "+%h %e script executed successfully" >&2

The use of set -e is somewhat cumbersome, but looks like the simplest solution to your basic script. For a more complex script, maybe instead use something like

mysql -e "... stuff ..." || exit

to terminate on failure of this individual command, but allow other failures in the script. Perhaps see also What does set -e mean in a bash script?

If you want to preserve the exit code from mysql and always print a message to show what happened, probably take out the set -e and do something like

if mysql -e "... whatever ..."
then
    date "+%h %e script completed successfully" >&2
else
    rc=$?
    date "+%h %e script failed: $rc" >&2
    exit $rc
fi

As an aside, date does not read its standard input for anything, so you can't pipe echo to it. The script above simply uses only date, but here are a few different ways you could solve that.

# Merge this output with the next output
date "+%h %e" | tr '\n' ' ' >&2
echo script executed successfully >&2

or

# Use a command substitution to interpolate the output from date into
# the arguments for echo
echo "$(date "+%h %e") script executed successfully >&2

For more complex situations, maybe also look into xargs, though it's absolutely horribly overkill here.

date "+%h %e" | xargs -I {} echo script executed successfully {} >&2

If you use only date, you will need to be mindful of your use of % in any literal message; to print a literal per-cent sign from date, use %%.

As a further stylistic aside, you should avoid upper case for your private variables.

tripleee
  • 175,061
  • 34
  • 275
  • 318
  • thank you for your help I want to ask one more thing like here I'm only printing success message suppose my script fails due to some error so i want to see that error with date like you have done for success message how can i achieve it? – Abhishek Singh Mar 16 '21 at 08:16
  • It's not impossible but rather cumbersome because piping standard error from `mysql` to a formatting command will lose the failure code from `mysql`. See if you can tweak its logging options instead, or just print the status message immediately after `mysql` finishes regardless of whether it fails or not (i.e. probably take out the `set -e` and maybe instead capture the exit code from `$?`) – tripleee Mar 16 '21 at 08:18
  • `mysql -e "... whatever ..." 2>&1 | sed "s/^/$(date "+%h %e")/" >&2` would do what you are asking but like I mentioned in my previous comment, you then have a new problem. – tripleee Mar 16 '21 at 08:20