]> arthur.barton.de Git - netdata.git/blob - netdata-installer.sh
set init.d defaults on old ubuntu installations
[netdata.git] / netdata-installer.sh
1 #!/usr/bin/env bash
2
3 # reload the user profile
4 [ -f /etc/profile ] && . /etc/profile
5
6 export PATH="${PATH}:/sbin:/usr/sbin:/usr/local/bin:/usr/local/sbin"
7
8 # fix PKG_CHECK_MODULES error
9 if [ -d /usr/share/aclocal ]
10 then
11         ACLOCAL_PATH=${ACLOCAL_PATH-/usr/share/aclocal}
12         export ACLOCAL_PATH
13 fi
14
15 LC_ALL=C
16 umask 022
17
18 # Be nice on production environments
19 renice 19 $$ >/dev/null 2>/dev/null
20
21 processors=$(cat /proc/cpuinfo  | grep ^processor | wc -l)
22 [ $(( processors )) -lt 1 ] && processors=1
23
24 # you can set CFLAGS before running installer
25 CFLAGS="${CFLAGS--O3}"
26
27 # keep a log of this command
28 printf "\n# " >>netdata-installer.log
29 date >>netdata-installer.log
30 printf "CFLAGS=\"%s\" " "${CFLAGS}" >>netdata-installer.log
31 printf "%q " "$0" "${@}" >>netdata-installer.log
32 printf "\n" >>netdata-installer.log
33
34 REINSTALL_PWD="${PWD}"
35 REINSTALL_COMMAND="$(printf "%q " "$0" "${@}"; printf "\n")"
36
37 banner() {
38     local   l1="  ^"                                                                      \
39             l2="  |.-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-.   .-"  \
40             l3="  |   '-'   '-'   '-'   '-'   '-'   '-'   '-'   '-'   '-'   '-'   '-'   '-'  "  \
41             l4="  +----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+-----+--->" \
42             sp="                                                                        " \
43             netdata="netdata" start end msg="${*}"
44
45     [ ${#msg} -lt ${#netdata} ] && msg="${msg}${sp:0:$(( ${#netdata} - ${#msg}))}"
46     [ ${#msg} -gt $(( ${#l2} - 20 )) ] && msg="${msg:0:$(( ${#l2} - 23 ))}..."
47
48     start="$(( ${#l2} / 2 - 4 ))"
49     [ $(( start + ${#msg} + 4 )) -gt ${#l2} ] && start=$((${#l2} - ${#msg} - 4))
50     end=$(( ${start} + ${#msg} + 4 ))
51
52     echo >&2
53     echo >&2 "${l1}"
54     echo >&2 "${l2:0:start}${sp:0:2}${netdata}${sp:0:$((end - start - 2 - ${#netdata}))}${l2:end:$((${#l2} - end))}"
55     echo >&2 "${l3:0:start}${sp:0:2}${msg}${sp:0:2}${l3:end:$((${#l2} - end))}"
56     echo >&2 "${l4}"
57     echo >&2
58 }
59
60 service="$(which service 2>/dev/null || command -v service 2>/dev/null)"
61 systemctl="$(which systemctl 2>/dev/null || command -v systemctl 2>/dev/null)"
62 service() {
63     local cmd="${1}" action="${2}"
64
65     if [ ! -z "${service}" ]
66     then
67         run "${service}" "${cmd}" "${action}"
68         return $?
69     elif [ ! -z "${systemctl}" ]
70     then
71         run "${systemctl}" "${action}" "${cmd}"
72         return $?
73     fi
74     return 1
75 }
76
77 ME="$0"
78 DONOTSTART=0
79 DONOTWAIT=0
80 NETDATA_PREFIX=
81 LIBS_ARE_HERE=0
82
83 usage() {
84     banner "installer command line options"
85     cat <<USAGE
86
87 ${ME} <installer options>
88
89 Valid <installer options> are:
90
91    --install /PATH/TO/INSTALL
92
93         If your give: --install /opt
94         netdata will be installed in /opt/netdata
95
96    --dont-start-it
97
98         Do not (re)start netdata.
99         Just install it.
100
101    --dont-wait
102
103         Do not wait for the user to press ENTER.
104         Start immediately building it.
105
106    --zlib-is-really-here
107    --libs-are-really-here
108
109         If you get errors about missing zlib,
110         or libuuid but you know it is available,
111         you have a broken pkg-config.
112         Use this option to allow it continue
113         without checking pkg-config.
114
115 Netdata will by default be compiled with gcc optimization -O3
116 If you need to pass different CFLAGS, use something like this:
117
118   CFLAGS="<gcc options>" ${ME} <installer options>
119
120 For the installer to complete successfully, you will need
121 these packages installed:
122
123    gcc make autoconf automake pkg-config zlib1g-dev (or zlib-devel)
124    uuid-dev (or libuuid-devel)
125
126 For the plugins, you will at least need:
127
128    curl nodejs
129
130 USAGE
131 }
132
133 md5sum="$(which md5sum 2>/dev/null || command -v md5sum 2>/dev/null)"
134 get_git_config_signatures() {
135     local x s file md5
136
137     [ ! -d "conf.d" ] && echo >&2 "Wrong directory." && return 1
138     [ -z "${md5sum}" -o ! -x "${md5sum}" ] && echo >&2 "No md5sum command." && return 1
139
140     echo >configs.signatures.tmp
141
142     for x in $(find conf.d -name \*.conf | sort)
143     do
144             x="${x/conf.d\//}"
145             echo "${x}"
146             for c in $(git log --follow "conf.d/${x}" | grep ^commit | cut -d ' ' -f 2)
147             do
148                     git checkout ${c} "conf.d/${x}" || continue
149                     s="$(cat "conf.d/${x}" | md5sum | cut -d ' ' -f 1)"
150                     echo >>configs.signatures.tmp "${x}:${s}"
151                     echo "    ${s}"
152             done
153             git checkout HEAD "conf.d/${x}" || break
154     done
155
156     cat configs.signatures.tmp |\
157         grep -v "^$" |\
158         sort -u |\
159         {
160             echo "declare -A configs_signatures=("
161             IFS=":"
162             while read file md5
163             do
164                 echo "  ['${md5}']='${file}'"
165             done
166             echo ")"
167         } >configs.signatures
168
169     rm configs.signatures.tmp
170
171     return 0
172 }
173
174
175 while [ ! -z "${1}" ]
176 do
177     if [ "$1" = "--install" ]
178         then
179         NETDATA_PREFIX="${2}/netdata"
180         shift 2
181     elif [ "$1" = "--zlib-is-really-here" -o "$1" = "--libs-are-really-here" ]
182         then
183         LIBS_ARE_HERE=1
184         shift 1
185     elif [ "$1" = "--dont-start-it" ]
186         then
187         DONOTSTART=1
188         shift 1
189     elif [ "$1" = "--dont-wait" ]
190         then
191         DONOTWAIT=1
192         shift 1
193     elif [ "$1" = "--help" -o "$1" = "-h" ]
194         then
195         usage
196         exit 1
197     elif [ "$1" = "get_git_config_signatures" ]
198         then
199         get_git_config_signatures && exit 0
200         exit 1
201     else
202         echo >&2
203         echo >&2 "ERROR:"
204         echo >&2 "I cannot understand option '$1'."
205         usage
206         exit 1
207     fi
208 done
209
210 banner "real-time performance monitoring, done right!"
211 cat <<BANNER
212
213   You are about to build and install netdata to your system.
214
215   It will be installed at these locations:
216
217    - the daemon    at ${NETDATA_PREFIX}/usr/sbin/netdata
218    - config files  at ${NETDATA_PREFIX}/etc/netdata
219    - web files     at ${NETDATA_PREFIX}/usr/share/netdata
220    - plugins       at ${NETDATA_PREFIX}/usr/libexec/netdata
221    - cache files   at ${NETDATA_PREFIX}/var/cache/netdata
222    - db files      at ${NETDATA_PREFIX}/var/lib/netdata
223    - log files     at ${NETDATA_PREFIX}/var/log/netdata
224    - pid file      at ${NETDATA_PREFIX}/var/run
225
226   This installer allows you to change the installation path.
227   Press Control-C and run the same command with --help for help.
228
229 BANNER
230
231 if [ "${UID}" -ne 0 ]
232     then
233     if [ -z "${NETDATA_PREFIX}" ]
234         then
235         banner "wrong command line options!"
236         cat <<NONROOTNOPREFIX
237
238 Sorry! This will fail!
239
240 You are attempting to install netdata as non-root, but you plan to install it
241 in system paths.
242
243 Please set an installation prefix, like this:
244
245     $0 ${@} --install /tmp
246
247 or, run the installer as root:
248
249     sudo $0 ${@}
250
251 We suggest to install it as root, or certain data collectors will not be able
252 to work. Netdata drops root privileges when running. So, if you plan to keep
253 it, install it as root to get the full functionality.
254
255 NONROOTNOPREFIX
256         exit 1
257
258     else
259         cat <<NONROOT
260
261 IMPORTANT:
262 You are about to install netdata as a non-root user.
263 Netdata will work, but a few data collection modules that
264 require root access will fail.
265
266 If you installing permanently on your system, run the
267 installer like this:
268
269     sudo $0 ${@}
270
271 NONROOT
272     fi
273 fi
274
275 have_autotools=
276 if [ "$(type autoreconf 2> /dev/null)" ]
277 then
278     autoconf_maj_min() {
279         local maj min IFS=.-
280
281         maj=$1
282         min=$2
283
284         set -- $(autoreconf -V | sed -ne '1s/.* \([^ ]*\)$/\1/p')
285         eval $maj=\$1 $min=\$2
286     }
287     autoconf_maj_min AMAJ AMIN
288
289     if [ "$AMAJ" -gt 2 ]
290     then
291         have_autotools=Y
292     elif [ "$AMAJ" -eq 2 -a "$AMIN" -ge 60 ]
293     then
294         have_autotools=Y
295     else
296         echo "Found autotools $AMAJ.$AMIN"
297     fi
298 else
299     echo "No autotools found"
300 fi
301
302 if [ ! "$have_autotools" ]
303 then
304     if [ -f configure ]
305     then
306         echo "Will skip autoreconf step"
307     else
308         banner "autotools v2.60 required"
309         cat <<"EOF"
310
311 -------------------------------------------------------------------------------
312 autotools 2.60 or later is required
313
314 Sorry, you do not seem to have autotools 2.60 or later, which is
315 required to build from the git sources of netdata.
316
317 You can either install a suitable version of autotools and automake
318 or download a netdata package which does not have these dependencies.
319
320 Source packages where autotools have already been run are available
321 here:
322        https://firehol.org/download/netdata/
323
324 The unsigned/master folder tracks the head of the git tree and released
325 packages are also available.
326 EOF
327         exit 1
328     fi
329 fi
330
331 if [ ${DONOTWAIT} -eq 0 ]
332     then
333     if [ ! -z "${NETDATA_PREFIX}" ]
334         then
335         read -p "Press ENTER to build and install netdata to '${NETDATA_PREFIX}' > "
336     else
337         read -p "Press ENTER to build and install netdata to your system > "
338     fi
339 fi
340
341 build_error() {
342     banner "sorry, it failed to build..."
343     cat <<EOF
344
345 ^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
346
347 Sorry! netdata failed to build...
348
349 You many need to check these:
350
351 1. The package uuid-dev (or libuuid-devel) has to be installed.
352
353    If your system cannot find libuuid, although it is installed
354    run me with the option:  --libs-are-really-here
355
356 2. The package zlib1g-dev (or zlib-devel) has to be installed.
357
358    If your system cannot find zlib, although it is installed
359    run me with the option:  --libs-are-really-here
360
361 3. You need basic build tools installed, like:
362
363    gcc make autoconf automake pkg-config
364
365    Autoconf version 2.60 or higher is required.
366
367 If you still cannot get it to build, ask for help at github:
368
369    https://github.com/firehol/netdata/issues
370
371
372 EOF
373     trap - EXIT
374     exit 1
375 }
376
377 run() {
378     printf >>netdata-installer.log "# "
379     printf >>netdata-installer.log "%q " "${@}"
380     printf >>netdata-installer.log " ... "
381
382     printf >&2 "\n"
383     printf >&2 ":-----------------------------------------------------------------------------\n"
384     printf >&2 "Running command:\n"
385     printf >&2 "\n"
386     printf >&2 "%q " "${@}"
387     printf >&2 "\n"
388
389     "${@}"
390
391     local ret=$?
392     if [ ${ret} -ne 0 ]
393         then
394         printf >>netdata-installer.log "FAILED!\n"
395     else
396         printf >>netdata-installer.log "OK\n"
397     fi
398
399     return ${ret}
400 }
401
402 if [ ${LIBS_ARE_HERE} -eq 1 ]
403     then
404     shift
405     echo >&2 "ok, assuming libs are really installed."
406     export ZLIB_CFLAGS=" "
407     export ZLIB_LIBS="-lz"
408     export UUID_CFLAGS=" "
409     export UUID_LIBS="-luuid"
410 fi
411
412 trap build_error EXIT
413
414 if [ "$have_autotools" ]
415 then
416     run ./autogen.sh || exit 1
417 fi
418
419 run ./configure \
420     --prefix="${NETDATA_PREFIX}/usr" \
421     --sysconfdir="${NETDATA_PREFIX}/etc" \
422     --localstatedir="${NETDATA_PREFIX}/var" \
423     --with-zlib --with-math --with-user=netdata \
424     CFLAGS="${CFLAGS}" || exit 1
425
426 # remove the build_error hook
427 trap - EXIT
428
429 if [ -f src/netdata ]
430     then
431     echo >&2 "Cleaning a possibly old compilation ..."
432     run make clean
433 fi
434
435 echo >&2 "Compiling netdata ..."
436 run make -j${processors} || exit 1
437
438 if [ "${BASH_VERSINFO[0]}" -ge "4" ]
439 then
440     declare -A configs_signatures=()
441     if [ -f "configs.signatures" ]
442         then
443         source "configs.signatures" || echo >&2 "ERROR: Failed to load configs.signatures !"
444     fi
445 fi
446
447 # migrate existing configuration files
448 # for node.d and charts.d
449 if [ -d "${NETDATA_PREFIX}/etc/netdata" ]
450     then
451     # the configuration directory exists
452
453     if [ ! -d "${NETDATA_PREFIX}/etc/netdata/charts.d" ]
454         then
455         run mkdir "${NETDATA_PREFIX}/etc/netdata/charts.d"
456     fi
457
458     # move the charts.d config files
459     for x in apache ap cpu_apps cpufreq example exim hddtemp load_average mem_apps mysql nginx nut opensips phpfpm postfix sensors squid tomcat
460     do
461         for y in "" ".old" ".orig"
462         do
463             if [ -f "${NETDATA_PREFIX}/etc/netdata/${x}.conf${y}" -a ! -f "${NETDATA_PREFIX}/etc/netdata/charts.d/${x}.conf${y}" ]
464                 then
465                 run mv -f "${NETDATA_PREFIX}/etc/netdata/${x}.conf${y}" "${NETDATA_PREFIX}/etc/netdata/charts.d/${x}.conf${y}"
466             fi
467         done
468     done
469
470     if [ ! -d "${NETDATA_PREFIX}/etc/netdata/node.d" ]
471         then
472         run mkdir "${NETDATA_PREFIX}/etc/netdata/node.d"
473     fi
474
475     # move the node.d config files
476     for x in named sma_webbox snmp
477     do
478         for y in "" ".old" ".orig"
479         do
480             if [ -f "${NETDATA_PREFIX}/etc/netdata/${x}.conf${y}" -a ! -f "${NETDATA_PREFIX}/etc/netdata/node.d/${x}.conf${y}" ]
481                 then
482                 run mv -f "${NETDATA_PREFIX}/etc/netdata/${x}.conf${y}" "${NETDATA_PREFIX}/etc/netdata/node.d/${x}.conf${y}"
483             fi
484         done
485     done
486 fi
487
488 # backup user configurations
489 installer_backup_suffix="${PID}.${RANDOM}"
490 for x in $(find "${NETDATA_PREFIX}/etc/netdata/" -name '*.conf' -type f)
491 do
492     if [ -f "${x}" ]
493         then
494         # make a backup of the configuration file
495         cp -p "${x}" "${x}.old"
496
497         if [ -z "${md5sum}" -o ! -x "${md5sum}" ]
498             then
499             # we don't have md5sum - keep it
500             cp -p "${x}" "${x}.installer_backup.${installer_backup_suffix}"
501         else
502             # find it relative filename
503             f="${x/*\/etc\/netdata\//}"
504
505             # find its checksum
506             md5="$(cat "${x}" | ${md5sum} | cut -d ' ' -f 1)"
507
508             # copy the original
509             if [ -f "conf.d/${f}" ]
510                 then
511                 cp "conf.d/${f}" "${x}.orig"
512             fi
513
514             if [ "${BASH_VERSINFO[0]}" -ge "4" ]
515             then
516                 if [ "${configs_signatures[${md5}]}" = "${f}" ]
517                 then
518                     # it is a stock version - don't keep it
519                     echo >&2 "File '${x}' is stock version."
520                 else
521                     # edited by user - keep it
522                     echo >&2 "File '${x}' has been edited by user."
523                     cp -p "${x}" "${x}.installer_backup.${installer_backup_suffix}"
524                 fi
525             else
526                 echo >&2 "File '${x}' cannot be check for custom edits."
527                 cp -p "${x}" "${x}.installer_backup.${installer_backup_suffix}"
528             fi
529         fi
530
531     elif [ -f "${x}.installer_backup.${installer_backup_suffix}" ]
532         then
533         rm -f "${x}.installer_backup.${installer_backup_suffix}"
534     fi
535 done
536
537 echo >&2 "Installing netdata ..."
538 run make install || exit 1
539
540 # restore user configurations
541 for x in $(find "${NETDATA_PREFIX}/etc/netdata/" -name '*.conf' -type f)
542 do
543     if [ -f "${x}.installer_backup.${installer_backup_suffix}" ]
544         then
545         cp -p "${x}.installer_backup.${installer_backup_suffix}" "${x}"
546         rm -f "${x}.installer_backup.${installer_backup_suffix}"
547     fi
548 done
549
550 NETDATA_ADDED_TO_DOCKER=0
551 if [ ${UID} -eq 0 ]
552     then
553     getent group netdata > /dev/null
554     if [ $? -ne 0 ]
555         then
556         echo >&2 "Adding netdata user group ..."
557         run groupadd -r netdata
558     fi
559
560     getent passwd netdata > /dev/null
561     if [ $? -ne 0 ]
562         then
563         echo >&2 "Adding netdata user account ..."
564         run useradd -r -g netdata -c netdata -s $(which nologin 2>/dev/null || command -v nologin 2>/dev/null || echo '/bin/false') -d / netdata
565     fi
566
567     getent group docker > /dev/null
568     if [ $? -eq 0 ]
569         then
570         # find the users in the docker group
571         docker=$(getent group docker | cut -d ':' -f 4)
572         if [[ ",${docker}," =~ ,netdata, ]]
573             then
574             # netdata is already there
575             :
576         else
577             # netdata is not in docker group
578             echo >&2 "Adding netdata user to the docker group (needed to get container names) ..."
579             run usermod -a -G docker netdata
580         fi
581         # let the uninstall script know
582         NETDATA_ADDED_TO_DOCKER=1
583     fi
584
585     if [ -d /etc/logrotate.d -a ! -f /etc/logrotate.d/netdata ]
586         then
587         echo >&2 "Adding netdata logrotate configuration ..."
588         run cp system/netdata.logrotate /etc/logrotate.d/netdata
589     fi
590 fi
591
592
593 # -----------------------------------------------------------------------------
594 # load options from the configuration file
595
596 # create an empty config if it does not exist
597 [ ! -f "${NETDATA_PREFIX}/etc/netdata/netdata.conf" ] && touch "${NETDATA_PREFIX}/etc/netdata/netdata.conf"
598
599 # function to extract values from the config file
600 config_option() {
601     local key="${1}" value="${2}" line=
602
603     if [ -s "${NETDATA_PREFIX}/etc/netdata/netdata.conf" ]
604         then
605         line="$( grep "^[[:space:]]*${key}[[:space:]]*=[[:space:]]*" "${NETDATA_PREFIX}/etc/netdata/netdata.conf" | head -n 1 )"
606         [ ! -z "${line}" ] && value="$( echo "${line}" | cut -d '=' -f 2 | sed -e "s/^[[:space:]]\+//g" -e "s/[[:space:]]\+$//g" )"
607     fi
608
609     echo "${value}"
610 }
611
612 # user
613 defuser="netdata"
614 [ ! "${UID}" = "0" ] && defuser="${USER}"
615 NETDATA_USER="$( config_option "run as user" "${defuser}" )"
616
617 NETDATA_WEB_USER="$( config_option "web files owner" "${defuser}" )"
618 NETDATA_WEB_GROUP="$( config_option "web files group" "${NETDATA_WEB_USER}" )"
619
620 # debug flags
621 defdebug=0
622 NETDATA_DEBUG="$( config_option "debug flags" ${defdebug} )"
623
624 # port
625 defport=19999
626 NETDATA_PORT="$( config_option "default port" ${defport} )"
627 NETDATA_PORT2="$( config_option "port" ${defport} )"
628
629 if [ "${NETDATA_PORT}" != "${NETDATA_PORT2}" ]
630 then
631     if [ "${NETDATA_PORT2}" != "${defport}" ]
632     then
633         NETDATA_PORT="${NETDATA_PORT2}"
634     fi
635 fi
636
637 # directories
638 NETDATA_LIB_DIR="$( config_option "lib directory" "${NETDATA_PREFIX}/var/lib/netdata" )"
639 NETDATA_CACHE_DIR="$( config_option "cache directory" "${NETDATA_PREFIX}/var/cache/netdata" )"
640 NETDATA_WEB_DIR="$( config_option "web files directory" "${NETDATA_PREFIX}/usr/share/netdata/web" )"
641 NETDATA_LOG_DIR="$( config_option "log directory" "${NETDATA_PREFIX}/var/log/netdata" )"
642 NETDATA_CONF_DIR="$( config_option "config directory" "${NETDATA_PREFIX}/etc/netdata" )"
643 NETDATA_RUN_DIR="${NETDATA_PREFIX}/var/run"
644
645
646 # -----------------------------------------------------------------------------
647 # prepare the directories
648
649 # this is needed if NETDATA_PREFIX is not empty
650 if [ ! -d "${NETDATA_RUN_DIR}" ]
651     then
652     mkdir -p "${NETDATA_RUN_DIR}" || exit 1
653 fi
654
655 echo >&2
656 echo >&2 "Fixing directories (user: ${NETDATA_USER})..."
657 for x in "${NETDATA_WEB_DIR}" "${NETDATA_CONF_DIR}" "${NETDATA_CACHE_DIR}" "${NETDATA_LOG_DIR}" "${NETDATA_LIB_DIR}" "${NETDATA_CONF_DIR}/python.d" "${NETDATA_CONF_DIR}/charts.d" "${NETDATA_CONF_DIR}/node.d"
658 do
659     if [ ! -d "${x}" ]
660         then
661         echo >&2 "Creating directory '${x}'"
662         run mkdir -p "${x}" || exit 1
663     fi
664
665     if [ ${UID} -eq 0 ]
666         then
667         if [ "${x}" = "${NETDATA_WEB_DIR}" ]
668             then
669             run chown -R "${NETDATA_WEB_USER}:${NETDATA_WEB_GROUP}" "${x}" || echo >&2 "WARNING: Cannot change the ownership of the files in directory ${x} to ${NETDATA_WEB_USER}:${NETDATA_WEB_GROUP}..."
670         else
671             run chown -R "${NETDATA_USER}:${NETDATA_USER}" "${x}" || echo >&2 "WARNING: Cannot change the ownership of the files in directory ${x} to ${NETDATA_USER}..."
672         fi
673     fi
674
675     run chmod 0755 "${x}" || echo >&2 "WARNING: Cannot change the permissions of the directory ${x} to 0755..."
676 done
677
678 if [ ${UID} -eq 0 ]
679     then
680     run chown root "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
681     run chmod 0755 "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
682     run setcap cap_dac_read_search,cap_sys_ptrace+ep "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
683     if [ $? -ne 0 ]
684         then
685         # fix apps.plugin to be setuid to root
686         run chown root "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
687         run chmod 4755 "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
688     fi
689 fi
690
691 # -----------------------------------------------------------------------------
692 # check if we can re-start netdata
693
694 if [ ${DONOTSTART} -eq 1 ]
695     then
696     if [ ! -s "${NETDATA_PREFIX}/etc/netdata/netdata.conf" ]
697         then
698         echo >&2 "Generating empty config file in: ${NETDATA_PREFIX}/etc/netdata/netdata.conf"
699         echo "# Get config from http://127.0.0.1:${NETDATA_PORT}/netdata.conf" >"${NETDATA_PREFIX}/etc/netdata/netdata.conf"
700
701         if [ "${UID}" -eq 0 ]
702             then
703             chown "${NETDATA_USER}" "${NETDATA_PREFIX}/etc/netdata/netdata.conf"
704         fi
705         chmod 0664 "${NETDATA_PREFIX}/etc/netdata/netdata.conf"
706     fi
707     banner "is installed now!"
708     echo >&2 "  enjoy real-time performance and health monitoring..."
709     exit 0
710 fi
711
712 # -----------------------------------------------------------------------------
713 # stop a running netdata
714
715 isnetdata() {
716     [ -z "$1" -o ! -f "/proc/$1/stat" ] && return 1
717     [ "$(cat "/proc/$1/stat" | cut -d '(' -f 2 | cut -d ')' -f 1)" = "netdata" ] && return 0
718     return 1
719 }
720
721 stop_netdata_on_pid() {
722     local pid="${1}" ret=0 count=0
723
724     isnetdata ${pid} || return 0
725
726     printf >&2 "Stopping netdata on pid ${pid} ..."
727     while [ ! -z "$pid" -a ${ret} -eq 0 ]
728     do
729         if [ ${count} -gt 45 ]
730             then
731             echo >&2 "Cannot stop the running netdata on pid ${pid}."
732             return 1
733         fi
734
735         count=$(( count + 1 ))
736
737         run kill ${pid} 2>/dev/null
738         ret=$?
739
740         test ${ret} -eq 0 && printf >&2 "." && sleep 2
741     done
742
743     echo >&2
744     if [ ${ret} -eq 0 ]
745     then
746         echo >&2 "SORRY! CANNOT STOP netdata ON PID ${pid} !"
747         return 1
748     fi
749
750     echo >&2 "netdata on pid ${pid} stopped."
751     return 0
752 }
753
754 stop_all_netdata() {
755     local p myns ns
756
757     myns="$(readlink /proc/self/ns/pid 2>/dev/null)"
758
759     echo >&2 "Stopping a (possibly) running netdata..."
760
761     for p in $(cat "${NETDATA_RUN_DIR}/netdata.pid" 2>/dev/null) \
762         $(cat /var/run/netdata.pid 2>/dev/null) \
763         $(cat /var/run/netdata/netdata.pid 2>/dev/null) \
764         $(pidof netdata 2>/dev/null)
765     do
766         ns="$(readlink /proc/${p}/ns/pid 2>/dev/null)"
767
768         if [ -z "${myns}" -o -z "${ns}" -o "${myns}" = "${ns}" ]
769             then
770             stop_netdata_on_pid ${p}
771         fi
772     done
773 }
774
775 # -----------------------------------------------------------------------------
776 # check for systemd
777
778 issystemd() {
779     local pids p myns ns systemctl
780
781     # if the directory /etc/systemd/system does not exit, it is not systemd
782     [ ! -d /etc/systemd/system ] && return 1
783
784     # if there is no systemctl command, it is not systemd
785     systemctl=$(which systemctl 2>/dev/null || command -v systemctl 2>/dev/null)
786     [ -z "${systemctl}" -o ! -x "${systemctl}" ] && return 1
787
788     # if pid 1 is systemd, it is systemd
789     [ "$(basename $(readlink /proc/1/exe) 2>/dev/null)" = "systemd" ] && return 0
790
791     # if systemd is not running, it is not systemd
792     pids=$(pidof systemd 2>/dev/null)
793     [ -z "${pids}" ] && return 1
794
795     # check if the running systemd processes are not in our namespace
796     myns="$(readlink /proc/self/ns/pid 2>/dev/null)"
797     for p in ${pids}
798     do
799         ns="$(readlink /proc/${p}/ns/pid 2>/dev/null)"
800
801         # if pid of systemd is in our namespace, it is systemd
802         [ ! -z "${myns}" && "${myns}" = "${ns}" ] && return 0
803     done
804
805     # else, it is not systemd
806     return 1
807 }
808
809 installed_init_d=0
810 install_non_systemd_init() {
811     [ "${UID}" != 0 ] && return 1
812
813     local key="unknown"
814     if [ -f /etc/os-release ]
815         then
816         source /etc/os-release || return 1
817         key="${ID}-${VERSION_ID}"
818
819     elif [ -f /etc/centos-release ]
820         then
821         key=$(</etc/centos-release)
822     fi
823
824     if [ -d /etc/init.d -a ! -f /etc/init.d/netdata ]
825         then
826         if [ "${key}" = "gentoo" ]
827             then
828             run cp system/netdata-openrc /etc/init.d/netdata && \
829             run chmod 755 /etc/init.d/netdata && \
830             run rc-update add netdata default && \
831             installed_init_d=1
832         
833         elif [ "${key}" = "ubuntu-12.04" -o "${key}" = "ubuntu-14.04" ]
834             then
835             run cp system/netdata-lsb /etc/init.d/netdata && \
836             run chmod 755 /etc/init.d/netdata && \
837             run update-rc.d netdata defaults && \
838             run update-rc.d netdata enable && \
839             installed_init_d=1
840
841         elif [ "${key}" = "CentOS release 6.8 (Final)" ]
842             then
843             run cp system/netdata-init-d /etc/init.d/netdata && \
844             run chmod 755 /etc/init.d/netdata && \
845             run chkconfig netdata on && \
846             installed_init_d=1
847         fi
848     fi
849
850     return 0
851 }
852
853 started=0
854 if [ "${UID}" -eq 0 ]
855     then
856
857     if issystemd
858     then
859         # systemd is running on this system
860
861         if [ ! -f /etc/systemd/system/netdata.service ]
862         then
863             echo >&2 "Installing systemd service..."
864             run cp system/netdata.service /etc/systemd/system/netdata.service && \
865                 run systemctl daemon-reload && \
866                 run systemctl enable netdata
867         else
868             service netdata stop
869         fi
870
871         stop_all_netdata
872         service netdata restart && started=1
873     else
874         install_non_systemd_init
875     fi
876
877     if [ ${started} -eq 0 ]
878     then
879         # check if we can use the system service
880         service netdata stop
881         stop_all_netdata
882         service netdata restart && started=1
883         if [ ${started} -eq 0 ]
884         then
885             service netdata start && started=1
886         fi
887     fi
888 fi
889
890 if [ ${started} -eq 0 ]
891 then
892     # still not started...
893
894     stop_all_netdata
895
896     echo >&2 "Starting netdata..."
897     run ${NETDATA_PREFIX}/usr/sbin/netdata -P ${NETDATA_RUN_DIR}/netdata.pid "${@}"
898     if [ $? -ne 0 ]
899         then
900         echo >&2
901         echo >&2 "SORRY! FAILED TO START NETDATA!"
902         exit 1
903     else
904         echo >&2 "OK. NetData Started!"
905     fi
906
907     echo >&2
908 fi
909
910 # -----------------------------------------------------------------------------
911 # save a config file, if it is not already there
912
913 if [ ! -s "${NETDATA_PREFIX}/etc/netdata/netdata.conf" ]
914     then
915     echo >&2
916     echo >&2 "-------------------------------------------------------------------------------"
917     echo >&2
918     echo >&2 "Downloading default configuration from netdata..."
919     sleep 5
920
921     # remove a possibly obsolete download
922     [ -f "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" ] && rm "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new"
923
924     # disable a proxy to get data from the local netdata
925     export http_proxy=
926     export https_proxy=
927
928     # try wget
929     wget 2>/dev/null -O "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" "http://localhost:${NETDATA_PORT}/netdata.conf"
930     ret=$?
931
932     # try curl
933     if [ ${ret} -ne 0 -o ! -s "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" ]
934         then
935         curl -s -o "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" "http://localhost:${NETDATA_PORT}/netdata.conf"
936         ret=$?
937     fi
938
939     if [ ${ret} -eq 0 -a -s "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" ]
940         then
941         mv "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" "${NETDATA_PREFIX}/etc/netdata/netdata.conf"
942         echo >&2 "New configuration saved for you to edit at ${NETDATA_PREFIX}/etc/netdata/netdata.conf"
943
944         if [ "${UID}" -eq 0 ]
945             then
946             chown "${NETDATA_USER}" "${NETDATA_PREFIX}/etc/netdata/netdata.conf"
947         fi
948         chmod 0664 "${NETDATA_PREFIX}/etc/netdata/netdata.conf"
949     else
950         echo >&2 "Cannnot download configuration from netdata daemon using url 'http://localhost:${NETDATA_PORT}/netdata.conf'"
951         [ -f "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new" ] && rm "${NETDATA_PREFIX}/etc/netdata/netdata.conf.new"
952     fi
953 fi
954
955 # -----------------------------------------------------------------------------
956 # Check for KSM
957
958 ksm_is_available_but_disabled() {
959     cat <<KSM1
960
961 -------------------------------------------------------------------------------
962 Memory de-duplication instructions
963
964 You have kernel memory de-duper (called Kernel Same-page Merging,
965 or KSM) available, but it is not currently enabled.
966
967 To enable it run:
968
969 echo 1 >/sys/kernel/mm/ksm/run
970 echo 1000 >/sys/kernel/mm/ksm/sleep_millisecs
971
972 If you enable it, you will save 40-60% of netdata memory.
973
974 KSM1
975 }
976
977 ksm_is_not_available() {
978     cat <<KSM2
979
980 -------------------------------------------------------------------------------
981 Memory de-duplication not present in your kernel
982
983 It seems you do not have kernel memory de-duper (called Kernel Same-page
984 Merging, or KSM) available.
985
986 To enable it, you need a kernel built with CONFIG_KSM=y
987
988 If you can have it, you will save 40-60% of netdata memory.
989
990 KSM2
991 }
992
993 if [ -f "/sys/kernel/mm/ksm/run" ]
994     then
995     if [ $(cat "/sys/kernel/mm/ksm/run") != "1" ]
996         then
997         ksm_is_available_but_disabled
998     fi
999 else
1000     ksm_is_not_available
1001 fi
1002
1003 # -----------------------------------------------------------------------------
1004 # Check for version.txt
1005
1006 if [ ! -s web/version.txt ]
1007     then
1008     cat <<VERMSG
1009
1010 -------------------------------------------------------------------------------
1011 Version update check warning
1012
1013 The way you downloaded netdata, we cannot find its version. This means the
1014 Update check on the dashboard, will not work.
1015
1016 If you want to have version update check, please re-install it
1017 following the procedure in:
1018
1019 https://github.com/firehol/netdata/wiki/Installation
1020
1021 VERMSG
1022 fi
1023
1024 # -----------------------------------------------------------------------------
1025 # apps.plugin warning
1026
1027 if [ "${UID}" -ne 0 ]
1028     then
1029     cat <<SETUID_WARNING
1030
1031 -------------------------------------------------------------------------------
1032 apps.plugin needs privileges
1033
1034 Since you have installed netdata as a normal user, to have apps.plugin collect
1035 all the needed data, you have to give it the access rights it needs, by running
1036 either of the following sets of commands:
1037
1038 To run apps.plugin with escalated capabilities:
1039
1040     sudo chown root:${NETDATA_USER} "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
1041     sudo chmod 0750 "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
1042     sudo setcap cap_dac_read_search,cap_sys_ptrace+ep "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
1043
1044 or, to run apps.plugin as root:
1045
1046     sudo chown root "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
1047     sudo chmod 4755 "${NETDATA_PREFIX}/usr/libexec/netdata/plugins.d/apps.plugin"
1048
1049 apps.plugin is performing a hard-coded function of data collection for all
1050 running processes. It cannot be instructed from the netdata daemon to perform
1051 any task, so it is pretty safe to do this.
1052
1053 SETUID_WARNING
1054 fi
1055
1056 # -----------------------------------------------------------------------------
1057 # Keep un-install info
1058
1059 cat >netdata-uninstaller.sh <<UNINSTALL
1060 #!/usr/bin/env bash
1061
1062 # this script will uninstall netdata
1063
1064 if [ "\$1" != "--force" ]
1065     then
1066     echo >&2 "This script will REMOVE netdata from your system."
1067     echo >&2 "Run it again with --force to do it."
1068     exit 1
1069 fi
1070
1071 echo >&2 "Stopping a possibly running netdata..."
1072 for p in \$(pidof netdata); do kill \$p; done
1073 sleep 2
1074
1075 deletedir() {
1076     if [ ! -z "\$1" -a -d "\$1" ]
1077         then
1078         echo
1079         echo "Deleting directory '\$1' ..."
1080         rm -I -R "\$1"
1081     fi
1082 }
1083
1084 if [ ! -z "${NETDATA_PREFIX}" -a -d "${NETDATA_PREFIX}" ]
1085     then
1086     # installation prefix was given
1087
1088     deletedir "${NETDATA_PREFIX}"
1089
1090 else
1091     # installation prefix was NOT given
1092
1093     if [ -f "${NETDATA_PREFIX}/usr/sbin/netdata" ]
1094         then
1095         echo "Deleting ${NETDATA_PREFIX}/usr/sbin/netdata ..."
1096         rm -i "${NETDATA_PREFIX}/usr/sbin/netdata"
1097     fi
1098
1099     deletedir "${NETDATA_PREFIX}/etc/netdata"
1100     deletedir "${NETDATA_PREFIX}/usr/share/netdata"
1101     deletedir "${NETDATA_PREFIX}/usr/libexec/netdata"
1102     deletedir "${NETDATA_PREFIX}/var/lib/netdata"
1103     deletedir "${NETDATA_PREFIX}/var/cache/netdata"
1104     deletedir "${NETDATA_PREFIX}/var/log/netdata"
1105 fi
1106
1107 if [ -f /etc/logrotate.d/netdata ]
1108     then
1109     echo "Deleting /etc/logrotate.d/netdata ..."
1110     rm -i /etc/logrotate.d/netdata
1111 fi
1112
1113 if [ -f /etc/systemd/system/netdata.service ]
1114     then
1115     echo "Deleting /etc/systemd/system/netdata.service ..."
1116     rm -i /etc/systemd/system/netdata.service
1117 fi
1118
1119 if [ -f /etc/init.d/netdata ]
1120     then
1121     echo "Deleting /etc/init.d/netdata ..."
1122     rm -i /etc/init.d/netdata
1123 fi
1124
1125 getent passwd netdata > /dev/null
1126 if [ $? -eq 0 ]
1127     then
1128     echo
1129     echo "You may also want to remove the user netdata"
1130     echo "by running:"
1131     echo "   userdel netdata"
1132 fi
1133
1134 getent group netdata > /dev/null
1135 if [ $? -eq 0 ]
1136     then
1137     echo
1138     echo "You may also want to remove the group netdata"
1139     echo "by running:"
1140     echo "   groupdel netdata"
1141 fi
1142
1143 getent group docker > /dev/null
1144 if [ $? -eq 0 -a "${NETDATA_ADDED_TO_DOCKER}" = "1" ]
1145     then
1146     echo
1147     echo "You may also want to remove the netdata user from the docker group"
1148     echo "by running:"
1149     echo "   gpasswd -d netdata docker"
1150 fi
1151
1152 UNINSTALL
1153 chmod 750 netdata-uninstaller.sh
1154
1155 # -----------------------------------------------------------------------------
1156
1157 cat <<END
1158
1159
1160 -------------------------------------------------------------------------------
1161
1162 OK. NetData is installed and it is running.
1163
1164 -------------------------------------------------------------------------------
1165
1166 By default netdata listens on all IPs on port ${NETDATA_PORT},
1167 so you can access it with:
1168
1169 http://this.machine.ip:${NETDATA_PORT}/
1170
1171 To stop netdata, just kill it, with:
1172
1173   killall netdata
1174
1175 To start it, just run it:
1176
1177   ${NETDATA_PREFIX}/usr/sbin/netdata
1178
1179
1180 END
1181 echo >&2 "Uninstall script generated: ./netdata-uninstaller.sh"
1182
1183 if [ -d .git ]
1184     then
1185     cat >netdata-updater.sh.new <<REINSTALL
1186 #!/usr/bin/env bash
1187
1188 force=0
1189 [ "\${1}" = "-f" ] && force=1
1190
1191 export PATH="\${PATH}:${PATH}"
1192 export CFLAGS="${CFLAGS}"
1193
1194 INSTALL_UID="${UID}"
1195 if [ "\${INSTALL_UID}" != "\${UID}" ]
1196     then
1197     echo >&2 "This script should be run as user with uid \${INSTALL_UID} but it now runs with uid \${UID}"
1198     exit 1
1199 fi
1200
1201 # make sure we cd to the working directory
1202 cd "${REINSTALL_PWD}" || exit 1
1203
1204 # make sure there is .git here
1205 [ \${force} -eq 0 -a ! -d .git ] && echo >&2 "No git structures found at: ${REINSTALL_PWD} (use -f for force re-install)" && exit 1
1206
1207 # signal netdata to start saving its database
1208 # this is handy if your database is big
1209 pids=\$(pidof netdata)
1210 [ ! -z "\${pids}" ] && kill -USR1 \${pids}
1211
1212 tmp=
1213 if [ -t 2 ]
1214     then
1215     # we are running on a terminal
1216     # open fd 3 and send it to stderr
1217     exec 3>&2
1218 else
1219     # we are headless
1220     # create a temporary file for the log
1221     tmp=\$(mktemp /tmp/netdata-updater-log-XXXXXX.log)
1222     # open fd 3 and send it to tmp
1223     exec 3>\${tmp}
1224 fi
1225
1226 info() {
1227     echo >&3 "\$(date) : INFO: " "\${@}"
1228 }
1229
1230 emptyline() {
1231     echo >&3
1232 }
1233
1234 error() {
1235     echo >&3 "\$(date) : ERROR: " "\${@}"
1236 }
1237
1238 # this is what we will do if it fails (head-less only)
1239 failed() {
1240     error "FAILED TO UPDATE NETDATA : \${1}"
1241
1242     if [ ! -z "\${tmp}" ]
1243     then
1244         cat >&2 "\${tmp}"
1245         rm "\${tmp}"
1246     fi
1247     exit 1
1248 }
1249
1250 get_latest_commit_id() {
1251     git log -1           2>&3 |\\
1252         grep ^commit     2>&3 |\\
1253         head -n 1        2>&3 |\\
1254         cut -d ' ' -f 2  2>&3
1255 }
1256
1257 update() {
1258     [ -z "\${tmp}" ] && info "Running on a terminal - (this script also supports running headless from crontab)"
1259
1260     emptyline
1261
1262     if [ -d .git ]
1263         then
1264         info "Updating netdata source from github..."
1265
1266         last_commit="\$(get_latest_commit_id)"
1267         [ \${force} -eq 0 -a -z "\${last_commit}" ] && failed "CANNOT GET LAST COMMIT ID (use -f for force re-install)"
1268
1269         git pull >&3 2>&3 || failed "CANNOT FETCH LATEST SOURCE (use -f for force re-install)"
1270
1271         new_commit="\$(get_latest_commit_id)"
1272         if [ \${force} -eq 0 ]
1273             then
1274             [ -z "\${new_commit}" ] && failed "CANNOT GET NEW LAST COMMIT ID (use -f for force re-install)"
1275             [ "\${new_commit}" = "\${last_commit}" ] && info "Nothing to be done! (use -f to force re-install)" && exit 0
1276         fi
1277     elif [ \${force} -eq 0 ]
1278         then
1279         failed "CANNOT FIND GIT STRUCTURES IN \$(pwd) (use -f for force re-install)"
1280     fi
1281
1282     emptyline
1283     info "Re-installing netdata..."
1284     ${REINSTALL_COMMAND// --dont-wait/} --dont-wait >&3 2>&3 || failed "FAILED TO COMPILE/INSTALL NETDATA"
1285
1286     [ ! -z "\${tmp}" ] && rm "\${tmp}" && tmp=
1287     return 0
1288 }
1289
1290 # the installer updates this script - so we run and exit in a single line
1291 update && exit 0
1292 ###############################################################################
1293 ###############################################################################
1294 REINSTALL
1295     chmod 755 netdata-updater.sh.new
1296     mv -f netdata-updater.sh.new netdata-updater.sh
1297     echo >&2 "Update script generated   : ./netdata-updater.sh"
1298 elif [ -f "netdata-updater.sh" ]
1299     then
1300     rm "netdata-updater.sh"
1301 fi
1302
1303 banner "is installed and running now!"
1304 echo >&2 "  enjoy real-time performance and health monitoring..."
1305 echo >&2 
1306 exit 0