1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249 250 251 252 253 254 255 256 257 258 259 260 261 262 263 264 265 266 267 268 269 270 271 272 273 274 275 276 277 278 279 280 281 282 283 284 285 286 287 288 289 290 291 292 293 294 295 296 297 298 299 300 301 302 303 304 305 306 307 308 309 310 311 312 313 314 315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 375 376 377 378 379 380 381 382 383 384 385 386 387 388 389 390 391 392 393 394 395 396 397 398 399 400 401 402 403 404 405 406 407 408 409 410 411 412 413 414 415 416 417 418 419 420 421 422 423 424 425 426 427 428 429 430 431
|
#!/bin/bash
TMP_DIR=${TMP_DIR:-/tmp}
# This script controls the Percona Toolkit test environment. The basic
# environment is a master on port 12345 in ${TMP_DIR}/12345 and a slave on port
# 12346 in ${TMP_DIR}/12346. This script attempts to ensure that all environment
# vars like PERCONA_TOOLKIT_BRANCH and PERCONA_TOOLKIT_SANDBOX are correct.
# Exist 0 on success/no errors, or 1 on any warnings or errors.
err() {
for msg; do
echo "$msg" >&2
done
if [ "$DEBUG_SANDBOXES" ]; then
echo
echo "MySQL processes:" >&2
ps x | grep mysql >&2
echo
for p in 12345 12346 12347; do
echo "Sandbox $p:" >&2
if [ -d "${TMP_DIR}/$p" ]; then
ls -lh ${TMP_DIR}/$p/* >&2
echo
cat ${TMP_DIR}/$p/data/mysqld.log >&2
echo
tail -n 100 ${TMP_DIR}/$p/data/genlog >&2
else
echo "${TMP_DIR}/$p does not exist" >&2
fi
done
fi
}
usage() {
err "Usage: test-env start|stop|restart|status|checkconfig|reset|kill" \
"" \
" start Start test servers in ${TMP_DIR}/PORT" \
" stop Stop test servers and remvoe all ${TMP_DIR}/PORT" \
" kill Kill test servers (use if stop fails)" \
" restart Stop and start test servers" \
" status Print status of test servers" \
" checkconfig Check test env and test servers" \
" reset Reset test server binary logs" \
" version Print MySQL version of running test servers" \
""
}
mysql_basedir_ok() {
local basedir=$1
if [ ! -d "$basedir" ] || [ ! -d "$basedir/bin" ]; then
return 0
fi
if [ ! -x "$basedir/bin/mysqld_safe" ]; then
return 0
fi
return 1 # basedir is ok
}
set_mysql_basedir() {
if [ -x "$PERCONA_TOOLKIT_SANDBOX/bin/mysqld" ]; then
mysqld="$PERCONA_TOOLKIT_SANDBOX/bin/mysqld"
elif [ -x "$PERCONA_TOOLKIT_SANDBOX/sbin/mysqld" ]; then
mysqld="$PERCONA_TOOLKIT_SANDBOX/sbin/mysqld"
elif [ -x "$PERCONA_TOOLKIT_SANDBOX/libexec/mysqld" ]; then
mysqld="$PERCONA_TOOLKIT_SANDBOX/libexec/mysqld"
else
err "Cannot find executable mysqld in $PERCONA_TOOLKIT_SANDBOX/bin, $PERCONA_TOOLKIT_SANDBOX/sbin or $PERCONA_TOOLKIT_SANDBOX/libexec."
return 0
fi
mysql_basedir_ok $PERCONA_TOOLKIT_SANDBOX
local basedir_ok=$?
if [ $basedir_ok -eq 1 ]; then
export PERCONA_TOOLKIT_SANDBOX=$PERCONA_TOOLKIT_SANDBOX
fi
return $basedir_ok
}
checkconfig() {
local print_conf=$1
local stat=""
conf_err=0
if [ -z "$PERCONA_TOOLKIT_BRANCH" ] || [ ! -d "$PERCONA_TOOLKIT_BRANCH" ]; then
conf_err=1
stat="INVALID"
else
stat="ok"
fi
if [ $print_conf ]; then
echo "PERCONA_TOOLKIT_BRANCH=$PERCONA_TOOLKIT_BRANCH - $stat"
fi
set_mysql_basedir
if [ $? -ne 1 ]; then
conf_err=1
stat="INVALID"
else
stat="ok"
fi
if [ $print_conf ]; then
echo -n "PERCONA_TOOLKIT_SANDBOX=$PERCONA_TOOLKIT_SANDBOX - $stat"
if [ -n "$BASEDIR_AUTO_DETECTED" ]; then
echo " (auto-detected)"
else
echo
fi
fi
return $conf_err
}
sandbox_status() {
local type=$1
local port=$2
local master_port=$3
local status=0 # sandbox is ok, no problems
echo "MySQL $type test server on port $port:"
echo -n " PID file exists - "
if [ -f "${TMP_DIR}/$port/data/mysql_sandbox$port.pid" ]; then
echo "yes"
echo -n " PID file has a PID - "
local pid=`cat ${TMP_DIR}/$port/data/mysql_sandbox$port.pid 2>/dev/null`
if [ -n "$pid" ]; then
echo "yes"
echo -n " process $pid is alive - "
kill -0 $pid >/dev/null 2>&1
if [ $? -eq 0 ]; then
echo "yes"
else
echo "NO"
status=1
fi
else
echo "NO"
status=1
fi
else
echo "NO"
status=1
fi
echo -n " MySQL is alive - "
$PERCONA_TOOLKIT_SANDBOX/bin/mysqladmin --defaults-file="${TMP_DIR}/$port/my.sandbox.cnf" ping >/dev/null 2>&1
if [ $? -eq 0 ]; then
echo "yes"
if [ "$MYSQL_VERSION" '>' "4.1" ]; then
echo -n " sakila db is loaded - "
${TMP_DIR}/$port/use -e 'show databases like "sakila"' 2>/dev/null | grep sakila >/dev/null 2>&1
if [ $? -eq 0 ]; then
echo "yes"
else
echo "NO"
status=1
fi
fi
if [ "$type" = "slave" ]; then
echo -n " slave is running - "
# Slave status should show:
# Slave_IO_Running: Yes
# Slave_SQL_Running: Yes
local slave_running=`${TMP_DIR}/$port/use -e 'show slave status\G' 2>/dev/null | grep Running | grep -c Yes`
if [ $slave_running -eq 2 ]; then
echo "yes"
else
echo "NO"
status=1
fi
if [ -n "$master_port" ]; then
echo -n " slave to master $master_port - "
local mp=`${TMP_DIR}/$port/use -e 'show slave status\G' 2>/dev/null | grep Master_Port | awk '{print $2}'`
if [ "$mp" = "$master_port" ]; then
echo "yes"
else
echo "NO"
status=1
fi
fi
fi
else
echo "NO"
status=1
fi
return $status
}
sandbox_is_running() {
local p=$1
ps xw | grep mysqld | grep -v grep | grep ${TMP_DIR}/$p >/dev/null
}
kill_sandbox() {
local p=$1
# See if the sandbox server is running.
sandbox_is_running $p
if [ $? -eq 0 ]; then
# Try to kill it with mysqladmin shutdown. We try different
# user/pass because sometimes a test can bork acct privs.
mysqladmin -h127.1 -P$p -umsandbox -pmsandbox shutdown >/dev/null 2>&1
mysqladmin -h127.1 -P$p -uroot -pmsandbox shutdown >/dev/null 2>&1
mysqladmin -h127.1 -P$p -uroot shutdown >/dev/null 2>&1
sleep 2
# See if the sandbox server is still running.
sandbox_is_running $p
if [ $? -eq 0 ]; then
# Kill both mysqld_safe and mysqld.
pid1=`ps xw | grep -v grep | grep mysqld_safe | grep ${TMP_DIR}/$p | awk '{print $1}'`
pid2=`ps xw | grep -v grep | grep -v mysqld_safe | grep mysqld | grep ${TMP_DIR}/$p | awk '{print $1}'`
[ "$pid1" ] && kill -9 $pid1 # Die, damn you, die!
[ "$pid2" ] && kill -9 $pid2
sleep 2
# Third and finaly check if the sandbox server is running.
sandbox_is_running $p
if [ $? -eq 0 ]; then
err "Failed to kill MySQL test server on port $p (PID $pid1, $pid2)"
return 1
else
echo "Killed MySQL test server on port $p (PID $pid1, $pid2)"
fi
else
echo "Killed MySQL test server on port $p"
fi
fi
if [ -d "${TMP_DIR}/$p" ]; then
rm -rf ${TMP_DIR}/$p
echo "Removed ${TMP_DIR}/$p"
fi
return 0
}
MYSQL_VERSION=""
set_mysql_version() {
if [ -d ${TMP_DIR}/12345 ] && [ -f ${TMP_DIR}/12345/use ]; then
MYSQL_VERSION=$(${TMP_DIR}/12345/use -ss -e "SELECT VERSION()" \
| cut -d'.' -f1,2)
fi
}
_seq() {
local i="$1"
awk "BEGIN { for(i=1; i<=$i; i++) print i; }"
}
# ###########################################################################
# Sanity check the cmd line options.
# ###########################################################################
if [ $# -lt 1 ]; then
usage
exit 1
fi
opt=$1
# ###########################################################################
# Process the option.
# ###########################################################################
exit_status=0
if [ -e ${PERCONA_TOOLKIT_SANDBOX}/lib/mysql/libjemalloc.so ]; then
export LD_PRELOAD=${PERCONA_TOOLKIT_SANDBOX}/lib/mysql/libjemalloc.so
fi
if [ $opt = 'checkconfig' ]; then
checkconfig 1
echo -n "Percona Toolkit test environment config is "
if [ $conf_err -eq 0 ]; then
echo "ok!"
exit 0
else
echo "invalid."
exit 1
fi
else
checkconfig
if [ $conf_err -eq 1 ]; then
err "The Percona Toolkit test environment config is invalid." \
"Run '$0 checkconfig' to see the current configuration."
exit 1
fi
fi
case $opt in
start)
cd $PERCONA_TOOLKIT_BRANCH/sandbox
./start-sandbox "${2:-"master"}" 12345
exit_status=$((exit_status | $?))
set_mysql_version
if [ $exit_status -eq 0 ]; then
if [ "${2:-""}" = "channels" ] && [ "$MYSQL_VERSION" '>' "5.6" ]; then
./start-sandbox master 12346
exit_status=$((exit_status | $?))
./start-sandbox master 12347
exit_status=$((exit_status | $?))
${TMP_DIR}/12345/use < $PERCONA_TOOLKIT_BRANCH/sandbox/gtid_on.sql
exit_status=$?
${TMP_DIR}/12346/use < $PERCONA_TOOLKIT_BRANCH/sandbox/gtid_on.sql
exit_status=$?
${TMP_DIR}/12347/use < $PERCONA_TOOLKIT_BRANCH/sandbox/slave_channels.sql
exit_status=$?
else
./start-sandbox "${2:-"slave"}" 12346 12345
exit_status=$((exit_status | $?))
./start-sandbox "${2:-"slave"}" 12347 12346
exit_status=$((exit_status | $?))
fi
if [ "${2:-""}" = "cluster" ]; then
# Bit of magic here. 'start-sandbox cluster new_node old_node'
# changes old_node's my.sandbox.cnf's wsrep_cluster_address to
# point to new_node. This is especially useful because otherwise,
# calling stop/start like below on 12345 would create a new cluster.
${TMP_DIR}/12345/stop >/dev/null
${TMP_DIR}/12345/start >/dev/null
echo -n "Checking that the cluster size is correct... "
size=$(${TMP_DIR}/12345/use -ss -e "SHOW STATUS LIKE 'wsrep_cluster_size'" | awk '{print $2}')
if [ ${size:-0} -ne 3 ]; then
echo "FAILED"
else
echo "OK"
fi
fi
if [ $? -eq 0 ]; then
SAKILA=${SAKILA:-1}
if [ $SAKILA -eq 1 ]; then
echo -n "Loading sakila database... "
./load-sakila-db 12345 "${2:-""}"
exit_status=$((exit_status | $?))
if [ $exit_status -ne 0 ]; then
echo "FAILED"
else
echo "OK"
fi
fi
# Create percona_test db and checksum all the tables.
../util/checksum-test-dataset
# LOAD DATA is disabled or broken on some boxes.
# PerconaTest exports $can_load_data which is true
# if percona_test.load_data has a row with 1,
# signaling that LOAD DATA LOCAL INFILE worked.
../util/check-load-data
ping=$(${TMP_DIR}/12345/use -ss -e "SELECT MD5(RAND())")
${TMP_DIR}/12345/use -e "SET AUTOCOMMIT=1; REPLACE INTO percona_test.sentinel (id, ping) VALUES (1, '$ping')";
echo -n "Waiting for replication to finish..."
for i in $(_seq 60); do
pong=$(${TMP_DIR}/12347/use -ss -e "SELECT ping FROM percona_test.sentinel WHERE id=1 AND ping='$ping'" 2>/dev/null)
[ "$ping" = "$pong" ] && break
echo -n '.'
sleep 1
done
if [ "$ping" = "$pong" ]; then
echo " OK"
else
echo " FAILED"
exit_status=$((exit_status | 1))
fi
fi
fi
if [ $exit_status -eq 0 ]; then
echo "Percona Toolkit test environment started with MySQL v$MYSQL_VERSION."
else
DEBUG_SANDBOXES=1
err "There was an error starting the Percona Toolkit test environment."
fi
;;
stop)
cd $PERCONA_TOOLKIT_BRANCH/sandbox
./stop-sandbox 12349 12348 12347 12346 12345
exit_status=$((exit_status | $?))
./stop-sandbox 2903 2902 2901 2900
exit_status=$((exit_status | $?))
if [ $exit_status -eq 0 ]; then
echo "Percona Toolkit test environment stopped."
else
DEBUG_SANDBOXES=1
err "Error stopping the Percona Toolkit test environment."
fi
;;
kill)
# This is a blunt approach for killing the entire test env
# when a polite stop fails. It uses kill -9 as a last resort.
for port in 12349 12348 12347 12346 12345 2903 2902 2901 2900; do
kill_sandbox $port
exit_status=$((exit_status | $?))
done
;;
restart)
shift;
$0 stop "$@"
$0 start "$@"
;;
status)
sandbox_status 'master' '12345'
master_status=$?
sandbox_status 'slave' '12346' '12345'
slave_status=$?
echo -n "Percona Test test environment is "
if [ $master_status -eq 0 ] && [ $slave_status -eq 0 ]; then
echo "ok!"
else
echo "invalid."
exit_status=1
fi
;;
version)
set_mysql_version
echo $MYSQL_VERSION
;;
*)
usage
exit_status=1
;;
esac
exit $exit_status
|