]> git.pld-linux.org Git - packages/mysql.git/blob - mysql.init
- fixed bullshit about changing password for mysql_sysadmin
[packages/mysql.git] / mysql.init
1 #!/bin/sh
2 #
3 # mysql         A very fast and reliable SQL database engine
4 #
5 # chkconfig:    2345 84 25
6 #
7 # description:  A very fast and reliable SQL database engine.
8 #
9 # $Id$
10
11 # Source function library
12 . /etc/rc.d/init.d/functions
13
14 # Get network config
15 . /etc/sysconfig/network
16
17 # Get service config
18 if [ -f /etc/sysconfig/mysql ]; then
19         . /etc/sysconfig/mysql
20 else
21         nls "Error: %s not found" /etc/sysconfig/mysql
22         nls "%s can't be run." MySQL
23         exit 1
24 fi
25
26 if [ -n "$MYSQL_DB_CLUSTERS" ]; then
27         nls "Warning: MYSQL_DB_CLUSTERS is set. It's obsolete. Use %s instead." /etc/mysql/clusters.conf
28 fi
29
30 if [ -f /etc/mysql/clusters.conf ]; then
31         MYSQL_DB_CLUSTERS=$(awk -F= '!/^#/{print $2}' /etc/mysql/clusters.conf)
32         if [ -z "$MYSQL_DB_CLUSTERS"  ]; then
33                 nls "Warning: there are no configured clusters."
34         fi
35
36 else
37         nls "Warning: Missing clusters config file %s" /etc/mysql/clusters.conf
38         if [ -z "$MYSQL_DB_CLUSTERS"  ]; then
39                 nls "Warning: there are no configured clusters."
40                 nls "Using default cluster /var/lib/mysql (compatibility mode)"
41                 MYSQL_DB_CLUSTERS=/var/lib/mysql
42         fi
43 fi
44
45
46 # Check that networking is up
47 if is_yes "${NETWORKING}"; then
48         if [ ! -f /var/lock/subsys/network -a "$1" != stop -a "$1" != status -a "$1" != init ]; then
49                 msg_network_down MySQL
50                 exit 1
51         fi
52 else
53         exit 0
54 fi
55
56 action="$1"
57
58 # any db cluster as command line argument?
59 if [ $# -gt 1 ]; then
60         shift
61         # perform action for specified clusters only
62         for a in "$@"; do
63                 # try auto resolving from /etc/mysql/clusters.conf
64                 if [[ "$a" != /* ]]; then
65                         m=$(awk -va="$a" -F= 'substr($0, 1, length(a)) == a {print $1}' /etc/mysql/clusters.conf)
66                         if [ -z "$m" ]; then
67                                 echo >&2 "Cluster name '$a' did not match anything!"
68                                 exit 1
69                         fi
70                         if [ $(echo "$m" | wc -l) -gt 1 ]; then
71                                 echo >&2 "Cluster name '$a' ambiguous:" $m
72                                 exit 1
73                         fi
74                         a=$(awk -va="$a" -F= 'substr($0, 1, length(a)) == a {print $2}' /etc/mysql/clusters.conf)
75                 fi
76                 DB_CLUSTERS="$DB_CLUSTERS $a"
77         done
78 else
79         DB_CLUSTERS="$MYSQL_DB_CLUSTERS"
80 fi
81
82 MYSQL_ERRLOG=/var/log/mysql/err
83 MYSQL_START_WAIT_TIME=${MYSQL_START_WAIT_TIME:-15}
84 MYSQL_STOP_WAIT_TIME=${MYSQL_STOP_WAIT_TIME:-900}
85
86 #
87 # Useful functions.
88 #
89
90 #
91 # check for mysql status
92 #
93 # arguments:
94 # $1 - db cluster
95 # $2 - start|stop
96 #
97 # sets variables:
98 # MYSQL_STATUS = starting | running | not running | died
99 # MYSQL_PID    = pid of mysqld process
100 #
101 mysqlstatus() {
102         clusterdir="$1"
103         mode="$2"
104         
105         mysqlgetconfig "$clusterdir"
106
107         MYSQL_STATUS="not running"
108         MYSQL_PID="unknown"
109         MYSQL_PIDFILE_PID=""
110         MYSQL_GREP_PID=""
111
112         if [ -f "$MYSQL_PIDFILE" ]; then
113                 MYSQL_PIDFILE_PID=$(cat "$MYSQL_PIDFILE")
114         fi
115         
116         if [ -n "$MYSQL_PIDFILE_PID" ]; then
117                 MYSQL_PID=$MYSQL_PIDFILE_PID
118                 if [ ! -d "/proc/$MYSQL_PID" ]; then
119                         MYSQL_STATUS="died"
120                         return
121                 elif (grep -qa "$MYSQL_PIDFILE" /proc/$MYSQL_PID/cmdline 2> /dev/null); then
122                         MYSQL_STATUS="running"
123                         return
124                 fi
125         fi
126
127         if [ "$mode" = "start" ]; then
128                 MYSQL_GREP_PID=$(grep -lE "^/usr/sbin/mysqld.*${MYSQL_PIDFILE}" /proc/[0-9]*/cmdline 2> /dev/null | awk -F "/" '{ print $3; exit; }')
129                 if [ -n "$MYSQL_GREP_PID" ]; then
130                         MYSQL_PID=$MYSQL_GREP_PID
131                         if grep -qa "$MYSQL_PIDFILE" /proc/$MYSQL_PID/cmdline 2> /dev/null; then
132                                 if [ -f "$MYSQL_PIDFILE" ]; then
133                                         MYSQL_PIDFILE_PID=$(cat "$MYSQL_PIDFILE")
134                                 fi
135                                 if [ -n "$MYSQL_PIDFILE_PID" ]; then
136                                         MYSQL_PID=$MYSQL_PIDFILE_PID
137                                         MYSQL_STATUS="running"
138                                         return
139                                 else
140                                         MYSQL_STATUS="starting"
141                                         return
142                                 fi
143                         fi
144                 fi
145         fi
146
147         # else default, "not running"
148 }
149
150 # get mysql configuration in variables
151 # MYSQL_CONFIG MYSQL_DATA_DIR MYSQL_USER MYSQL_PIDFILE
152 #
153 # arguments
154 # $1 - db cluster
155
156 mysqlgetconfig() {
157         clusterdir="$1"
158
159         # emulate old behaviour if only one cluster specified
160         if [ "$clusterdir" = "$MYSQL_DB_CLUSTERS" -a "$clusterdir" = "/var/lib/mysql" -a -f /etc/mysqld.conf ]; then
161                 MYSQL_RA_COMPAT=yes
162                 config_file=/etc/mysqld.conf
163         else
164                 config=$(awk -F= -vclusterdir="$clusterdir" '!/^#/{ if (clusterdir == $2) print $1}' /etc/mysql/clusters.conf)
165                 if [[ $config = /* ]]; then
166                         config_file="$config"
167                 elif [ -f "/etc/mysql/$config" ]; then
168                         config_file="/etc/mysql/$config"
169                 else
170                         config_file="$clusterdir/mysqld.conf"
171                 fi
172         fi
173
174         MYSQL_CLUSTER_DIR="$clusterdir"
175
176         if [ -z "$config_file" ]; then
177                 nls "Error: Can't find config file for %s cluster" "$clusterdir"
178                 exit 6
179         else
180                 MYSQL_CONFIG="$config_file"
181         fi
182
183         if [ ! -f "$config_file" ]; then
184                 nls "Error: config file %s not found" "$config_file"
185                 nls "MySQL can't be run. Did you initialize DB by doing \`$0 init'?"
186                 exit 6
187         fi
188
189         eval `awk '
190 /^[ \t]*\[.*\][ \t]*$/ {
191         match($0,/\[.*\]/)
192         section=substr($0, RSTART + 1, RSTART + RLENGTH - 3)
193 }
194 section == "mysqld" && $2 ~ "=" {
195         if ($1 == "datadir") {
196                 printf("MYSQL_DATA_DIR=%s;", $3)
197         } else if ($1 == "user") {
198                 printf("MYSQL_USER=%s;", $3)
199         } else if ($1 == "pid-file") {
200                 printf("MYSQL_PIDFILE=%s;", $3)
201         } else if ($1 == "socket") {
202                 printf("MYSQL_SOCKET=%s;", $3)
203         }
204 }
205 ' $config_file`
206
207
208         if is_yes "$MYSQL_RA_COMPAT"; then
209                 MYSQL_DATA_DIR_SUB=""
210         else
211                 MYSQL_DATA_DIR_SUB="/mysqldb"
212         fi
213
214         if [ -z "$MYSQL_DATA_DIR" -o "$MYSQL_DATA_DIR" != "${clusterdir}${MYSQL_DATA_DIR_SUB}/db" ]; then
215                 nls "Error: datadir specified in %s should be %s" "$config_file" "$clusterdir${MYSQL_DATA_DIR_SUB}/db"
216                 nls " MySQL can't be run."
217                 exit 6
218         fi
219
220         if [ -z "$MYSQL_PIDFILE" -o "$MYSQL_PIDFILE" != "$clusterdir${MYSQL_DATA_DIR_SUB}/mysql.pid" ]; then
221                 nls "Error: pid-file specified in %s should be %s" "$config_file" "$clusterdir${MYSQL_DATA_DIR_SUB}/mysql.pid"
222                 nls " MySQL can't be run."
223                 exit 6
224         fi
225
226         if [ -z $MYSQL_USER ]; then
227                 echo "$(nls 'MySQL user not configured properly')"'!' >&2
228                 nls "Edit %s and configure it." "$config_file" >&2
229                 exit 6
230         fi
231 }
232
233 # start mysql
234 mysqlstart() {
235         clusterdir="$1"
236         mysqlgetconfig "$clusterdir"
237         if [ ! -d "$MYSQL_DATA_DIR/mysql" ]; then
238                 nls "MySQL cluster %s not initialized." "$clusterdir"
239                 nls "Try \`%s init %s' before start." "$0" "$clusterdir"
240                 exit 6
241         fi
242
243         msg_starting "MySQL $clusterdir"
244         busy
245         [ -z "$DEFAULT_SERVICE_RUN_NICE_LEVEL" ] && DEFAULT_SERVICE_RUN_NICE_LEVEL=0
246         rm -f "$MYSQL_PIDFILE"
247
248         TMPDIR=/tmp nice -n ${SERVICE_RUN_NICE_LEVEL:-$DEFAULT_SERVICE_RUN_NICE_LEVEL} \
249                 /usr/bin/setsid /usr/sbin/mysqld \
250                         --defaults-file=$MYSQL_CONFIG \
251                         --datadir=$MYSQL_DATA_DIR \
252                         --pid-file=$MYSQL_PIDFILE $MYSQL_OPTIONS \
253                 >> $MYSQL_ERRLOG 2>&1 &
254         pid=$!
255
256         sleep 0.1
257         mysqlstatus "$clusterdir" start
258         # it takes longer for mysqld to start and create pidfile if it has to recover innodb transactions
259         if [ "$MYSQL_STATUS" = "starting" ]; then
260                 echo ""
261                 show "Waiting for MySQL to start"
262                 busy
263
264                 # while the pid is running, mysql is starting up
265                 # if the pidfile was created, it started up successfully
266                 # if either case fails we break and report status
267                 while true; do
268                         [ -d /proc/$pid ] || break
269                         [ -f "$MYSQL_PIDFILE" ] && break
270                         sleep 0.2
271                 done
272         fi
273
274         mysqlstatus "$clusterdir" start
275         if [ "$MYSQL_STATUS" = "running" -a "$MYSQL_PID" != "unknown" ]; then
276                 ok
277         elif [ "$MYSQL_STATUS" = "died" ]; then
278                 RETVAL=1
279                 died
280         else
281                 RETVAL=1
282                 fail
283         fi
284 }
285
286 # stop mysql
287 mysqlstop() {
288         clusterdir="$1"
289         mysqlstatus "$clusterdir" stop
290         msg_stopping "MySQL $clusterdir"
291         busy
292
293         # try graceful shutdown -- send shutdown command
294         # requires mysql_sysadmin user proper privs
295         /usr/bin/mysqladmin --defaults-file=$MYSQL_CONFIG ${MYSQL_SOCKET:+--socket=$MYSQL_SOCKET} shutdown >/dev/null 2>&1
296         mysqlstatus "$clusterdir" stop
297
298         if [ "$MYSQL_PID" != "unknown" ]; then
299                 kill -TERM "$MYSQL_PID" 2> /dev/null
300                 for nr in $(seq 1 $(($MYSQL_STOP_WAIT_TIME*10))); do
301                         [ -d "/proc/$MYSQL_PID" ] || break
302                         sleep 0.1
303                 done
304         fi
305         
306         mysqlstatus "$clusterdir" stop
307         if [ "$MYSQL_STATUS" = "died" ]; then
308                 died
309         elif [ "$MYSQL_STATUS" = "running" -o "$MYSQL_STATUS" = "starting" ]; then
310                 fail
311         else
312                 ok
313         fi
314 }
315
316 #
317 # check for running mysql instances; if any instance is running then
318 # create subsys lock file
319 #
320 mysqlsubsys() {
321         # check for every defined db cluster in sysconfig file
322         for mysqldir in $DB_CLUSTERS; do
323                 mysqlstatus "$mysqldir"
324                 if [ "$MYSQL_STATUS" = "running" ]; then
325                         touch /var/lock/subsys/mysql
326                         return
327                 fi
328         done
329         rm -f /var/lock/subsys/mysql
330 }
331
332 mysqlinit() {
333         clusterdir="$1"
334
335         if [ -f /etc/mysqld.conf ]; then
336                 nls "Running in \`no cluster compat' mode: can't initialize database."
337                 nls "Move /etc/mysqld.conf away and rerun \`$0 init' (new config will be in $clusterdir)."
338                 exit 1
339         fi
340
341         if [ -f "$clusterdir/mysqld.conf" ]; then
342                 mysqlgetconfig "$clusterdir"
343         else
344                 MYSQL_USER="mysql"
345                 MYSQL_CLUSTER_DIR="$clusterdir"
346                 MYSQL_DATA_DIR="$clusterdir/mysqldb/db"
347                 MYSQL_PIDFILE="$clusterdir/mysqldb/mysql.pid"
348                 MYSQL_SOCKET="$clusterdir/mysqldb/mysql.sock"
349
350                 # this $MYSQL_CONFIG will be created later
351                 MYSQL_CONFIG="$MYSQL_CLUSTER_DIR/mysqld.conf"
352         fi
353
354         show "Initializing cluster %s" "$clusterdir"; echo
355
356         # Check if not exist init database
357         if [ -d "$MYSQL_DATA_DIR/mysql" ]; then
358                 nls "Seems that database is initialized now. Remove by hand %s" "$MYSQL_DATA_DIR/mysql"
359                 nls "before initializing database."
360                 nls "For now skipping cluster %s." "$clusterdir"
361                 return
362         fi
363
364         show "Creating privilege mysql tables for $MYSQL_DATA_DIR"
365         busy
366         TMP=/tmp TMPDIR=/tmp
367
368         # Install this in the user table, too
369         hostname="`hostname --fqdn 2> /dev/null | tr -d '[:space:]'`"
370         [ "$hostname" = "localhost" -o -z "$hostname" ] && hostname="`hostname 2> /dev/null | tr -d '[:space:]'`"
371         [ -z "$hostname" ] && hostname="localhost-unknown"
372
373         # Check if hostname is valid
374         if [ -z "$hostname" ]; then
375                 deltext
376                 fail
377                 nls "Sorry, the host name is not configured."
378                 nls "Please configure the 'hostname' command to return a hostname."
379                 exit 1
380         elif ! hostname -i >/dev/null 2>&1; then
381                 deltext
382                 fail
383                 nls "Sorry, the host '%s' could not be looked up." "$hostname"
384                 nls "Please configure the 'hostname' command to return a correct hostname."
385                 exit 1
386         fi
387
388         mkdir -p "$MYSQL_DATA_DIR" > /dev/null 2>&1
389         # Using mysql:mysql for MYSQL_CLUSTER_DIR is creating SECURITY hole, root:root is proper
390         chown root:root "$MYSQL_CLUSTER_DIR"
391     chown mysql:mysql "$MYSQL_CLUSTER_DIR/mysqldb" "$MYSQL_DATA_DIR" > /dev/null 2>&1
392         chmod 751 "$MYSQL_CLUSTER_DIR" "$MYSQL_CLUSTER_DIR/mysqldb"
393
394         if [ -f /usr/share/mysql/mysqld.conf -a ! -f "$MYSQL_CLUSTER_DIR/mysqld.conf" ]; then
395             sed -e "
396                 s#\(datadir.*\)=.*#\1= $MYSQL_DATA_DIR#g;
397                 s#\(pid-file.*\)=.*#\1= $MYSQL_PIDFILE#g;
398                 s#\(socket.*\)=.*#\1= $MYSQL_SOCKET#g;
399                 s#@clusterdir@#$MYSQL_CLUSTER_DIR#g;
400                 " /usr/share/mysql/mysqld.conf > "$MYSQL_CLUSTER_DIR/mysqld.conf"
401             chown root:root "$MYSQL_CLUSTER_DIR/mysqld.conf"
402             chmod 640 "$MYSQL_CLUSTER_DIR/mysqld.conf"
403         fi
404
405         if [ ! -e /var/lib/mysql/mysql.sock ] || [ -L /var/lib/mysql/mysql.sock ] && [ -z "$(readlink /var/lib/mysql/mysql.sock)" ]; then
406                 sock=${MYSQL_SOCKET#/var/lib/mysql/} # make it relative if possible
407             ln -s "$sock" /var/lib/mysql/mysql.sock
408         fi
409
410         cat > $MYSQL_DATA_DIR/mysql-init.sql <<-EOF
411                 CREATE DATABASE mysql;
412                 use mysql;
413                 $(cat /usr/share/mysql/mysql_system_tables.sql)
414                 $(sed -e "s,@@hostname,'$hostname',g" /usr/share/mysql/mysql_system_tables_data.sql)
415 EOF
416
417         ok=0
418         /usr/sbin/mysqld --bootstrap --skip-grant-tables \
419                 --datadir=$MYSQL_DATA_DIR --user=$MYSQL_USER \
420                 --slave-load-tmpdir=$MYSQL_DATA_DIR --tmpdir=$MYSQL_DATA_DIR < \
421                 $MYSQL_DATA_DIR/mysql-init.sql 2>> /var/log/mysql/err && ok=1
422         [ -f $MYSQL_DATA_DIR/mysql/host.frm ] || ok=0
423
424         if [ "$ok" = 1 ]; then
425                 rm -f $MYSQL_DATA_DIR/mysql-init.sql
426             ok
427         cat << END_OF_MSG
428
429 PLEASE REMEMBER TO SET A PASSWORD FOR THE MySQL USERS!
430 This is done (after starting database; press enter when asked for password) with:
431
432 mysqladmin -u mysql -S $MYSQL_SOCKET password 'password'
433 mysqladmin -h $hostname -u mysql -S $MYSQL_SOCKET password 'password'
434 echo "set password=password('newpassword');" | mysql -u mysql_sysadmin -S $MYSQL_SOCKET
435
436 NOTE: mysql_sysadmin password should be placed to $MYSQL_CONFIG in
437 mysqladmin section. See the manual for more instructions.
438 (This user is used at logs rotation and server shutdown)
439
440 If you want to use new help tables in MySQL 4.1.x then you'll need to import the help data:
441 mysql -u mysql -p -S $MYSQL_SOCKET mysql < /usr/share/mysql/fill_help_tables.sql
442
443 END_OF_MSG
444       else
445             fail
446             cat << END_OF_MSG
447 Installation of grant tables FAILED!
448
449 The initialization SQL script was preserved at $MYSQL_DATA_DIR/mysql-init.sql
450
451 Examine the logs in /var/log/mysql for more information.  You can
452 also try to start the mysqld daemon with:
453
454 /usr/sbin/mysqld --skip-grant &
455
456 You can use the command line tool mysql to connect to the mysql
457 database and look at the grant tables:
458
459 shell> mysql -u mysql mysql
460 mysql> show tables
461
462 Try 'mysqld --help' if you have problems with paths. Setting on
463 logging in /etc/mysqld.conf gives you a log in /var/log/mysql/log that
464 may be helpful. The latest information about MySQL is available on the
465 web at http://www.mysql.com/.
466
467 Please check PLD Linux ftp site for newer versions of this package.
468
469 Please consult the MySQL manual section: 'Problems running
470 mysql_install_db', and the manual section that describes problems on
471 your OS.  Another information source is the MySQL email archive.
472 Please check all of the above before mailing us!  And if you do mail
473 us, you MUST use the mysqlbug script!
474
475 END_OF_MSG
476
477         exit 1
478         fi
479 }
480
481 #
482 # End of useful functions.
483 #
484
485 start() {
486         if [ ! -f $MYSQL_ERRLOG ]; then
487                 touch $MYSQL_ERRLOG
488         fi
489         chown mysql:mysql $MYSQL_ERRLOG
490         chmod 640 $MYSQL_ERRLOG
491
492         for mysqldir in $DB_CLUSTERS; do
493                 mysqlstatus "$mysqldir" start
494                 if [ "$MYSQL_STATUS" = "running" ]; then
495                         msg_already_running "MySQL $mysqldir"
496                 else
497                         mysqlstart "$mysqldir"
498                 fi
499         done
500         mysqlsubsys
501 }
502
503 stop() {
504         for mysqldir in $DB_CLUSTERS; do
505                 mysqlstatus "$mysqldir" stop
506                 if [ "$MYSQL_STATUS" = "not running" ]; then
507                         msg_not_running "MySQL $mysqldir"
508                 else
509                         mysqlstop "$mysqldir"
510                 fi
511         done
512         mysqlsubsys
513 }
514
515 RETVAL=0
516 case "$action" in
517   start)
518         start
519         ;;
520   stop)
521         stop
522         ;;
523   status)
524         for mysqldir in $DB_CLUSTERS; do
525                 mysqlstatus "$mysqldir"
526                 if [ "$MYSQL_STATUS" = "running" ]; then
527                         show "MySQL cluster %s, PID %s" "$mysqldir" "$MYSQL_PID"
528                         pids="$pids/$MYSQL_PID/"
529                         progress "$MYSQL_STATUS"
530                 else
531                         show "MySQL cluster %s" "$mysqldir"
532                         progress "$MYSQL_STATUS" "$CFAIL"
533                 fi
534                 echo
535         done
536
537         for pid in $(/sbin/pidof mysqld); do
538                 if [[ $pids != */$pid/* ]]; then
539                         running="$running $pid"
540                 fi
541         done
542
543         if [ $# -gt 1 -a "$running" ]; then
544                 nls "Warning: MySQL Daemon processes not under clusters.conf control:"
545                 # see if we can display their status
546                 for pid in $running; do
547                         datadir=$(cat /proc/$pid/cmdline | tr '\0' '\n' | fgrep -- --datadir=)
548                         datadir=${datadir#--datadir=} # strip --datadir
549                         mysqldir=${datadir%/mysqldb/db} # strip /mysqldb/db
550                         mysqlstatus "$mysqldir"
551                         if [ "$MYSQL_STATUS" = "running" ]; then
552                                 show "MySQL cluster %s, PID %s" "$mysqldir" "$pid"
553                                 progress "$MYSQL_STATUS"
554                         else
555                                 show "MySQL cluster %s" "$mysqldir"
556                                 progress "$MYSQL_STATUS" "$CFAIL"
557                         fi
558                         echo
559                 done
560         fi
561         ;;
562   restart|force-reload)
563         stop
564         start
565         ;;
566   init)
567         for mysqldir in $DB_CLUSTERS; do
568                 mysqlinit "$mysqldir"
569         done
570         exit $?
571         ;;
572   flush-logs)
573         for mysqldir in $DB_CLUSTERS; do
574             mysqlgetconfig "$mysqldir"
575                 # just if mysqld is really running
576                 if /usr/bin/mysqladmin --defaults-file="$MYSQL_CONFIG" --socket="$MYSQL_SOCKET" ping >/dev/null 2>&1; then
577                         /usr/bin/mysqladmin --defaults-file="$MYSQL_CONFIG" --socket="$MYSQL_SOCKET" flush-logs
578                 fi
579         done
580         ;;
581   *)
582         msg_usage "$0 {start|stop|init|restart|force-reload|status}"
583         exit 3
584 esac
585
586 exit $RETVAL
This page took 0.06559 seconds and 4 git commands to generate.