zkServer.sh 12 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312
  1. #! /usr/bin/env bash
  2. #
  3. # Licensed to the Apache Software Foundation (ASF) under one
  4. # or more contributor license agreements. See the NOTICE file
  5. # distributed with this work for additional information
  6. # regarding copyright ownership. The ASF licenses this file
  7. # to you under the Apache License, Version 2.0 (the
  8. # "License"); you may not use this file except in compliance
  9. # with the License. You may obtain a copy of the License at
  10. #
  11. # https://www.apache.org/licenses/LICENSE-2.0
  12. #
  13. # Unless required by applicable law or agreed to in writing,
  14. # software distributed under the License is distributed on an
  15. # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
  16. # KIND, either express or implied. See the License for the
  17. # specific language governing permissions and limitations
  18. # under the License.
  19. #
  20. #
  21. # If this scripted is run out of /usr/bin or some other system bin directory
  22. # it should be linked to and not copied. Things like java jar files are found
  23. # relative to the canonical path of this script.
  24. #
  25. # use POSIX interface, symlink is followed automatically
  26. ZOOBIN="${BASH_SOURCE-$0}"
  27. ZOOBIN="$(dirname "$ZOOBIN")"
  28. ZOOBINDIR="$(cd "$ZOOBIN" && pwd)"
  29. if [[ -e "$ZOOBIN/../libexec/zkEnv.sh" ]]; then
  30. # shellcheck source=bin/zkEnv.sh
  31. . "$ZOOBINDIR"/../libexec/zkEnv.sh
  32. else
  33. # shellcheck source=bin/zkEnv.sh
  34. . "$ZOOBINDIR"/zkEnv.sh
  35. fi
  36. # See the following page for extensive details on setting
  37. # up the JVM to accept JMX remote management:
  38. # http://java.sun.com/javase/6/docs/technotes/guides/management/agent.html
  39. # by default we allow local JMX connections
  40. if [[ -z $JMXLOCALONLY ]]; then
  41. JMXLOCALONLY=false
  42. fi
  43. if [[ -z $JMXDISABLE ]] || [[ $JMXDISABLE == 'false' ]]; then
  44. echo "ZooKeeper JMX enabled by default" >&2
  45. if [[ -z $JMXPORT ]]; then
  46. # for some reason these two options are necessary on jdk6 on Ubuntu
  47. # accord to the docs they are not necessary, but otw jconsole cannot
  48. # do a local attach
  49. ZOOMAIN=("-Dcom.sun.management.jmxremote" "-Dcom.sun.management.jmxremote.local.only=$JMXLOCALONLY" "org.apache.zookeeper.server.quorum.QuorumPeerMain")
  50. else
  51. if [[ -z $JMXAUTH ]]; then
  52. JMXAUTH=false
  53. fi
  54. if [[ -z $JMXSSL ]]; then
  55. JMXSSL=false
  56. fi
  57. if [[ -z $JMXLOG4J ]]; then
  58. JMXLOG4J=true
  59. fi
  60. echo "ZooKeeper remote JMX Port set to $JMXPORT" >&2
  61. echo "ZooKeeper remote JMX authenticate set to $JMXAUTH" >&2
  62. echo "ZooKeeper remote JMX ssl set to $JMXSSL" >&2
  63. echo "ZooKeeper remote JMX log4j set to $JMXLOG4J" >&2
  64. if [[ -z $JMXHOSTNAME ]]; then
  65. ZOOMAIN=("-Dcom.sun.management.jmxremote" "-Dcom.sun.management.jmxremote.port=$JMXPORT" "-Dcom.sun.management.jmxremote.authenticate=$JMXAUTH" "-Dcom.sun.management.jmxremote.ssl=$JMXSSL" "-Dzookeeper.jmx.log4j.disable=$JMXLOG4J" "org.apache.zookeeper.server.quorum.QuorumPeerMain")
  66. else
  67. echo "ZooKeeper remote JMX Hostname set to $JMXHOSTNAME" >&2
  68. ZOOMAIN=("-Dcom.sun.management.jmxremote" "-Djava.rmi.server.hostname=$JMXHOSTNAME" "-Dcom.sun.management.jmxremote.port=$JMXPORT" "-Dcom.sun.management.jmxremote.authenticate=$JMXAUTH" "-Dcom.sun.management.jmxremote.ssl=$JMXSSL" "-Dzookeeper.jmx.log4j.disable=$JMXLOG4J" "org.apache.zookeeper.server.quorum.QuorumPeerMain")
  69. fi
  70. fi
  71. else
  72. echo "JMX disabled by user request" >&2
  73. ZOOMAIN=("org.apache.zookeeper.server.quorum.QuorumPeerMain")
  74. fi
  75. if [[ -n $SERVER_JVMFLAGS ]]; then
  76. JVMFLAGS="$SERVER_JVMFLAGS $JVMFLAGS"
  77. fi
  78. # shellcheck disable=SC2206
  79. flags=($JVMFLAGS)
  80. # shellcheck disable=SC2206
  81. clientflags=($CLIENT_JVMFLAGS)
  82. if [[ -n $2 ]]; then
  83. ZOOCFG="$ZOOCFGDIR/$2"
  84. fi
  85. # if we give a more complicated path to the config, don't screw around in $ZOOCFGDIR
  86. if [[ "$(dirname "$ZOOCFG")" != "$ZOOCFGDIR" ]]; then
  87. ZOOCFG="$2"
  88. fi
  89. if $cygwin; then
  90. ZOOCFG=$(cygpath -wp "$ZOOCFG")
  91. # cygwin has a "kill" in the shell itself, gets confused
  92. KILL='/bin/kill'
  93. else
  94. KILL='kill'
  95. fi
  96. echo "Using config: $ZOOCFG" >&2
  97. case "$OSTYPE" in
  98. *solaris*)
  99. GREP='/usr/xpg4/bin/grep'
  100. ;;
  101. *)
  102. GREP='grep'
  103. ;;
  104. esac
  105. ZOO_DATADIR="$($GREP "^[[:space:]]*dataDir" "$ZOOCFG" | sed -e 's/.*=//')"
  106. ZOO_DATADIR="$(echo -e "$ZOO_DATADIR" | sed -e 's/^[[:space:]]*//' -e 's/[[:space:]]*$//')"
  107. ZOO_DATALOGDIR="$($GREP "^[[:space:]]*dataLogDir" "$ZOOCFG" | sed -e 's/.*=//')"
  108. # iff autocreate is turned off and the datadirs don't exist fail
  109. # immediately as we can't create the PID file, etc..., anyway.
  110. if [[ -n $ZOO_DATADIR_AUTOCREATE_DISABLE ]]; then
  111. if [[ ! -d "$ZOO_DATADIR/version-2" ]]; then
  112. echo "ZooKeeper data directory is missing at $ZOO_DATADIR fix the path or run initialize"
  113. exit 1
  114. fi
  115. if [[ -n $ZOO_DATALOGDIR ]] && [[ ! -d "$ZOO_DATALOGDIR/version-2" ]]; then
  116. echo "ZooKeeper txnlog directory is missing at $ZOO_DATALOGDIR fix the path or run initialize"
  117. exit 1
  118. fi
  119. flags=("-Dzookeeper.datadir.autocreate=false" "${flags[@]}")
  120. fi
  121. if [[ -z $ZOOPIDFILE ]]; then
  122. if [[ ! -d $ZOO_DATADIR ]]; then
  123. mkdir -p "$ZOO_DATADIR"
  124. fi
  125. ZOOPIDFILE="$ZOO_DATADIR/zookeeper_server.pid"
  126. else
  127. # ensure it exists, otw stop will fail
  128. mkdir -p "$(dirname "$ZOOPIDFILE")"
  129. fi
  130. if [[ ! -w $ZOO_LOG_DIR ]]; then
  131. mkdir -p "$ZOO_LOG_DIR"
  132. fi
  133. ZOO_LOG_FILE=${ZOO_LOG_FILE:-zookeeper-$USER-server-$HOSTNAME.log}
  134. _ZOO_DAEMON_OUT="$ZOO_LOG_DIR/zookeeper-$USER-server-$HOSTNAME.out"
  135. case $1 in
  136. start)
  137. echo -n "Starting zookeeper ... "
  138. if [[ -f $ZOOPIDFILE ]]; then
  139. if kill -0 "$(cat "$ZOOPIDFILE")" &>/dev/null; then
  140. echo "already running as process $(cat "$ZOOPIDFILE")."
  141. exit 1
  142. fi
  143. fi
  144. nohup "$JAVA" "-Dzookeeper.log.dir=$ZOO_LOG_DIR" \
  145. "-Dzookeeper.log.file=$ZOO_LOG_FILE" \
  146. -XX:+HeapDumpOnOutOfMemoryError -XX:OnOutOfMemoryError='kill -9 %p' \
  147. "${flags[@]}" "${ZOOMAIN[@]}" "$ZOOCFG" &>"$_ZOO_DAEMON_OUT" </dev/null &
  148. case "$OSTYPE" in
  149. *solaris*)
  150. /bin/echo "${!}\\c" >"$ZOOPIDFILE"
  151. ;;
  152. aix*)
  153. /bin/echo "$!\c" >"$ZOOPIDFILE"
  154. ;;
  155. *)
  156. echo -n $! >"$ZOOPIDFILE"
  157. ;;
  158. esac
  159. # this checks the exit code of the echo statements to verify the PID was written
  160. # shellcheck disable=SC2320,SC2181
  161. if [[ $? -eq 0 ]]; then
  162. sleep 1
  163. pid=$(cat "$ZOOPIDFILE")
  164. if ps -p "$pid" &>/dev/null; then
  165. echo STARTED
  166. else
  167. echo FAILED TO START
  168. exit 1
  169. fi
  170. else
  171. echo FAILED TO WRITE PID
  172. exit 1
  173. fi
  174. ;;
  175. start-foreground)
  176. ZOO_CMD=(exec "$JAVA")
  177. if [[ -n $ZOO_NOEXEC ]]; then
  178. ZOO_CMD=("$JAVA")
  179. fi
  180. "${ZOO_CMD[@]}" "-Dzookeeper.log.dir=$ZOO_LOG_DIR" \
  181. "-Dzookeeper.log.file=$ZOO_LOG_FILE" \
  182. -XX:+HeapDumpOnOutOfMemoryError -XX:OnOutOfMemoryError='kill -9 %p' \
  183. "${flags[@]}" "${ZOOMAIN[@]}" "$ZOOCFG"
  184. ;;
  185. print-classpath)
  186. echo "CLASSPATH=$CLASSPATH"
  187. ;;
  188. print-cmd)
  189. echo "\"$JAVA\" -Dzookeeper.log.dir=\"$ZOO_LOG_DIR\" \
  190. -Dzookeeper.log.file=\"$ZOO_LOG_FILE\" \
  191. -XX:+HeapDumpOnOutOfMemoryError -XX:OnOutOfMemoryError='kill -9 %p' \
  192. $(for x in "${flags[@]}"; do echo "\"$x\""; done | paste -sd' ') \
  193. $(for x in "${ZOOMAIN[@]}"; do echo "\"$x\""; done | paste -sd' ') \
  194. \"$ZOOCFG\" &>\"$_ZOO_DAEMON_OUT\" </dev/null"
  195. ;;
  196. stop)
  197. echo -n "Stopping zookeeper ... "
  198. if [[ ! -f $ZOOPIDFILE ]]; then
  199. echo "no zookeeper to stop (could not find file $ZOOPIDFILE)"
  200. else
  201. $KILL "$(cat "$ZOOPIDFILE")"
  202. rm "$ZOOPIDFILE"
  203. sleep 1
  204. echo STOPPED
  205. fi
  206. exit 0
  207. ;;
  208. version)
  209. ZOOMAIN=("org.apache.zookeeper.version.VersionInfoMain")
  210. $JAVA "${ZOOMAIN[@]}" 2>/dev/null
  211. ;;
  212. restart)
  213. shift
  214. "$0" stop "$@"
  215. sleep 3
  216. "$0" start "$@"
  217. ;;
  218. status)
  219. # -q is necessary on some versions of linux where nc returns too quickly, and no stat result is output
  220. isSSL="false"
  221. clientPortAddress=$($GREP "^[[:space:]]*clientPortAddress[^[:alpha:]]" "$ZOOCFG" | sed -e 's/.*=//')
  222. if [[ -z $clientPortAddress ]]; then
  223. clientPortAddress="localhost"
  224. fi
  225. clientPort=$($GREP "^[[:space:]]*clientPort[^[:alpha:]]" "$ZOOCFG" | sed -e 's/.*=//')
  226. if ! [[ $clientPort =~ ^[0-9]+$ ]]; then
  227. dataDir=$($GREP "^[[:space:]]*dataDir" "$ZOOCFG" | sed -e 's/.*=//')
  228. myid=$(cat "$dataDir/myid" 2>/dev/null)
  229. if ! [[ $myid =~ ^[0-9]+$ ]]; then
  230. echo "myid could not be determined, will not able to locate clientPort in the server configs."
  231. else
  232. clientPortAndAddress=$($GREP "^[[:space:]]*server.$myid=.*;.*" "$ZOOCFG" | sed -e 's/.*=//' | sed -e 's/.*;//')
  233. if [[ -z $clientPortAndAddress ]]; then
  234. echo "Client port not found in static config file. Looking in dynamic config file."
  235. dynamicConfigFile=$($GREP "^[[:space:]]*dynamicConfigFile" "$ZOOCFG" | sed -e 's/.*=//')
  236. clientPortAndAddress=$($GREP "^[[:space:]]*server.$myid=.*;.*" "$dynamicConfigFile" | sed -e 's/.*=//' | sed -e 's/.*;//')
  237. fi
  238. if [[ -z $clientPortAndAddress ]]; then
  239. echo "Client port not found in the server configs"
  240. else
  241. # Extracts address and port from address:port, even if address contains optional square braces
  242. # For example, this extracts the address 127::1 and the port 2181 from "[127::1]:2181"
  243. if [[ $clientPortAndAddress =~ ^\[?([^\]]*)\]?:([0-9]+) ]]; then
  244. clientPortAddress=${BASH_REMATCH[1]}
  245. clientPort=${BASH_REMATCH[2]}
  246. elif [[ $clientPortAndAddress =~ ^[0-9]+$ ]]; then
  247. clientPort=$clientPortAndAddress
  248. fi
  249. fi
  250. fi
  251. fi
  252. if [[ -z $clientPort ]]; then
  253. echo "Client port not found. Looking for secureClientPort in the static config."
  254. secureClientPort=$($GREP "^[[:space:]]*secureClientPort[^[:alpha:]]" "$ZOOCFG" | sed -e 's/.*=//')
  255. if [[ -n $secureClientPort ]]; then
  256. isSSL="true"
  257. clientPort=$secureClientPort
  258. clientPortAddress=$($GREP "^[[:space:]]*secureClientPortAddress[^[:alpha:]]" "$ZOOCFG" | sed -e 's/.*=//')
  259. if [[ -z $clientPortAddress ]]; then
  260. clientPortAddress="localhost"
  261. fi
  262. else
  263. echo "Unable to find either secure or unsecure client port in any configs. Terminating."
  264. exit 1
  265. fi
  266. fi
  267. echo "Client port found: $clientPort. Client address: $clientPortAddress. Client SSL: $isSSL."
  268. STAT=$("$JAVA" "-Dzookeeper.log.dir=$ZOO_LOG_DIR" "-Dzookeeper.log.file=$ZOO_LOG_FILE" \
  269. "${clientflags[@]}" "${flags[@]}" org.apache.zookeeper.client.FourLetterWordMain \
  270. "$clientPortAddress" "$clientPort" srvr "$isSSL" 2>/dev/null |
  271. $GREP Mode)
  272. if [[ -z $STAT ]]; then
  273. if [[ $isSSL == "true" ]]; then
  274. echo " "
  275. echo "Note: We used secureClientPort ($secureClientPort) to establish connection, but we failed. The 'status'"
  276. echo " command establishes a client connection to the server to execute diagnostic commands. Please make sure you"
  277. echo " provided all the Client SSL connection related parameters in the CLIENT_JVMFLAGS environment variable! E.g.:"
  278. echo ' CLIENT_JVMFLAGS="-Dzookeeper.clientCnxnSocket=org.apache.zookeeper.ClientCnxnSocketNetty'
  279. echo " -Dzookeeper.ssl.trustStore.location=/tmp/clienttrust.jks -Dzookeeper.ssl.trustStore.password=password"
  280. echo " -Dzookeeper.ssl.keyStore.location=/tmp/client.jks -Dzookeeper.ssl.keyStore.password=password"
  281. echo ' -Dzookeeper.client.secure=true" ./zkServer.sh status'
  282. echo " "
  283. fi
  284. echo "Error contacting service. It is probably not running."
  285. exit 1
  286. else
  287. echo "$STAT"
  288. exit 0
  289. fi
  290. ;;
  291. *)
  292. echo "Usage: $0 [--config <conf-dir>] {start|start-foreground|stop|version|restart|status|print-cmd}" >&2
  293. ;;
  294. esac