Skip to content

Commit b997b2b

Browse files
committed
Fixes for supporting passwords with weird characters
Use URL encoding in DATABASE_URL and return mysql_options as an array (via ugly global variable), so each element in it can be separately added to the command line using `@` for expansion. Because of changing the script to bash, also reverts some of the changes in 483200a. The changed escaping of `DoctrineMigrations\\Version` passed to mysql is purely due to changing from `/bin/sh` to `/bin/bash`. Somehow passing that to the `mysql` wrapper function, it got unescaped before, even though `/bin/sh` is just a symlink to bash...
1 parent 98dc0e5 commit b997b2b

File tree

1 file changed

+37
-14
lines changed

1 file changed

+37
-14
lines changed

sql/dj_setup_database.in

Lines changed: 37 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
#!/bin/sh
1+
#!/bin/bash
22
# @configure_input@
33

44
# This script allows one to perform DOMjudge database setup actions.
@@ -52,30 +52,50 @@ not have to pass any of the options above.
5252
EOF
5353
}
5454

55+
urlencode()
56+
{
57+
# We need to escape for PHP ' and \ by prefixing them with a \.
58+
local str="${1//\\/\\\\}"
59+
str="${str//\'/\\\'}"
60+
php -r "echo rawurlencode('$str');"
61+
}
62+
63+
# This is global variable to be able to return the output from
64+
# mysql_options() below as an array, which is not possible otherwise.
65+
declare -a _mysql_options
66+
5567
mysql_options()
5668
{
69+
local user pass
70+
_mysql_options=()
71+
5772
# shellcheck disable=SC2153
5873
if [ -n "$DBUSER" ]; then
59-
_user="-u $DBUSER"
60-
else
61-
_user="${DBA_USER:+-u ${DBA_USER}}"
74+
_mysql_options+=('-u' "$DBUSER")
75+
elif [ -n "$DBA_USER" ]; then
76+
_mysql_options+=('-u' "$DBA_USER")
6277
fi
6378
# shellcheck disable=SC2153
6479
if [ -n "$PASSWD" ]; then
65-
_pass="-p$PASSWD"
66-
else
67-
[ -n "$PROMPT_PASSWD" ] && _pass="-p"
68-
[ -n "$DBA_PASSWD" ] && _pass="-p$DBA_PASSWD"
80+
_mysql_options+=("-p$PASSWD")
81+
elif [ -n "$DBA_PASSWD" ]; then
82+
_mysql_options+=("-p$DBA_PASSWD")
83+
elif [ -n "$PROMPT_PASSWD" ]; then
84+
_mysql_options+=('-p')
6985
fi
7086

71-
[ -z "$USE_SOCKET" ] && port="-P$DBPORT"
72-
echo $_user ${_pass:+"$_pass"} -h "$DBHOST" ${port:+"$port"}
87+
_mysql_options+=('-h' "$DBHOST")
88+
89+
if [ -z "$USE_SOCKET" ]; then
90+
_mysql_options+=("-P$DBPORT")
91+
fi
7392
}
7493

7594
# Wrapper around mysql command to allow setting options, user, etc.
7695
mysql()
7796
{
78-
command mysql $(mysql_options) --silent --skip-column-names "$@"
97+
mysql_options
98+
command mysql "${_mysql_options[@]}" --silent --skip-column-names "$@"
7999
}
80100

81101
# Quick shell hack to get a key from an INI file.
@@ -126,10 +146,13 @@ symfony_console()
126146
fi
127147

128148
if [ -n "$DBA_USER" ]; then
149+
user=$(urlencode "${DBA_USER}")
150+
host=$(urlencode "${domjudge_DBHOST}")
151+
db=$(urlencode "${domjudge_DBNAME}")
129152
if [ -n "$DBA_PASSWD" ]; then
130-
DATABASE_URL=mysql://${DBA_USER}:${DBA_PASSWD}@${domjudge_DBHOST}:${domjudge_DBPORT}/${domjudge_DBNAME}
153+
DATABASE_URL="mysql://$user:$(urlencode "${DBA_PASSWD}")@$host:${domjudge_DBPORT}/$db"
131154
else
132-
DATABASE_URL=mysql://${DBA_USER}@${domjudge_DBHOST}:${domjudge_DBPORT}/${domjudge_DBNAME}
155+
DATABASE_URL="mysql://$user@$host:${domjudge_DBPORT}/$db"
133156
fi
134157
fi
135158
fi
@@ -356,7 +379,7 @@ upgrade)
356379
# shellcheck disable=SC2016,SC2028
357380
echo 'INSERT INTO `doctrine_migration_versions`
358381
(version, executed_at, execution_time)
359-
SELECT concat("DoctrineMigrations\\\\Version", version), executed_at, 1
382+
SELECT concat("DoctrineMigrations\\Version", version), executed_at, 1
360383
FROM migration_versions;' | mysql "$DBNAME"
361384
echo "DROP TABLE \`migration_versions\`" | mysql "$DBNAME"
362385
fi

0 commit comments

Comments
 (0)