First Commit
[librecmc/package-feed.git] / net / radicale / files / radicale.init
1 #!/bin/sh /etc/rc.common
2 # Copyright (C) 2006-2016 OpenWrt.org
3
4 START=80
5 STOP=10
6
7 CFGDIR=/var/etc/radicale
8 SYSCFG=$CFGDIR/config
9 LOGCFG=$CFGDIR/logging
10
11 DATADIR="/srv/radicale"
12 LOGDIR=""
13
14 PGREP="ps | grep '[p]ython.*[r]adicale' 2>/dev/null | awk '{print \$1}' "
15
16 # we could start with empty configuration file using defaults
17 [ -f /etc/config/radicale ] || touch /etc/config/radicale
18
19 _uci2radicale() {
20         local _SYSTMP="$SYSCFG.tmp"
21         local _LOGTMP="$LOGCFG.tmp"
22         local _LOPT                             # list option name
23         local _LVAL                             # list option value
24         local _STYPE                            # section type
25         local _SNAME                            # section name
26         local _console_level="ERROR"            # logging console level
27         local _file_level="INFO"                # logging file level
28         local _file_path="/var/log/radicale"    # logging file path
29         local _file_maxbytes="8196"             # logging file maxBytes
30         local _file_backupcount="1"             # logging file backupCount
31         local _syslog_level="WARNING"           # logging syslog level
32
33         # write list values to config
34         _write_list() {
35                 _write_value "$_LOPT" "$_LVAL"  # there might be spaces in _LVAL
36                 _LOPT=""
37                 _LVAL=""
38         }
39
40         _write_value() {
41                 # $1    option
42                 # $2    value
43                 local __OPT=$1
44                 local __VAL=$2
45                 # section "server" ignore option "daemon" and "pid"
46                 [ "$_SNAME" = "server" -a "$__OPT" = "daemon" ] && return 0
47                 [ "$_SNAME" = "server" -a "$__OPT" = "pid" ] && return 0
48                 # section "logging" ignore option "config" (logging config file)
49                 [ "$_SNAME" = "logging" -a "$__OPT" = "config" ] && return 0
50                 # section "auth" ignore option "htpasswd_filename" (htpasswd file)
51                 [ "$_SNAME" = "auth" -a "$__OPT" = "htpasswd_filename" ] && return 0
52                 # section "rights" ignore option "file" (reg-based rights file)
53                 [ "$_SNAME" = "rights" -a "$__OPT" = "file" ] && return 0
54                 # section "headers" replace "_" with "-" in option (UCI problem)
55                 [ "$_SNAME" = "headers" ] && __OPT=$(echo "$__OPT" | sed -e "s#_#-#g")
56                 # save data driectory
57                 [ "$_SNAME" = "storage" -a "$__OPT" = "filesystem_folder" ] && DATADIR="$__VAL"
58                 # special handling for well-known, value needs single quotes
59                 [ "$_SNAME" = "well-known" -a "${__VAL#*\%\(}" != "$__VAL" ] && __VAL="'$__VAL'"
60                 # handling of log settings
61                 if [ "$_STYPE" = "logging" -a "$_SNAME" = "logger" ]; then
62                         eval "_$__OPT='$__VAL'" # set to environment for later use
63                 else
64                         # handle bool
65                         [ "$__VAL" = "0" ] && __VAL="False"
66                         [ "$__VAL" = "1" ] && __VAL="True"
67                         # append data to the corresponding section
68                         sed -i "/\[$_SNAME\]/a $__OPT = $__VAL" $_SYSTMP
69                 fi
70         }
71
72         # redefined callback for sections when calling config_load
73         config_cb() {
74                 # $1    "Type"
75                 # $2    "Name"
76                 # write out last list option
77                 [ -n "$_LOPT" ] && _write_list
78                 # mark invalid
79                 _STYPE=""
80                 _SNAME=""
81                 # check section type
82                 [ "$1" = "setting" -o "$1" = "logging" ] && {
83                         _STYPE="$1"
84                         _SNAME="$2"
85                 }
86                 # translate section name
87                 [ "$2" = "well_known" ] && _SNAME="well-known"
88                 return 0
89         }
90
91         # redefined callback for lists when calling config_load
92         list_cb() {
93                 # $1    name of variable
94                 # $2    value
95                 # invalid section type then ignore
96                 [ -z "$_STYPE" -o -z "$_SNAME" ] && return 0
97                 # write out last list option if new list starts
98                 [ -n "$_LOPT" -a "$_LOPT" != "$1" ] && _write_list
99                 # new list option
100                 if [ -z "$_LOPT" ]; then
101                         _LOPT="$1"
102                         _LVAL="$2"
103                 else
104                         _LVAL="$_LVAL, $2"
105                 fi
106                 return 0
107         }
108
109         # redefined callback for options when calling config_load
110         option_cb() {
111                 # $1    name of variable
112                 # $2    value
113                 local __OPT="$1"
114                 local __VAL="$2"
115                 # invalid section type then ignore
116                 [ -z "$_STYPE" -o -z "$_SNAME" ] && return 0
117                 # ignore list entrys will be handled by list_cb()
118                 [ "${__OPT#*_ITEM}" != "$__OPT" ]   && return 0 # ignore lists *_ITEM*
119                 [ "${__OPT#*_LENGTH}" != "$__OPT" ] && return 0 # ignore lists *_LENGTH
120                 # write out last list option and clear
121                 [ -n "$_LOPT" ] && _write_list
122                 # write to file
123                 _write_value "$__OPT" "$__VAL"  # there might be spaces in __VAL
124                 return 0
125         }
126
127         # temporary config file
128         # radicale need read access
129         mkdir -m0755 -p $CFGDIR
130
131         cp /etc/radicale/config.template  $_SYSTMP
132         config_load radicale    # calling above config_cb()/option_cb()/list_cb() and write into $_SYSTMP
133         sed -i "/\[logging\]/a config = /var/etc/radicale/logging" $_SYSTMP     # hard-code logging config
134         sed -i "/\[auth\]/a htpasswd_filename = /etc/radicale/users" $_SYSTMP   # hard-code htpasswd
135         sed -i "/\[rights\]/a file = /etc/radicale/rights" $_SYSTMP             # hard-code regexp-based rights
136
137         # temporary logging config file
138         cp /etc/radicale/logging.template $_LOGTMP
139         LOGDIR="$_file_path"
140         sed -i "/\[handler_console\]/a level = $_console_level" $_LOGTMP
141         sed -i "/\[handler_file\]/a level = $_file_level" $_LOGTMP
142         sed -i "/\[handler_file\]/a args = ('$_file_path/radicale','a',$_file_maxbytes,$_file_backupcount)" $_LOGTMP
143         sed -i "/\[handler_syslog\]/a level = $_syslog_level" $_LOGTMP
144
145         # move tmp to final
146         mv -f $_SYSTMP $SYSCFG
147         mv -f $_LOGTMP $LOGCFG
148 }
149
150 _set_permission() {
151         # config file permissions (read access for group)
152         chmod 644 $SYSCFG $LOGCFG
153         chgrp -R radicale $CFGDIR
154         # log directory (full access and owner)
155         [ -d $LOGDIR ] || mkdir -m0755 -p $LOGDIR
156         chown -R radicale:radicale $LOGDIR
157         # data directory does not exist
158         [ -d $DATADIR ] || {
159                 logger -p user.error -t "radicale[----]" "Data directory '$DATADIR' does not exists. Startup failed !!!"
160                 exit 1
161         }
162         chgrp -R radicale $DATADIR
163 }
164
165 boot() {
166         # wait a given time (default 10 seconds) before startup
167         # to wait for interfaces to come up / not using hotplug events during boot
168         _start() {
169                 [ $1 -gt 0 ] && sleep $1
170                 start
171         }
172
173         local _DELAY
174         _DELAY=$(uci_get "radicale" "system" "boot_delay" "10")
175         _start $_DELAY &
176         return 0
177 }
178
179 shutdown() {
180         rm -f /tmp/radicale.hotplug
181         stop
182 }
183
184 start() {
185         _running() {
186                 sleep 2         # give radicale time to completely come up
187                 local _PID=$(eval "$PGREP")
188                 kill -1 $_PID 2>/dev/null
189                 [ $? -eq 0 ] \
190                         && logger -p user.notice -t "radicale[$_PID]" "Service started successfully"\
191                         || logger -p user.warn -t "radicale[----]" "Service failed to start"
192         }
193
194         # if already running do nothing
195         local _PID=$(eval "$PGREP")
196         kill -1 $_PID 2>/dev/null && return 0
197
198         _uci2radicale
199         _set_permission
200
201         radicale --daemon --config=$SYSCFG
202         touch /tmp/radicale.hotplug
203
204         _running &      # check if running and syslog
205
206         return 0
207 }
208
209 reload() {
210         # reload is also used by luci
211         local _PID=$(eval "$PGREP")
212         kill -1 $_PID 2>/dev/null
213         if [ $? -eq 0 ]; then
214                 # only restart if already running
215                 restart
216         else
217                 # only start if enabled
218                 enabled && start
219         fi
220         return 0
221 }
222
223 stop() {
224         local _PID=$(eval "$PGREP")
225         [ -z "$_PID" ] && return 0      # not running
226         kill -15 $_PID 2>/dev/null
227         sleep 3                 # give time to shutdown
228         local _tmp=$(eval "$PGREP")
229         if [ -z "$_tmp" ]; then
230                 logger -p user.notice -t "radicale[$_PID]" "Service shutdown successfully"
231         else
232                 kill -9 $_tmp   # Normally never come here
233                 logger -p user.warn -t "radicale[----]" "Service shutdown FORCED"
234         fi
235         return 0
236 }