#!/bin/bash
set -e

function samba_delete_gpos()
{
    declare -a EOLE_GPOS_A_SUPPRIMER
    mapfile -t EOLE_GPOS_A_SUPPRIMER < <(CreoleGet eole_gpos_a_supprimer)
    
    echo "GPOS EOLE à supprimer"
    local NB_A_SUPPRIMER=${#EOLE_GPOS_A_SUPPRIMER[@]}
    for (( i = NB_A_SUPPRIMER; i > 0; ))
    do
        i=$(( i - 1))
        GPONAME="${EOLE_GPOS_A_SUPPRIMER[$i]}"
        if ! samba_delete_gpo "$GPONAME"
        then
            echo "* Delete '$GPONAME' Erreur ou n'existe pas"
            # j'ignore si elle a déjà été supprimée !
        #else
        #    echo "* Delete '$GPONAME' OK"
        fi
    done
}

function samba_import_gpo_with_templating()
{
    local GPONAME="${1}"
    local TEMPLATE
    local BASE
    local BASE_TMPL
    local CHEMIN_RELATIF
    local DESTINATION
    local TARGET
    local TEMPLATE_UTF16LE
    local DESTINATION_UTF16LE
    local SOURCE
    
    SOURCE="/usr/share/eole/gpo/${GPONAME}"
    if [ ! -d "$SOURCE" ]
    then
        echo "* La GPO '$GPONAME' n'a pas de source !"
        return
    fi

    echo "* '$GPONAME'"

    # je travaille dans un répertoire temporaire, donc copie avant !
    BASE="$(mktemp -d /tmp/XXXXXX)"
    cp -rf "${SOURCE}/" "${BASE}/"
    BASE="${BASE}/${GPONAME}"

    if [ -d "$BASE/tmpl" ]
    then
        echo "  Templatisation de la GPO '$GPONAME'"
        BASE_TMPL="$BASE/tmpl/"
        
        while IFS=';' read -r TEMPLATE
        do
            CHEMIN_RELATIF="${TEMPLATE/$BASE_TMPL/}"
            DESTINATION="$BASE/policy/$CHEMIN_RELATIF"
            TARGET=$(basename "$TEMPLATE")

            if [ -d "$TEMPLATE" ]
            then
                if [ ! -d "$DESTINATION" ]
                then
                    mkdir -p "$DESTINATION"
                fi
                continue
            fi
            
            if ! CreoleCat -s "${TEMPLATE}" -o "${BASE}/${TARGET}-utf8" 2>"$BASE/creolecat.err" 
            then
                if grep -q encodage "$BASE/creolecat.err"
                then
                    # au cas ou le template est UTF16-LE
                    iconv -f UTF-16LE -t UTF-8 "${TEMPLATE}" -o "${TEMPLATE}-utf8"
                    CreoleCat -s "${TEMPLATE}-utf8" -o "${BASE}/${TARGET}-utf8"
                else
                    cat "$BASE/creolecat.err"
                    # TODO : continue ou sortie ?
                    continue
                fi
            fi 
            
            if file "$DESTINATION" |grep -q "Unicode text, UTF-16, little-endian text"
            then
                DESTINATION_UTF16LE=oui
                iconv -f UTF-16LE -t UTF-8 "$DESTINATION" -o "${BASE}/actuel-${TARGET}-utf8"
            else
                DESTINATION_UTF16LE=non
                cat "${DESTINATION}" >"${BASE}/actuel-${TARGET}-utf8" 
            fi
            
            if ! diff "${BASE}/${TARGET}-utf8" "${BASE}/actuel-${TARGET}-utf8" >/dev/null
            then
                if [ "$DESTINATION_UTF16LE" == oui ]
                then
                    iconv -f UTF-8 -t UTF-16LE "${BASE}/${TARGET}-utf8" -o "${DESTINATION}"
                else
                    cat "${BASE}/${TARGET}-utf8" >"${DESTINATION}"
                fi
                echo "  ${CHEMIN_RELATIF} généré"
                
                # ICI je crée le fichier sémaphore qui va imposer la récréation de la GPO si elle existe 
                touch "/var/tmp/gpo-script/update_$GPONAME"
            fi
        done < <(find "$BASE_TMPL")
    fi

    # import sans lien avec une UO !
    if samba_import_gpo "$GPONAME" "${BASE}"
    then
        echo "* Import GPO $GPONAME : OK"
    else
        echo "* Import GPO $GPONAME : Erreur ($?)"
    fi
    if [ -n "$BASE" ]
    then
        /bin/rm -rf "$BASE"
    fi 
}

function samba_import_gpos_with_templating()
{
    declare -a EOLE_GPOS_A_CHARGER
    mapfile -t EOLE_GPOS_A_CHARGER < <(CreoleGet eole_gpos_a_charger)

    echo "Chargement des GPOS EOLE"
    local NB_A_CHARGER=${#EOLE_GPOS_A_CHARGER[@]}
    for (( i = NB_A_CHARGER; i > 0; ))
    do
        i=$(( i - 1))
        GPONAME="${EOLE_GPOS_A_CHARGER[$i]}"
        samba_import_gpo_with_templating "${GPONAME}"
    done
}

function samba_link_gpos()
{
    declare -a EOLE_GPOS_NAMES
    declare -a EOLE_GPOS_UO
    mapfile -t EOLE_GPOS_NAMES < <(CreoleGet eole_gpos_names)
    mapfile -t EOLE_GPOS_UO < <(CreoleGet eole_gpos_uo)
    
    echo "Liens GPOS EOLE / UO"
    local NB_GPOS_A_LIER=${#EOLE_GPOS_NAMES[@]}
    for (( i = NB_GPOS_A_LIER; i > 0; ))
    do
        i=$(( i - 1))
        GPONAME="${EOLE_GPOS_NAMES[$i]}"
        OU="${EOLE_GPOS_UO[$i]}"
        #echo "GPONAME='$GPONAME', UO='$OU'"
        
         if ! GPOID=$(gpo-tool helper show_by_name "$GPONAME" --attribut name -H "ldap://${AD_HOST_NAME}.${AD_REALM}" -U"$CREDENTIAL" )
        then
            #echo "* '$GPONAME' n'existe pas !"
            continue
        fi
        
        local NEW_DN="OU=${OU//\//,OU=},$BASEDN"
        if ! samba-tool ou list --full-dn |grep -q "${NEW_DN}"
        then
            echo "'$NEW_DN' n'existe pas !"
            continue
        fi

        if samba-tool gpo setlink "$NEW_DN" "$GPOID" -H "ldap://${AD_HOST_NAME}.${AD_REALM}" -U"${CREDENTIAL}" >/dev/null 2>/tmp/gpo_setlink.err
        then
            echo "  '$GPONAME' liée à '$NEW_DN' "
        else
            if grep -q 'already linked to this container' /tmp/gpo_setlink.err
            then
                echo "  '$GPONAME' liée à '$NEW_DN'"
            else
                echo "  '$GPONAME' impossible de lier la GPO à '$NEW_DN'"
                cat /tmp/gpo_setlink.err
            fi
        fi
    done
    samba_import_gpo_clean_after
}

function samba_gpo_load_credential()
{
    if [ -d /var/lib/lxc/addc/rootfs ]
    then
        # cas ScribeAD
        CONTAINER_ROOTFS="/var/lib/lxc/addc/rootfs"
        EST_SCRIBE_AD=oui
    else
        CONTAINER_ROOTFS=""
        EST_SCRIBE_AD=non
    fi
    
    #shellcheck disable=SC1091,SC1090
    . "$CONTAINER_ROOTFS/etc/eole/samba4-vars.conf"
    . "$CONTAINER_ROOTFS/usr/lib/eole/samba4.sh"

    BASEDN="DC=${AD_REALM//./,DC=}"
    GPO_ADMIN="gpo-${AD_HOST_NAME}"
    GPO_ADMIN_DN="${GPO_ADMIN}@${AD_REALM^^}"
    GPO_ADMIN_PWD_FILE=$(get_passwordfile_for_account "${GPO_ADMIN}")
    if [ ! -f "${GPO_ADMIN_PWD_FILE}" ]
    then
        echo "Warning:Le fichier ${GPO_ADMIN_PWD_FILE} est manquant"
        return 1
    fi
    ADMIN_PWD="$(cat "${GPO_ADMIN_PWD_FILE}")"
    CREDENTIAL="${GPO_ADMIN_DN}%${ADMIN_PWD}"
    return 0
}

function doMain()
{
    COMMANDE_A_EXECUTER=${1:-reconfigure}
    ACTIVER_EOLE_GPOS=$(CreoleGet activer_eole_gpos)
    if [ "$ACTIVER_EOLE_GPOS" != "oui" ]
    then
        echo "Pas de GPO EOLE d'après genconfig"
        return 0
    fi
    
    echo "Gestion des GPOS EOLE"
    if ! samba_gpo_load_credential
    then
        echo "Pas de gestion des GPOS EOLE sur les serveurs membres ou Dc Secondaires"
        return 0
    fi
    
    samba_delete_gpos
    samba_import_gpos_with_templating
    samba_link_gpos
    
    workaround_policies
    workaround_sysvol
    samba_import_gpo_clean_after
    return 0
}

# execute main si non sourcé
if [[ "${BASH_SOURCE[0]}" == "$0" ]]
then
   doMain "$@"
fi
