0

I need a shell script to load data into mysql db. The script is the next:

# !bin/bash

qry="DROP TABLE IF EXISTS tmp_x;
    CREATE TEMPORARY TABLE tmp_x AS SELECT * FROM x.y LIMIT 0;
    LOAD DATA INFILE 'path/xxx.csv' 
    INTO TABLE tmp_x 
    FIELDS TERMINATED BY "\," 
    ENCLOSED BY "\""
    LINES TERMINATED BY "\\n"
    IGNORE 1 ROWS;"

mysql --host=xxx --user=xxx --password=xxx db << EOF 
$qry
EOF

I get the following error message:

ERROR 1064 (42000) at line 3: You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '
ENCLOSED BY "

LINES TERMINATED BY \n

IGNORE 1 ROWS' at line 3

I think it is something to do escaping some character, I tried changing to single quotes but it does not work neither.

I am workin on Ubuntu 18.

Any help will be very grateful.

3
  • 1
    Why not just put the query directly in the heredoc? Quote the heredoc (<<'EOF' instead of <<EOF) and it's completely literal -- the shell doesn't change anything in its contents at all. Commented Feb 20, 2020 at 17:01
  • BTW, if you want to see how your variable was parsed with the current code, just printf '%s\n' "$qry" and then compare it to what you know is good/working SQL. Commented Feb 20, 2020 at 17:02
  • probably you need to escape double quotes of "\," , otherwise string will end after encountering first double quote. Also you shebang seems wrong. Commented Feb 20, 2020 at 17:03

2 Answers 2

4

Try this:

#!/bin/bash

mysql --host=xxx --user=xxx --password=xxx db << EOF 
    DROP TABLE IF EXISTS tmp_x;
    CREATE TEMPORARY TABLE tmp_x AS SELECT * FROM x.y LIMIT 0;
    LOAD DATA INFILE 'path/xxx.csv' 
    INTO TABLE tmp_x 
    FIELDS TERMINATED BY ',' 
    ENCLOSED BY '"'
    LINES TERMINATED BY '\\n'
    IGNORE 1 ROWS;
EOF

If you really must use a variable, you'll need to play with quoting:

#!/bin/bash

qry="DROP TABLE IF EXISTS tmp_x;
    CREATE TEMPORARY TABLE tmp_x AS SELECT * FROM x.y LIMIT 0;
    LOAD DATA INFILE 'path/xxx.csv' 
    INTO TABLE tmp_x 
    FIELDS TERMINATED BY \",\" 
    ENCLOSED BY \"\\\"\"
    LINES TERMINATED BY \"\\n\"
    IGNORE 1 ROWS;"

mysql --host=xxx --user=xxx --password=xxx db << EOF 
$qry
EOF
Sign up to request clarification or add additional context in comments.

Comments

1

It can be troublesome to use double-quoted strings in your SQL, since you're using double-quotes as the string delimiter in bash. In other words, which is the double-quote that ends the bash string, and which should be treated as a literal double-quote character in the SQL?

To resolve this, use single-quotes for string delimiters in the SQL.

Another issue: There's no need to put a backslash before , for the field terminator.

Another issue: The \n needs another backslash.

Here's what I tried and it seems to work:

qry="DROP TABLE IF EXISTS tmp_x;
    CREATE TEMPORARY TABLE tmp_x AS SELECT * FROM x.y LIMIT 0;
    LOAD DATA INFILE 'path/xxx.csv'
    INTO TABLE tmp_x
    FIELDS TERMINATED BY ','
    ENCLOSED BY '\"'
    LINES TERMINATED BY '\\\n'
    IGNORE 1 ROWS;"

I only printed the query, I haven't tested running it.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.