##@cooked comments # -*- coding: utf-8 mode: sh -*- vim:sw=4:sts=4:et:ai:si:sta:fenc=utf-8 ## Gestion du service apache (démarrage/arrêt), et de sa configuration ##@cooked nocomments ##@require base ##@require sysinfos uprovide apache urequire base sysinfos function __apache_prefixes_checkdir() { local dir for dir in "$@"; do if [ -d "$dir" ]; then echo "$dir" return 0 fi done return 1 } function __apache_prefixes_checkfile() { local file for file in "$@"; do if [ -f "$file" ]; then echo "$file" return 0 fi done return 1 } function __apache_prefixes_checkexec() { local exec for exec in "$@"; do if [ -x "$exec" ]; then echo "$exec" return 0 fi done return 1 } function get_default_apachebin_prefix() { __apache_prefixes_checkexec /usr/sbin/{apache2,apache,httpd} } function get_default_apacheversion_prefix() { [ -n "$APACHEBIN" ] || return local version="$($APACHEBIN -v | grep version:)" if [[ "$version" == *1.3* ]]; then echo "" elif [[ "$version" == *2.0* ]]; then echo "2" elif [[ "$version" == *2.2* ]]; then echo "2.2" elif [[ "$version" == *2.4* ]]; then echo "2.4" fi } function get_default_apachectl_prefix() { [ -n "$APACHEBIN" ] || return __apache_prefixes_checkexec "$(dirname "$APACHEBIN")"/apache*ctl } function get_default_apachelogdir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir /var/log/{apache2,httpd} elif check_sysinfos -s linux; then if check_sysinfos -d debianlike; then __apache_prefixes_checkdir /var/log/{apache2,apache} elif check_sysinfos -d redhatlike; then __apache_prefixes_checkdir /var/log/httpd elif check_sysinfos -d gentoo; then # XXX à vérifier __apache_prefixes_checkdir /var/log/{apache{2,},httpd} fi fi } function get_default_apachesslcertsdir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir /etc/{apache2,httpd}/ssl.crt elif check_sysinfos -s linux; then __apache_prefixes_checkdir /etc/ssl/certs /etc/pki/tls/certs /etc/httpd/conf/ssl.crt fi } function get_default_apachesslkeysdir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir /etc/{apache2,httpd}/ssl.key elif check_sysinfos -s linux; then __apache_prefixes_checkdir /etc/ssl/private /etc/pki/tls/private /etc/httpd/conf/ssl.key fi } function get_default_apacheconfdir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir /etc/{apache2,httpd} elif check_sysinfos -s linux; then if check_sysinfos -d debianlike; then __apache_prefixes_checkdir /etc/{apache{2,,-ssl},httpd} elif check_sysinfos -d redhatlike; then __apache_prefixes_checkdir /etc/httpd elif check_sysinfos -d gentoo; then __apache_prefixes_checkdir /etc/{apache{2,},httpd} fi fi } function get_default_apacheconf_prefix() { [ -n "$APACHECONFDIR" ] || return __apache_prefixes_checkfile "$APACHECONFDIR"/{apache2,{,conf/}httpd}.conf } function get_default_apacheavsitesdir_prefix() { [ -n "$APACHECONFDIR" ] || return if check_sysinfos -s darwin; then __apache_prefixes_checkdir "$APACHECONFDIR/sites_disabled" elif check_sysinfos -d debianlike gentoo; then __apache_prefixes_checkdir "$APACHECONFDIR/sites-available" fi } function get_default_apachesitesdir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir "$APACHECONFDIR/sites" elif check_sysinfos -d debianlike gentoo; then __apache_prefixes_checkdir "$APACHECONFDIR/sites-enabled" fi } function get_default_htdocsdir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir /Library/WebServer/Documents elif check_sysinfos -s linux; then if check_sysinfos -d debianlike; then __apache_prefixes_checkdir /var/www elif check_sysinfos -d redhatlike; then __apache_prefixes_checkdir /var/www/html elif check_sysinfos -d gentoo; then __apache_prefixes_checkdir /var/www/localhost/htdocs fi fi } function get_default_cgibindir_prefix() { if check_sysinfos -s darwin; then __apache_prefixes_checkdir /Library/WebServer/CGI-Executables elif check_sysinfos -s linux; then if check_sysinfos -d debianlike; then __apache_prefixes_checkdir /usr/lib/cgi-bin elif check_sysinfos -d redhatlike; then __apache_prefixes_checkdir /var/www/cgi-bin elif check_sysinfos -d gentoo; then __apache_prefixes_checkdir /var/www/localhost/cgi-bin fi fi } __apache_prefixes= function __compute_apache_prefixes() { [ -n "$__apache_prefixes" ] && return APACHEBIN="${APACHEBIN:-$(get_default_apachebin_prefix)}" APACHEVERSION="${APACHEVERSION:-$(get_default_apacheversion_prefix)}" APACHECTL="${APACHECTL:-$(get_default_apachectl_prefix)}" APACHELOGDIR="${APACHELOGDIR:-$(get_default_apachelogdir_prefix)}" APACHESSLCERTSDIR="${APACHESSLCERTSDIR:-$(get_default_apachesslcertsdir_prefix)}" APACHESSLKEYSDIR="${APACHESSLKEYSDIR:-$(get_default_apachesslkeysdir_prefix)}" APACHECONFDIR="${APACHECONFDIR:-$(get_default_apacheconfdir_prefix)}" APACHECONF="${APACHECONF:-$(get_default_apacheconf_prefix)}" APACHEAVSITESDIR="${APACHEAVSITESDIR:-$(get_default_apacheavsitesdir_prefix)}" APACHESITESDIR="${APACHESITESDIR:-$(get_default_apachesitesdir_prefix)}" HTDOCSDIR="${HTDOCSDIR:-$(get_default_htdocsdir_prefix)}" CGIBINDIR="${CGIBINDIR:-$(get_default_cgibindir_prefix)}" __apache_prefixes=1 } UTOOLS_PREFIXES=("${UTOOLS_PREFIXES[@]}" APACHEBIN APACHEVERSION APACHECTL APACHELOGDIR APACHESSLCERTSDIR APACHESSLKEYSDIR APACHECONFDIR APACHECONF APACHEAVSITESDIR APACHESITESDIR HTDOCSDIR CGIBINDIR) function compute_apache_prefixes() { __compute_apache_prefixes } function recompute_apache_prefixes() { __apache_prefixes= __compute_apache_prefixes } function get_APACHEBIN_prefix() { __compute_apache_prefixes echo "$APACHEBIN" } function get_APACHEVERSION_prefix() { __compute_apache_prefixes echo "$APACHEVERSION" } function get_APACHECTL_prefix() { __compute_apache_prefixes echo "$APACHECTL" } function get_APACHELOGDIR_prefix() { __compute_apache_prefixes echo "$APACHELOGDIR" } function get_APACHESSLCERTSDIR_prefix() { __compute_apache_prefixes echo "$APACHESSLCERTSDIR" } function get_APACHESSLKEYSDIR_prefix() { __compute_apache_prefixes echo "$APACHESSLKEYSDIR" } function get_APACHECONFDIR_prefix() { __compute_apache_prefixes echo "$APACHECONFDIR" } function get_APACHECONF_prefix() { __compute_apache_prefixes echo "$APACHECONF" } function get_APACHEAVSITESDIR_prefix() { __compute_apache_prefixes echo "$APACHEAVSITESDIR" } function get_APACHESITESDIR_prefix() { __compute_apache_prefixes echo "$APACHESITESDIR" } function get_HTDOCSDIR_prefix() { __compute_apache_prefixes echo "$HTDOCSDIR" } function get_CGIBINDIR_prefix() { __compute_apache_prefixes echo "$CGIBINDIR" } function __apache_resolvcert() { [ -n "$__rc_dir" ] || __rc_dir="$(dirname "$__rc_conf")" eval "$( source "$__rc_conf" set_var_cmd __rc_cert "$cert" set_var_cmd __rc_key "$key" set_var_cmd __rc_ca "$ca" )" [ -n "$__rc_cert" ] && __rc_cert="$(abspath "$__rc_cert" "$__rc_dir")" [ -n "$__rc_key" ] && __rc_key="$(abspath "$__rc_key" "$__rc_dir")" [ -n "$__rc_ca" ] && __rc_ca="$(abspath "$__rc_ca" "$__rc_dir")" } function __apache_checkvars() { if [ -n "$__rc_cert" -a -z "$__rc_key" ]; then local __rc_name __rc_ext splitname "$__rc_cert" __rc_name __rc_ext if [ "$__rc_ext" == "crt" -o "$__rc_ext" == "pem" ]; then __rc_key="$__rc_name.key" enote "La clé privée n'a pas été spécifiée. La valeur $(ppath "$__rc_key") sera utilisée" else eerror "Impossible de trouver la clé privée correspondant au certificat $(ppath "$__rc_cert")" return 1 fi fi if [ -z "$__rc_cert" -a -z "$__rc_ca" ]; then eerror "Vous devez spécifier le certificat à installer" return 1 elif [ -z "$__rc_cert" ]; then eattention "Seul le certificat autorité a été spécifié." elif [ -z "$__rc_ca" ]; then ewarn "Aucun certificat autorité n'a pas été spécifié. Cela ne peut marcher que si le certificat est autosigné" fi local i for i in "$__rc_cert" "$__rc_key" "$__rc_ca"; do [ -n "$i" ] || continue [ -f "$i" ] || { eerror "$i: Fichier introuvable" return 1 } done } function apache_resolvecert() { # Calculer l'emplacement des certificats correspondant aux arguments $1 et # $2 (qui correspondent aux options --conf et --dir de apache_addcert()), # puis initialiser les variables $3(=cert), $4(=key) et $5(=ca) local __rc_conf="$1" __rc_dir="$2" local __rc_cert __rc_key __rc_ca __apache_resolvcert __apache_checkvars || return 1 set_var "${3:-cert}" "$__rc_cert" set_var "${4:-key}" "$__rc_key" set_var "${5:-ca}" "$__rc_ca" } function apache_addcert() { function __apache_addcert_display_help() { uecho "apache_addcert: Installer un certificat sur le serveur USAGE apache_addcert [options] [cert.pem [cert.key [ca.pem]]] OPTIONS --conf certsconf --dir certsdir Spécifier un fichier de configuration et un répertoire depuis lesquels prendre les informations sur les certificats à utiliser. Le fichier de configuration doit définir les variables cert, key et ca avec les noms des fichiers contenant respectivement le certificat, la clé privée, et les certificats autorités, exprimés relativement au répertoire certsdir. Si ces options ne sont pas spécifiées, les fichiers doivent être donnés sur la ligne de commande. --out-cert cert --out-key key --out-ca ca Au lieu d'installer les certificats, placer les chemins vers les fichiers correspondant dans les variables spécifiées" } eval "$(utools_local)" local action=install local certsconf certsdir cert key ca local __out_cert __out_key __out_ca parse_opts "${PRETTYOPTS[@]}" \ --help '$exit_with __apache_addcert_display_help' \ -C:,--conf: certsconf= \ -d:,--dir: certsdir= \ --out-cert: '$set@ __out_cert; action=dump' \ --out-key: '$set@ __out_key; action=dump' \ --out-ca: '$set@ __out_ca; action=dump' \ @ args -- "$@" && set -- "${args[@]}" || die "$args" local __rc_conf __rc_dir local __rc_cert __rc_key __rc_ca if [ -n "$certsconf" ]; then __rc_conf="$certsconf" __rc_dir="$certsdir" __apache_resolvconf __apache_checkvars || return 1 else __rc_cert="$1" __rc_key="$2" __rc_ca="$3" __apache_checkvars || return 1 fi cert="$__rc_cert" key="$__rc_key" ca="$__rc_ca" if [ -n "$cert" ]; then estepi "Certificat: $(ppath "$cert")" estepi "Clé privée: $(ppath "$key")" fi [ -n "$ca" ] && estepi "CAutorités: $(ppath "$ca")" ask_yesno "Voulez-vous continuer?" O || return 1 urequire install etitle "Installation des certificats" certsdir="$(get_APACHESSLCERTSDIR_prefix)" keysdir="$(get_APACHESSLKEYSDIR_prefix)" if [ ! -d "$certsdir" ]; then mkdir -p "$certsdir" || return 1 chmod 755 "$certsdir" || return 1 fi if [ ! -d "$keysdir" ]; then mkdir -p "$keysdir" || return 1 chmod 710 "$keysdir" || return 1 fi if [ -n "$cert" ]; then copy_replace "$cert" "$certsdir" || return 1 chmod 644 "$certsdir/$(basename "$cert")" || return 1 copy_replace "$key" "$keysdir" || return 1 chmod 640 "$keysdir/$(basename "$key")" || return 1 fi if [ -n "$ca" ]; then copy_replace "$ca" "$certsdir" || return 1 chmod 644 "$certsdir/$(basename "$ca")" || return 1 fi eend return 0 } function apache_autoconf() { function __apache_autoconf_display_help() { uecho "apache_autoconf: Mettre à jour la configuration d'apache USAGE apache_autoconf AUTOCONFDIR [CERTSDIR] AUTOCONFDIR peut contenir les fichiers et répertoires suivants, qui sont tous optionnels: - modules.conf la liste des modules qu'il faut activer. Si un module n'existe pas dans ce fichier, ou si ce fichier n'existe pas, aucune modification n'est effectuée. Si un module est de la forme -module, il est désactivé. Si un module est de la forme +module, il est activé. Cette syntaxe permet de supporter les modules dont le nom commencerait par '-' - sites.conf la liste des sites qu'il faut activer. Si un site ne figure pas dans ce fichier, il est désactivé. Si ce fichier n'existe pas, tous les sites existant sont activés. - tous les autres fichiers sont copiés tels quels dans /etc/apache2. Notamment, apache2.conf est le fichier de configuration principal d'apache et ports.conf le fichier de configuration des ports d'écoute. - modules/ le répertoire des configurations de modules à installer. Les fichiers de ce répertoire sont de la forme MODULE.conf et sont installés dans le répertoire /etc/apache2/mods-available. Il faut mentioner le module dans le fichier modules.conf pour l'activer. - sites/ le répertoire des sites à installer. Les fichiers de ce répertoire sont de la forme NAME.conf pour les sites écoutant en clair, et NAME.ssl.conf pour les sites écoutant en https. Pour chaque site NAME.ssl.conf, un fichier NAME-certs.conf doit exister dans certsconf/ Dans les fichiers NAME.ssl.conf, les valeurs @@cert@@, @@key@@ et @@ca@@ sont respectivement remplacées par l'emplacement des fichiers de certificats définis dans les fichiers correspondants NAME-certs.conf - cgi-bin/ le répertoire des scripts cgi à installer - www/ le répertoire qui contient les fichiers du serveur web à installer dans l'emplacement par défaut. - certsconf/ le répertoire qui contient la configuration pour les certificats à installer. Si ce répertoire existe, il faut spécifier CERTSDIR Les fichiers de ce répertoire sont de la forme NAME-certs.conf et chacun d'eux correspondant en principe à un fichier NAME.ssl.conf dans sites/ - RewriteRules/ le répertoire qui contient la configuration de réécriture. Tous les fichiers RewriteRules*.conf de ce répertoire sont copiés dans /etc/apache2 IMPORTANT: Cette fonction n'est pour le moment supporté que sur debian OPTIONS --confdir CONFDIR Spécifier l'emplacement des fichiers de configuration apache ainsi que modules.conf et sites.conf Par défaut, utiliser AUTOCONFDIR --modulesdir MODULESDIR Spécifier l'emplacement des fichiers de configuration des modules. Par défaut, utiliser AUTOCONFDIR/modules si ce répertoire existe. --sitesdir SITESDIR Spécifier l'emplacement des fichiers de configuration des sites. Par défaut, utiliser AUTOCONFDIR/sites si ce répertoire existe. --cgibindir CGIBINDIR Spécifier l'emplacement des scripts cgi à installer. Par défaut, utiliser AUTOCONFDIR/cgi-bin si ce répertoire existe. --wwwdir WWWDIR Spécifier l'emplacement des fichiers du serveur web Par défaut, utiliser AUTOCONFDIR/www si ce répertoire existe. --certsconfdir CERTSCONFDIR Spécifier l'emplacement des fichiers de configuration des certificats. Par défaut, utiliser AUTOCONFDIR/certsconf si ce répertoire existe. Il faut alors spécifier aussi CERTSDIR, l'emplacement des certificats à installer. --rrdir RRDIR Spécifier l'emplacement des fichiers de réécriture. Par défaut, utiliser AUTOCONFDIR/RewriteRules si ce répertoire existe. --no-restart Ne pas redémarrer apache en cas de modification de la configuration" } eval "$(utools_local)" local autoconfdir certsdir confdir modulesdir sitesdir cgibindir wwwdir certsconfdir rrdir local restart=1 parse_opts "${PRETTYOPTS[@]}" \ --help '$exit_with __apache_autoconf_display_help' \ --confdir: confdir= \ --modulesdir: modulesdir= \ --sitesdir: sitesdir= \ --cgibindir: cgibindir= \ --wwwdir: wwwdir= \ --certsconfdir: certsconfdir= \ --rrdir: rrdir= \ --no-restart restart= \ @ args -- "$@" && set -- "${args[@]}" || die "$args" if ! check_sysinfos -s linux -d debian; then eerror "apache_autoconf n'est supporté que sur Debian linux" return 1 fi urequire install compute_apache_prefixes autoconfdir="$1" [ -n "$autoconfdir" ] || { eerror "Vous devez spécifier le répertoire de base de la configuration apache" return 1 } certsdir="$2" if [ -z "$confdir" -o -z "$modulesdir" -o -z "$sitesdir" \ -o -z "$cgibindir" -o -z "$wwwdir" -o -z "$certsconfdir" \ -o -z "$rrdir" ]; then [ -d "$autoconfdir" ] || { eerror "$autoconfdir: répertoire invalide" return 1 } fi [ -n "$confdir" ] || confdir="$autoconfdir" [ -n "$modulesdir" ] || modulesdir="$autoconfdir/modules" [ -n "$sitesdir" ] || sitesdir="$autoconfdir/sites" [ -n "$cgibindir" ] || cgibindir="$autoconfdir/cgi-bin" [ -n "$wwwdir" ] || wwwdir="$autoconfdir/www" [ -n "$certsconfdir" ] || certsconfdir="$autoconfdir/certsconf" [ -n "$rrdir" ] || rrdir="$autoconfdir/RewriteRules" if [ -d "$certsconfdir" ]; then if [ -z "$certsdir" ]; then eerror "CERTSDIR est requis si --certsconfdir est spécifié" return 1 elif [ ! -d "$certsdir" ]; then eerror "$certsdir: répertoire invalide" return 1 fi fi local modified conf if [ -d "$certsconfdir" ]; then local -a certsconfs local certsconf cert key ca etitle "Installation des certificats" array_lsfiles certsconfs "$certsconfdir" "*.conf" for certsconf in "${certsconfs[@]}"; do apache_resolvecert "$certsconf" "$certsdir" cert key ca || return 1 apache_addcert -y "$cert" "$key" "$ca" modified=1 done eend fi if [ -d "$modulesdir" ]; then local -a confs local conf etitle "Installation des configurations des modules" array_from_lines confs "$(list_files "$modulesdir" "*.conf")" for conf in "${confs[@]}"; do estep "$conf" copy_update "$modulesdir/$conf" "$APACHECONFDIR/mods-available/$conf" && modified=1 done eend fi if [ -d "$rrdir" ]; then local -a confs local conf etitle "Installation des règles de réécriture" array_from_lines confs "$(list_files "$rrdir" "RewriteRules*.conf")" for conf in "${confs[@]}"; do estep "$conf" copy_update "$rrdir/$conf" "$APACHECONFDIR/$conf" && modified=1 done eend fi local -a enablesites disablesites if [ -d "$sitesdir" ]; then local -a confs local conf confname destconf certsconf tmpconf etitle "Installation des sites" array_lsfiles confs "$sitesdir" "*.conf" for conf in "${confs[@]}"; do confname="$(basename "$conf")" destconf="$confname" certsconf= if [ "${destconf%.ssl.conf}" != "$destconf" ]; then if [ -d "$certsconfdir" ]; then certsconf="${destconf%.ssl.conf}-certs.conf" else ewarn "$conf: fichier ignoré parce que --certsconfdir n'a pas été spécifié" fi fi case "$destconf" in default.conf) destconf=default;; default.ssl.conf) destconf=default-ssl;; esac if [ -n "$certsconf" ]; then certsconf="$certsconfdir/$certsconf" if [ -f "$certsconf" ]; then apache_resolvecert "$certsconf" "$certsdir" cert key ca || return 1 ac_set_tmpfile tmpconf sed "\ s#@@cert@@#$APACHESSLCERTSDIR/$(basename "$cert")#g s#@@key@@#$APACHESSLKEYSDIR/$(basename "$key")#g s#@@ca@@#$APACHESSLCERTSDIR/$(basename "$ca")#g " <"$conf" >"$tmpconf" copy_update "$tmpconf" "$APACHEAVSITESDIR/$destconf" else eerror "$(ppath "$certsconf"): fichier introuvable. Il a été ignoré" fi else copy_update "$conf" "$APACHEAVSITESDIR/$destconf" fi enablesites=("${enablesites[@]}" "$destconf") modified=1 done eend fi if [ -d "$confdir" ]; then local -a confs local conf etitle "Configuration de base" array_from_lines confs "$(list_files "$confdir")" for conf in "${confs[@]}"; do case "$conf" in modules.conf|sites.conf) continue;; esac estep "$conf" copy_update "$confdir/$conf" "$APACHECONFDIR/$conf" && modified=1 done if [ -f "$confdir/modules.conf" ]; then local -a modules local module array_from_lines modules "$(<"$confdir/modules.conf" filter_conf)" for module in "${modules[@]}"; do if [ "${module#-}" != "$module" ]; then module="${module#-}" if a2dismod "$module"; then estep "Désactivation du module $module" modified=1 fi else module="${module#+}" if a2enmod "$module"; then estep "Activation du module $module" modified=1 fi fi done fi if [ -f "$confdir/sites.conf" ]; then local -a sitesconfs; local sitesconf array_from_lines sitesconfs "$(<"$confdir/sites.conf" filter_conf)" if [ ${#sitesconfs[*]} -gt 0 ]; then # si une configuration existe, ignorer la configuration # automatique enablesites=() disablesites=() for sitesconf in "${sitesconfs[@]}"; do if [ "${sitesconf#+}" != "$sitesconf" ]; then array_del disablesites "${sitesconf#+}" array_add enablesites "${sitesconf#+}" elif [ "${sitesconf#-}" != "$sitesconf" ]; then array_del enablesites "${sitesconf#-}" array_add disablesites "${sitesconf#-}" else array_del disablesites "$sitesconf" array_add enablesites "$sitesconf" fi done fi fi eend fi if [ -d "$cgibindir" ]; then etitle "Installation des scripts CGI" cpdirnovcs "$cgibindir" "$CGIBINDIR" eend fi if [ -d "$wwwdir" ]; then etitle "Installation des fichiers du serveur web" cpdirnovcs "$wwwdir" "$HTDOCSDIR" eend fi if [ -n "${enablesites[*]}" -o -n "${disablesites[*]}" ]; then etitle "(dés)Activation des sites" local site for site in "${enablesites[@]}"; do a2ensite "$site" done for site in "${disablesites[@]}"; do a2dissite "$site" done eend fi if [ -n "$modified" -a -n "$restart" ]; then estep "Redémarrage d'apache" "$APACHECTL" restart fi }