aboutsummaryrefslogtreecommitdiff
path: root/ejabberdctl.template
diff options
context:
space:
mode:
authorEvgeniy Khramtsov <ekhramtsov@process-one.net>2013-04-08 11:12:54 +0200
committerChristophe Romain <christophe.romain@process-one.net>2013-06-13 11:11:02 +0200
commit4d8f7706240a1603468968f47fc7b150b788d62f (patch)
tree92d55d789cc7ac979b3c9e161ffb7f908eba043a /ejabberdctl.template
parentFix Guide: ejabberd_service expects a shaper_rule, not a shaper (diff)
Switch to rebar build tool
Use dynamic Rebar configuration Make iconv dependency optional Disable transient_supervisors compile option Add hipe compilation support Only compile ibrowse and lhttpc when needed Make it possible to generate an OTP application release Add --enable-debug compile option Add --enable-all compiler option Add --enable-tools configure option Add --with-erlang configure option. Add --enable-erlang-version-check configure option. Add lager support Improve the test suite
Diffstat (limited to 'ejabberdctl.template')
-rwxr-xr-xejabberdctl.template392
1 files changed, 392 insertions, 0 deletions
diff --git a/ejabberdctl.template b/ejabberdctl.template
new file mode 100755
index 000000000..a98e73ef2
--- /dev/null
+++ b/ejabberdctl.template
@@ -0,0 +1,392 @@
+#!/bin/sh
+
+# define default configuration
+POLL=true
+SMP=auto
+ERL_MAX_PORTS=32000
+ERL_PROCESSES=250000
+ERL_MAX_ETS_TABLES=1400
+
+SCRIPT_DIR=$(cd ${0%/*} && pwd)
+
+# define default environment variables
+NODE=ejabberd
+HOST=localhost
+ERLANG_NODE=$NODE@$HOST
+ERL={{erl}}
+INSTALLUSER={{installuser}}
+
+# parse command line parameters
+ARGS=
+while [ $# -ne 0 ] ; do
+ PARAM=$1
+ shift
+ case $PARAM in
+ --) break ;;
+ --node) ERLANG_NODE_ARG=$1; shift ;;
+ --config-dir) ETCDIR=$1 ; shift ;;
+ --config) EJABBERD_CONFIG_PATH=$1 ; shift ;;
+ --ctl-config) EJABBERDCTL_CONFIG_PATH=$1 ; shift ;;
+ --logs) LOGS_DIR=$1 ; shift ;;
+ --spool) SPOOLDIR=$1 ; shift ;;
+ *) ARGS="$ARGS $PARAM" ;;
+ esac
+done
+
+# Define ejabberd variable if they have not been defined from the command line
+if [ "$ETCDIR" = "" ] ; then
+ ETCDIR={{sysconfdir}}/ejabberd
+fi
+if [ "$EJABBERD_CONFIG_PATH" = "" ] ; then
+ EJABBERD_CONFIG_PATH=$ETCDIR/ejabberd.cfg
+fi
+if [ "$EJABBERDCTL_CONFIG_PATH" = "" ] ; then
+ EJABBERDCTL_CONFIG_PATH=$ETCDIR/ejabberdctl.cfg
+fi
+[ -f "$EJABBERDCTL_CONFIG_PATH" ] && . "$EJABBERDCTL_CONFIG_PATH"
+if [ "$LOGS_DIR" = "" ] ; then
+ LOGS_DIR={{localstatedir}}/log/ejabberd
+fi
+if [ "$SPOOLDIR" = "" ] ; then
+ SPOOLDIR={{localstatedir}}/lib/ejabberd
+fi
+if [ "$EJABBERD_DOC_PATH" = "" ] ; then
+ EJABBERD_DOC_PATH={{docdir}}
+fi
+if [ "$ERLANG_NODE_ARG" != "" ] ; then
+ ERLANG_NODE=$ERLANG_NODE_ARG
+ NODE=${ERLANG_NODE%@*}
+fi
+
+# check the proper system user is used
+ID=`id -g`
+GIDS=`id -G`
+EJID=`id -g $INSTALLUSER`
+EXEC_CMD="false"
+for GID in $GIDS; do
+ if [ $GID -eq 0 ] ; then
+ EXEC_CMD="su ${INSTALLUSER} -p -c"
+ fi
+done
+if [ "$ID" -eq "$EJID" ] ; then
+ EXEC_CMD="sh -c"
+fi
+if [ "$EXEC_CMD" = "false" ] ; then
+ echo "This command can only be run by root or the user $INSTALLUSER" >&2
+ exit 4
+fi
+
+NAME=-name
+[ "$ERLANG_NODE" = "${ERLANG_NODE%.*}" ] && NAME=-sname
+
+KERNEL_OPTS=""
+if [ "$FIREWALL_WINDOW" != "" ] ; then
+ KERNEL_OPTS="${KERNEL_OPTS} -kernel inet_dist_listen_min ${FIREWALL_WINDOW%-*} inet_dist_listen_max ${FIREWALL_WINDOW#*-}"
+fi
+if [ "$INET_DIST_INTERFACE" != "" ] ; then
+ KERNEL_OPTS="${KERNEL_OPTS} -kernel inet_dist_use_interface \"${INET_DIST_INTERFACE}\""
+fi
+
+ERLANG_OPTS="+K $POLL -smp $SMP +P $ERL_PROCESSES $ERL_OPTIONS"
+
+# define additional environment variables
+if [ "{{release}}" != "true" ] ; then
+ if [ "$EJABBERDDIR" = "" ] ; then
+ EJABBERDDIR={{libdir}}/ejabberd
+ fi
+ if [ "$EJABBERD_EBIN_PATH" = "" ] ; then
+ EJABBERD_EBIN_PATH=$EJABBERDDIR/ebin
+ fi
+ if [ "$EJABBERD_PRIV_PATH" = "" ] ; then
+ EJABBERD_PRIV_PATH=$EJABBERDDIR/priv
+ fi
+ if [ "$EJABBERD_BIN_PATH" = "" ] ; then
+ EJABBERD_BIN_PATH=$EJABBERD_PRIV_PATH/bin
+ fi
+ if [ "$EJABBERD_SO_PATH" = "" ] ; then
+ EJABBERD_SO_PATH=$EJABBERD_PRIV_PATH/lib
+ fi
+ if [ "$EJABBERD_MSGS_PATH" = "" ] ; then
+ EJABBERD_MSGS_PATH=$EJABBERD_PRIV_PATH/msgs
+ fi
+fi
+
+EJABBERD_LOG_PATH=$LOGS_DIR/ejabberd.log
+SASL_LOG_PATH=$LOGS_DIR/erlang.log
+DATETIME=`date "+%Y%m%d-%H%M%S"`
+ERL_CRASH_DUMP=$LOGS_DIR/erl_crash_$DATETIME.dump
+ERL_INETRC=$ETCDIR/inetrc
+HOME=$SPOOLDIR
+
+# create the home dir with the proper user if doesn't exist, because it stores cookie file
+[ -d $HOME ] || $EXEC_CMD "mkdir -p $HOME"
+
+# Change to a directory readable by INSTALLUSER to
+# prevent "File operation error: eacces." messages
+cd $HOME
+
+# export global variables
+export EJABBERD_CONFIG_PATH
+export EJABBERD_MSGS_PATH
+export EJABBERD_LOG_PATH
+export EJABBERD_SO_PATH
+export EJABBERD_BIN_PATH
+export EJABBERD_DOC_PATH
+export EJABBERD_PID_PATH
+export ERL_CRASH_DUMP
+export ERL_EPMD_ADDRESS
+export ERL_INETRC
+export ERL_MAX_PORTS
+export ERL_MAX_ETS_TABLES
+export HOME
+export EXEC_CMD
+
+
+# Compatibility in ZSH
+#setopt shwordsplit 2>/dev/null
+
+# start server
+start ()
+{
+ checknodenameusage
+ [ "$?" -eq 0 ] && echo "\nERROR: The node '$ERLANG_NODE' is already running." && return 1
+
+ $EXEC_CMD "$ERL \
+ $NAME $ERLANG_NODE \
+ -noinput -detached \
+ -pa $EJABBERD_EBIN_PATH \
+ -mnesia dir \"\\\"$SPOOLDIR\\\"\" \
+ $KERNEL_OPTS \
+ -s ejabberd \
+ -sasl sasl_error_logger \\{file,\\\"$SASL_LOG_PATH\\\"\\} \
+ $ERLANG_OPTS $ARGS \"$@\""
+}
+
+# attach to server
+debug ()
+{
+ echo "--------------------------------------------------------------------"
+ echo ""
+ echo "IMPORTANT: we will attempt to attach an INTERACTIVE shell"
+ echo "to an already running ejabberd node."
+ echo "If an ERROR is printed, it means the connection was not successful."
+ echo "You can interact with the ejabberd node if you know how to use it."
+ echo "Please be extremely cautious with your actions,"
+ echo "and exit immediately if you are not completely sure."
+ echo ""
+ echo "To detach this shell from ejabberd, press:"
+ echo " control+c, control+c"
+ echo ""
+ echo "--------------------------------------------------------------------"
+ echo "To bypass permanently this warning, add to ejabberdctl.cfg the line:"
+ echo " EJABBERD_BYPASS_WARNINGS=true"
+ echo "Press any key to continue"
+ if [ "$EJABBERD_BYPASS_WARNINGS" != "true" ] ; then
+ read foo
+ fi
+ echo ""
+ TTY=`tty | sed -e 's/.*\///g'`
+ $EXEC_CMD "$ERL \
+ $NAME debug-${TTY}-${ERLANG_NODE} \
+ -remsh $ERLANG_NODE \
+ -hidden \
+ $KERNEL_OPTS \
+ $ERLANG_OPTS $ARGS \"$@\""
+}
+
+# start interactive server
+live ()
+{
+ checknodenameusage
+ [ "$?" -eq 0 ] && echo "\nERROR: The node '$ERLANG_NODE' is already running." && return 1
+
+ echo "--------------------------------------------------------------------"
+ echo ""
+ echo "IMPORTANT: ejabberd is going to start in LIVE (interactive) mode."
+ echo "All log messages will be shown in the command shell."
+ echo "You can interact with the ejabberd node if you know how to use it."
+ echo "Please be extremely cautious with your actions,"
+ echo "and exit immediately if you are not completely sure."
+ echo ""
+ echo "To exit this LIVE mode and stop ejabberd, press:"
+ echo " q(). and press the Enter key"
+ echo ""
+ echo "--------------------------------------------------------------------"
+ echo "To bypass permanently this warning, add to ejabberdctl.cfg the line:"
+ echo " EJABBERD_BYPASS_WARNINGS=true"
+ echo "Press any key to continue"
+ if [ "$EJABBERD_BYPASS_WARNINGS" != "true" ] ; then
+ read foo
+ fi
+ echo ""
+ $EXEC_CMD "$ERL \
+ $NAME $ERLANG_NODE \
+ -pa $EJABBERD_EBIN_PATH \
+ -mnesia dir \"\\\"$SPOOLDIR\\\"\" \
+ $KERNEL_OPTS \
+ -s ejabberd \
+ $ERLANG_OPTS $ARGS \"$@\""
+}
+
+help ()
+{
+ echo ""
+ echo "Commands to start an ejabberd node:"
+ echo " start Start an ejabberd node in server mode"
+ echo " debug Attach an interactive Erlang shell to a running ejabberd node"
+ echo " live Start an ejabberd node in live (interactive) mode"
+ echo ""
+ echo "Optional parameters when starting an ejabberd node:"
+ echo " --config-dir dir Config ejabberd: $ETCDIR"
+ echo " --config file Config ejabberd: $EJABBERD_CONFIG_PATH"
+ echo " --ctl-config file Config ejabberdctl: $EJABBERDCTL_CONFIG_PATH"
+ echo " --logs dir Directory for logs: $LOGS_DIR"
+ echo " --spool dir Database spool dir: $SPOOLDIR"
+ echo " --node nodename ejabberd node name: $ERLANG_NODE"
+ echo ""
+}
+
+# common control function
+ctl ()
+{
+ COMMAND=$@
+
+ # Control number of connections identifiers
+ # using flock if available. Expects a linux-style
+ # flock that can lock a file descriptor.
+ MAXCONNID=100
+ CONNLOCKDIR={{localstatedir}}/lock/ejabberdctl
+ FLOCK='/usr/bin/flock'
+ if [ ! -x "$FLOCK" ] || [ ! -d "$CONNLOCKDIR" ] ; then
+ JOT='/usr/bin/jot'
+ if [ ! -x "$JOT" ] ; then
+ # no flock or jot, simply invoke ctlexec()
+ CTL_CONN="ctl-${ERLANG_NODE}"
+ ctlexec $CTL_CONN $COMMAND
+ result=$?
+ else
+ # no flock, but at least there is jot
+ RAND=`jot -r 1 0 $MAXCONNID`
+ CTL_CONN="ctl-${RAND}-${ERLANG_NODE}"
+ ctlexec $CTL_CONN $COMMAND
+ result=$?
+ fi
+ else
+ # we have flock so we get a lock
+ # on one of a limited number of
+ # conn names -- this allows
+ # concurrent invocations using a bound
+ # number of atoms
+ for N in $(seq 1 $MAXCONNID); do
+ CTL_CONN="ejabberdctl-$N"
+ CTL_LOCKFILE="$CONNLOCKDIR/$CTL_CONN"
+ (
+ exec 8>"$CTL_LOCKFILE"
+ if flock --nb 8; then
+ ctlexec $CTL_CONN $COMMAND
+ ssresult=$?
+ # segregate from possible flock exit(1)
+ ssresult=$(expr $ssresult \* 10)
+ exit $ssresult
+ else
+ exit 1
+ fi
+ )
+ result=$?
+ if [ $result -eq 1 ]; then
+ # means we errored out in flock
+ # rather than in the exec - stay in the loop
+ # trying other conn names...
+ badlock=1
+ else
+ badlock=""
+ break;
+ fi
+ done
+ result=$(expr $result / 10)
+ fi
+
+ if [ "$badlock" ];then
+ echo "Ran out of connections to try. Your ejabberd processes" >&2
+ echo "may be stuck or this is a very busy server. For very" >&2
+ echo "busy servers, consider raising MAXCONNID in ejabberdctl">&2
+ exit 1;
+ fi
+
+ case $result in
+ 0) :;;
+ 1) :;;
+ 2) help;;
+ 3) help;;
+ esac
+ return $result
+}
+
+ctlexec ()
+{
+ CONN_NAME=$1; shift
+ COMMAND=$@
+ $EXEC_CMD "$ERL \
+ $NAME ${CONN_NAME} \
+ -noinput \
+ -hidden \
+ -pa $EJABBERD_EBIN_PATH \
+ $KERNEL_OPTS \
+ -s ejabberd_ctl -extra $ERLANG_NODE $COMMAND"
+}
+
+# display ctl usage
+usage ()
+{
+ ctl
+ exit
+}
+
+# stop epmd if there is no other running node
+stop_epmd()
+{
+ epmd -names | grep -q name || epmd -kill
+}
+
+# allow sync calls
+wait_for_status()
+{
+ # args: status try delay
+ # return: 0 OK, 1 KO
+ timeout=$2
+ status=4
+ while [ $status -ne $1 ]; do
+ sleep $3
+ timeout=$(($timeout - 1))
+ [ $timeout -eq 0 ] && {
+ status=$1
+ } || {
+ ctl status > /dev/null
+ status=$?
+ }
+ done
+ [ $timeout -eq 0 ] && {
+ status=1
+ } || {
+ status=0
+ }
+ return $status
+}
+
+# check node name is used or not
+# $? --> 0=alreadyused 1=available
+checknodenameusage ()
+{
+ $EXEC_CMD "$ERL \
+ $NAME $ERLANG_NODE \
+ -s erlang halt | grep -c duplicate_name > /dev/null "
+}
+
+case $ARGS in
+ ' start') start;;
+ ' debug') debug;;
+ ' live') live;;
+ ' started') wait_for_status 0 30 2;; # wait 30x2s before timeout
+ ' stopped') wait_for_status 3 15 2; stop_epmd;; # wait 15x2s before timeout
+ *) ctl $ARGS;;
+esac