radicale2: Update CalDAV/CardDAV server to v2.x
Radicale 2.x adds support for many new clients, bug-fixes, etc so add v2 of this application. We do it as a separate package for those not ready to switch (it's not an straight inplace upgrade from 1.x). We do however CONFLICT with 1.x as they can't be run side-by-side on the same host (without containers for somesuch). Signed-off-by: Daniel F. Dickinson <cshored@thecshore.com>
This commit is contained in:
parent
483c9fceae
commit
615fa96f9c
4 changed files with 404 additions and 0 deletions
106
net/radicale2/Makefile
Normal file
106
net/radicale2/Makefile
Normal file
|
@ -0,0 +1,106 @@
|
|||
# This is free software, licensed under the GNU General Public License v2.
|
||||
# See /LICENSE for more information.
|
||||
|
||||
include $(TOPDIR)/rules.mk
|
||||
|
||||
PKG_NAME:=radicale2
|
||||
PKG_VERSION:=2.1.11
|
||||
PKG_RELEASE:=1
|
||||
PKG_MAINTAINER:=Daniel Dickinson <cshored@thecshore.com>
|
||||
|
||||
PKG_LICENSE:=GPL-3.0
|
||||
PKG_LICENSE_FILES:=COPYING
|
||||
|
||||
PKG_SOURCE:=Radicale-$(PKG_VERSION).tar.gz
|
||||
PKG_SOURCE_URL:=https://files.pythonhosted.org/packages/source/R/Radicale/
|
||||
PKG_HASH:=02273fcc6ae10e0f74aa12652e24d0001eec8dbf467d54ddb4dfcc2af7d7a5db
|
||||
PKG_BUILD_DIR:=$(BUILD_DIR)/radicale2-$(BUILD_VARIANT)-$(PKG_VERSION)
|
||||
|
||||
include $(INCLUDE_DIR)/package.mk
|
||||
include ../../lang/python/python3-package.mk
|
||||
|
||||
PKG_UNPACK:=$(HOST_TAR) -C $(PKG_BUILD_DIR) --strip-components=1 -xzf $(DL_DIR)/$(PKG_SOURCE)
|
||||
|
||||
define Package/radicale2/Default
|
||||
SECTION:=net
|
||||
CATEGORY:=Network
|
||||
SUBMENU:=Web Servers/Proxies
|
||||
URL:=http://radicale.org/
|
||||
TITLE:=Radicale 2.x CalDAV/CardDAV server
|
||||
MAINTAINER:=Daniel Dickinson <cshored@thecshore.com>
|
||||
endef
|
||||
|
||||
define Package/radicale2
|
||||
$(call Package/radicale2/Default)
|
||||
USERID:=radicale2=225:radicale2=225
|
||||
DEPENDS:=+python3 +python3-dateutil +python3-vobject +python3-setuptools
|
||||
CONFLICTS:=radicale
|
||||
VARIANT:=python3
|
||||
endef
|
||||
|
||||
define Package/radicale2-examples
|
||||
$(call Package/radicale2/Default)
|
||||
TITLE:=Radicale v2 example configs
|
||||
endef
|
||||
|
||||
define Package/radicale2-meta/description
|
||||
The Radicale Project is a CalDAV (calendar) and CardDAV (contact) server. It aims to be a light solution, easy to use, easy to install, easy to configure. As a consequence, it requires few software dependances and is pre-configured to work out-of-the-box.
|
||||
|
||||
The Radicale Project runs on most of the UNIX-like platforms (Linux, BSD, MacOS X) and Windows. It is known to work with Evolution, Lightning, iPhone and Android clients. It is free and open-source software, released under GPL version 3.
|
||||
endef
|
||||
|
||||
define Package/radicale2/description
|
||||
$(call Package/radicale2-meta/description)
|
||||
.
|
||||
This package contains the python files.
|
||||
endef
|
||||
|
||||
define Package/radicale2-examples/description
|
||||
$(call Package/radicale2-meta/description)
|
||||
.
|
||||
This package contains upstream configs for example purposes.
|
||||
endef
|
||||
|
||||
define Package/radicale2/conffiles
|
||||
/etc/config/radicale2
|
||||
/etc/radicale2/config
|
||||
/etc/radicale2/users
|
||||
/etc/radicale2/rights
|
||||
/etc/radicale2/logging
|
||||
endef
|
||||
|
||||
define Package/radicale2/preinst
|
||||
#!/bin/sh
|
||||
[ -n "$${IPKG_INSTROOT}" ] && exit 0 # if run within buildroot exit
|
||||
|
||||
# stop service if PKG_UPGRADE
|
||||
[ "$${PKG_UPGRADE}" = "1" ] && /etc/init.d/radicale2 stop >/dev/null 2>&1
|
||||
|
||||
exit 0 # suppress errors from stop command
|
||||
endef
|
||||
|
||||
define Py3Package/radicale2/filespec
|
||||
+|$(PYTHON3_PKG_DIR)
|
||||
+|/usr/bin/radicale2|0755
|
||||
endef
|
||||
|
||||
define Py3Package/radicale2/install
|
||||
$(INSTALL_DIR) $(1)/usr/bin
|
||||
$(INSTALL_BIN) $(PKG_INSTALL_DIR)/usr/bin/radicale $(PKG_INSTALL_DIR)/usr/bin/radicale2
|
||||
$(SED) 's,^#!.*python.*,#!/usr/bin/python$(PYTHON3_VERSION),' $(PKG_INSTALL_DIR)/usr/bin/radicale2
|
||||
$(INSTALL_DIR) $(1)/etc/config $(1)/etc/init.d
|
||||
$(INSTALL_CONF) ./files/radicale2.config $(1)/etc/config/radicale2
|
||||
$(INSTALL_BIN) ./files/radicale2.init $(1)/etc/init.d/radicale2
|
||||
endef
|
||||
|
||||
define Package/radicale2-examples/install
|
||||
$(INSTALL_DIR) $(1)/usr/share/radicale2
|
||||
$(INSTALL_DATA) $(PKG_BUILD_DIR)/config $(1)/usr/share/radicale2/config.example
|
||||
$(INSTALL_DATA) $(PKG_BUILD_DIR)/rights $(1)/usr/share/radicale2/rights.example
|
||||
$(INSTALL_DATA) $(PKG_BUILD_DIR)/logging $(1)/usr/share/radicale2/logging.example
|
||||
endef
|
||||
|
||||
$(eval $(call Py3Package,radicale2))
|
||||
$(eval $(call BuildPackage,radicale2))
|
||||
$(eval $(call BuildPackage,radicale2-src))
|
||||
$(eval $(call BuildPackage,radicale2-examples))
|
7
net/radicale2/files/radicale2.config
Normal file
7
net/radicale2/files/radicale2.config
Normal file
|
@ -0,0 +1,7 @@
|
|||
#config section server
|
||||
# list host 127.0.0.1:5232
|
||||
# list host ::1:5232
|
||||
|
||||
#config user
|
||||
#option name user1
|
||||
#option password password1
|
278
net/radicale2/files/radicale2.init
Executable file
278
net/radicale2/files/radicale2.init
Executable file
|
@ -0,0 +1,278 @@
|
|||
#!/bin/sh /etc/rc.common
|
||||
|
||||
START=80
|
||||
STOP=10
|
||||
|
||||
CFGDIR=/var/etc/radicale2
|
||||
SYSCFG=$CFGDIR/config
|
||||
USRCFG=$CFGDIR/users
|
||||
|
||||
DATADIR="/srv/radicale2/data"
|
||||
LOGDIR=""
|
||||
USE_PROCD=1
|
||||
|
||||
# we could start with empty configuration file using defaults
|
||||
[ -f ${IPKG_INSTROOT}/etc/config/radicale2 ] || touch ${IPKG_INSTROOT}/etc/config/radicale2
|
||||
|
||||
conf_line() {
|
||||
local cfgfile="$1"
|
||||
local option="$2"
|
||||
local value="$3"
|
||||
|
||||
if [ -n "$value" ]; then
|
||||
eval "echo '$2' = '$value' >>'$cfgfile'"
|
||||
fi
|
||||
}
|
||||
|
||||
conf_getline() {
|
||||
local cfg="$1"
|
||||
local cfgfile="$2"
|
||||
local option="$3"
|
||||
local defval="$4"
|
||||
local flag="$5"
|
||||
unset value
|
||||
|
||||
if [ "$flag" != "1" ]; then
|
||||
config_get value "$cfg" "$option" "$defval"
|
||||
conf_line "$cfgfile" "$option" "$value"
|
||||
else
|
||||
config_get_bool value "$cfg" "$option" "$defval"
|
||||
[ -z "$defval" ] && defval=1
|
||||
if [ "$value" -ne "$defval" ]; then
|
||||
if [ "$value" -ne 0 ]; then
|
||||
conf_line "$cfgfile" "$option" "True"
|
||||
else
|
||||
conf_line "$cfgfile" "$option" "False"
|
||||
fi
|
||||
fi
|
||||
fi
|
||||
}
|
||||
|
||||
build_hosts_line() {
|
||||
local val="$1"
|
||||
|
||||
append hostlist "$val" ", "
|
||||
}
|
||||
|
||||
conf_section() {
|
||||
local cfg="$1"
|
||||
local cfgfile="$2"
|
||||
local hostlist=""
|
||||
local value
|
||||
|
||||
echo "[$cfg]
|
||||
" >>$cfgfile
|
||||
|
||||
case $cfg in
|
||||
server)
|
||||
config_list_foreach "$cfg" host build_hosts_line
|
||||
conf_line "$tmpfile" hosts "$hostlist"
|
||||
conf_getline "$cfg" $tmpfile max_connections
|
||||
conf_getline "$cfg" $tmpfile max_conntent_length
|
||||
conf_getline "$cfg" $tmpfile timeout
|
||||
|
||||
conf_getline "$cfg" $tmpfile ssl 0 1
|
||||
if [ "$value" -eq 1 ]; then
|
||||
conf_getline "$cfg" $tmpfile certificate
|
||||
conf_getline "$cfg" $tmpfile key
|
||||
conf_getline "$cfg" $tmpfile certificate_authority
|
||||
conf_getline "$cfg" $tmpfile protocol
|
||||
conf_getline "$cfg" $tmpfile ciphers
|
||||
fi
|
||||
|
||||
conf_getline "$cfg" $tmpfile dns_lookup 1 1
|
||||
conf_getline "$cfg" $tmpfile realm
|
||||
;;
|
||||
encoding)
|
||||
conf_getline "$cfg" $tmpfile request
|
||||
conf_getline "$cfg" $tmpfile stock
|
||||
;;
|
||||
auth)
|
||||
conf_getline "$cfg" $tmpfile "type" htpasswd
|
||||
if [ "$value" = "htpasswd" ]; then
|
||||
conf_getline "$cfg" $tmpfile htpasswd_filename $CFGDIR/users
|
||||
conf_getline "$cfg" "$tmpfile" htpasswd_encryption plain
|
||||
fi
|
||||
|
||||
conf_getline "$cfg" "$tmpfile" delay
|
||||
;;
|
||||
rights)
|
||||
conf_getline "$cfg" "$tmpfile" "type"
|
||||
if [ "$value" = "from_file" ]; then
|
||||
conf_getline "$cfg" "$tmpfile" "file"
|
||||
fi
|
||||
;;
|
||||
storage)
|
||||
conf_getline "$cfg" $tmpfile filesystem_folder "$DATADIR"
|
||||
DATADIR="$value"
|
||||
conf_getline "$cfg" $tmpfile filesystem_locking 1 1
|
||||
conf_getline "$cfg" $tmpfile max_sync_token_age
|
||||
conf_getline "$cfg" $tmpfile filesystem_close_lock_file 0 1
|
||||
conf_getline "$cfg" $tmpfile hook
|
||||
;;
|
||||
web)
|
||||
conf_getline "$cfg" $tmpfile "type"
|
||||
;;
|
||||
logging)
|
||||
conf_getline "$cfg" "$tmpfile" config
|
||||
conf_getline "$cfg" "$tmpfile" debug 0 1
|
||||
conf_getline "$cfg" "$tmpfile" full_environment 0 1
|
||||
conf_getline "$cfg" "$tmpfile" mask_passwords 1 1
|
||||
;;
|
||||
headers)
|
||||
config_get "$cfg" "$tmpfile" cors
|
||||
if [ -n "$cors" ]; then
|
||||
echo "Access-Control-Allow-Origin = $cors" >>$tmpfile
|
||||
fi
|
||||
;;
|
||||
esac
|
||||
|
||||
echo "
|
||||
" >>$cfgfile
|
||||
}
|
||||
|
||||
add_missing_sections() {
|
||||
local cfgfile="$1"
|
||||
|
||||
for section in server encoding auth rights storage web logging headers; do
|
||||
if [ "$section" = "server" ]; then
|
||||
grep -q "\[$section\]" $cfgfile || echo "
|
||||
[$section]
|
||||
hosts = 0.0.0.0:5232, [::]:5232
|
||||
|
||||
" >>$cfgfile
|
||||
elif [ "$section" = "auth" ]; then
|
||||
grep -q "\[$section\]" $cfgfile || echo "
|
||||
[$section]
|
||||
type = htpasswd
|
||||
htpasswd_filename = $CFGDIR/users
|
||||
htpasswd_encryption = plain
|
||||
|
||||
" >>$cfgfile
|
||||
elif [ "$section" = "storage" ]; then
|
||||
grep -q "\[$section\]" $cfgfile || echo "
|
||||
[$section]
|
||||
filesystem_folder = $DATADIR
|
||||
|
||||
" >>$cfgfile
|
||||
else
|
||||
grep -q "\[$section\]" $cfgfile || echo "
|
||||
[$section]
|
||||
|
||||
" >>$cfgfile
|
||||
fi
|
||||
done
|
||||
}
|
||||
|
||||
add_user() {
|
||||
local cfg="$1"
|
||||
local tmpfile="$2"
|
||||
local name password
|
||||
|
||||
config_get name "$cfg" name
|
||||
config_get password "$cfg" password
|
||||
|
||||
[ -n "$name" ] && echo "$name:$password" >>$tmpfile
|
||||
}
|
||||
|
||||
build_users() {
|
||||
local tmpfile="$1"
|
||||
|
||||
# temporary config file
|
||||
# radicale2 needs read access
|
||||
chmod 0640 $tmpfile
|
||||
|
||||
config_foreach add_user user "$tmpfile"
|
||||
}
|
||||
|
||||
build_config() {
|
||||
local tmpfile=$(mktemp)
|
||||
local tmpfile2=$(mktemp)
|
||||
|
||||
# temporary config file
|
||||
# radicale2 need read access
|
||||
chmod 0640 $tmpfile
|
||||
|
||||
config_load radicale2
|
||||
config_foreach conf_section section $tmpfile
|
||||
add_missing_sections $tmpfile
|
||||
|
||||
build_users $tmpfile2
|
||||
|
||||
# move tmp to final
|
||||
mkdir -m0750 -p $CFGDIR
|
||||
cat $tmpfile >$SYSCFG
|
||||
rm -f $tmpfile
|
||||
cat $tmpfile2 >$USRCFG
|
||||
rm -f $tmpfile2
|
||||
}
|
||||
|
||||
set_permission() {
|
||||
# config file permissions (read access for group)
|
||||
chmod 0750 $CFGDIR
|
||||
chmod 0640 $SYSCFG
|
||||
chmod 0640 $USRCFG
|
||||
chgrp -R radicale2 $CFGDIR
|
||||
# data directory does not exist
|
||||
[ -d $DATADIR ] || {
|
||||
logger -p user.error -t "radicale2[----]" "Data directory '$DATADIR' does not exist. Startup failed !!!"
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
interface_triggers() {
|
||||
local action="$1"
|
||||
local triggerlist trigger
|
||||
|
||||
config_load radicale2
|
||||
config_get triggerlist server triggerlist
|
||||
|
||||
. /lib/functions/network.sh
|
||||
|
||||
if [ -n "$triggerlist" ]; then
|
||||
for trigger in $triggerlist; do
|
||||
if [ "$action" = "add_trigger" ]; then
|
||||
procd_add_interface_trigger "interface.*" "$trigger" /etc/init.d/radicale2 reload
|
||||
else
|
||||
network_is_up "$trigger" && return 0
|
||||
fi
|
||||
done
|
||||
else
|
||||
if [ "$action" = "add_trigger" ]; then
|
||||
procd_add_raw_trigger "interface.*.up" 2000 /etc/init.d/radicale2 reload
|
||||
else
|
||||
ubus call network.device status | grep -q '"up": true' && return 0
|
||||
fi
|
||||
fi
|
||||
[ "$action" = "add_trigger" ] || return 1
|
||||
}
|
||||
|
||||
start_service() {
|
||||
local haveinterface
|
||||
|
||||
if [ ! -r /etc/radicale2/config ]; then
|
||||
build_config
|
||||
set_permission
|
||||
fi
|
||||
|
||||
interface_triggers "check_interface_up" || return
|
||||
|
||||
procd_open_instance "radicale2"
|
||||
procd_set_param respawn
|
||||
procd_set_param stderr 1
|
||||
procd_set_param stdout 1
|
||||
if [ ! -r /etc/radicale2/config ]; then
|
||||
procd_set_param command /usr/bin/radicale2 --config="$SYSCFG"
|
||||
else
|
||||
procd_set_param command /usr/bin/radicale2 --config="/etc/radicale2/config"
|
||||
fi
|
||||
procd_set_param user radicale2
|
||||
procd_close_instance
|
||||
|
||||
return 0
|
||||
}
|
||||
|
||||
service_triggers() {
|
||||
interface_triggers "add_trigger"
|
||||
procd_add_reload_trigger "radicale2"
|
||||
}
|
13
net/radicale2/patches/110-disable-setup_requirements.patch
Normal file
13
net/radicale2/patches/110-disable-setup_requirements.patch
Normal file
|
@ -0,0 +1,13 @@
|
|||
Index: radicale2-python3-2.1.11/setup.py
|
||||
===================================================================
|
||||
--- radicale2-python3-2.1.11.orig/setup.py
|
||||
+++ radicale2-python3-2.1.11/setup.py
|
||||
@@ -67,7 +67,7 @@ setup(
|
||||
package_data={"radicale": WEB_FILES},
|
||||
entry_points={"console_scripts": ["radicale = radicale.__main__:run"]},
|
||||
install_requires=["vobject>=0.9.6", "python-dateutil>=2.7.3"],
|
||||
- setup_requires=pytest_runner,
|
||||
+ setup_requires=[],
|
||||
tests_require=tests_require,
|
||||
extras_require={
|
||||
"test": tests_require,
|
Loading…
Reference in a new issue