#
# Copyright (C) 2020-2023 Lin Song <linsongui@gmail.com>
#
# This work is licensed under the Creative Commons Attribution-ShareAlike 3.0
# Unported License: http://creativecommons.org/licenses/by-sa/3.0/
#
# Attribution required: please include my name in any derivative and let me
# know how you have improved it!

name: test_set_2

on: workflow_call

jobs:
  test_set_2:
    runs-on: ubuntu-20.04
    if: github.repository_owner == 'hwdsl2'
    strategy:
      matrix:
        os_version: ["ubuntu:22.04", "ubuntu:20.04", "ubuntu:18.04", "debian:12", "debian:11", "debian:10", "alpine:3.17", "alpine:3.18"]
      fail-fast: false
    container:
      image: ${{ matrix.os_version }}
      options: --cap-add=NET_ADMIN --device=/dev/ppp
    steps:
      - uses: actions/checkout@v3
        with:
          persist-credentials: false
      - name: Test
        run: |
          set -ex

          os_type=""
          [ -f /etc/os-release ] && os_type=$(. /etc/os-release && printf '%s' "$ID")
          [ -z "$os_type" ] && exit 1

          log1=/var/log/auth.log
          if [ "$os_type" = "alpine" ]; then
            log2=/var/log/messages
          else
            log2=/var/log/syslog
          fi

          restart_ipsec() {
            if [ "$os_type" = "alpine" ]; then
              ipsec whack --shutdown || true
              ipsec pluto --config /etc/ipsec.conf
            fi
            echo "Waiting for IPsec to restart."
            count=0
            while ! grep -q "pluto\[$(cat /var/run/pluto/pluto.pid)\]: listening for IKE messages" "$log1"; do
              [ "$count" -ge "30" ] && { echo "IPsec failed to start."; exit 1; }
              count=$((count+1))
              printf '%s' '.'
              sleep 0.5
            done
            echo
          }

          restart_fail2ban() {
            rm -f /var/log/fail2ban.log
            service fail2ban restart
            echo "Waiting for Fail2ban to restart."
            count=0
            while ! grep -qs -E "Jail '(sshd?|ssh-iptables)' started" /var/log/fail2ban.log; do
              [ "$count" -ge "30" ] && { echo "Fail2ban failed to start."; exit 1; }
              count=$((count+1))
              printf '%s' '.'
              sleep 0.5
            done
            echo
          }

          mkdir -p /opt/src
          cd /opt/src
          ls -ld "$GITHUB_WORKSPACE/vpnsetup.sh"
          echo "# hwdsl2" > run.sh

          if [ "$os_type" = "alpine" ]; then
            apk add -U wget rsyslog sed bash
            rsyslogd
          else
            export DEBIAN_FRONTEND=noninteractive
            apt-get -yqq update
            apt-get -yqq dist-upgrade
            apt-get -yqq install wget rsyslog
            if grep -qs bookworm /etc/debian_version \
              || [ "$(sed 's/\..*//' /etc/debian_version 2>/dev/null)" = "12" ]; then
              rsyslogd
            else
              service rsyslog start
            fi
          fi

          cp -f "$GITHUB_WORKSPACE"/vpnsetup.sh .
          cp -f "$GITHUB_WORKSPACE"/extras/vpnuninstall.sh ./vpnunst.sh
          sed -i -e '/curl /a sed -i "/swan_ver_latest=/s/^/#/" "$tmpdir/vpn.sh"' \
            -e '/curl /a sed -i \x27/status=0/a sed -i "/swan_ver_latest=/s/^/#/" /opt/src/ikev2.sh\x27 "$tmpdir/vpn.sh"' \
            vpnsetup.sh

          sh vpnsetup.sh

          if [ "$os_type" = "alpine" ]; then
            xl2tpd -c /etc/xl2tpd/xl2tpd.conf
            restart_ipsec
          else
            restart_ipsec
            restart_fail2ban
            cat /var/log/fail2ban.log
          fi

          netstat -anpu | grep pluto
          netstat -anpu | grep xl2tpd
          iptables -nvL
          iptables -nvL | grep -q 'ppp+'
          iptables -nvL | grep -q '192\.168\.43\.0/24'
          iptables -nvL -t nat
          iptables -nvL -t nat | grep -q '192\.168\.42\.0/24'
          iptables -nvL -t nat | grep -q '192\.168\.43\.0/24'
          grep pluto "$log1"
          grep xl2tpd "$log2"
          ipsec status
          ipsec status | grep -q l2tp-psk
          ipsec status | grep -q xauth-psk
          ipsec status | grep -q ikev2-cp

          ls -ld /etc/ipsec.d/vpnclient.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient.sswan
          ls -ld /etc/ipsec.d/vpnclient.p12

          ls -l /usr/bin/ikev2.sh
          ls -l /usr/bin/addvpnuser.sh
          ls -l /usr/bin/delvpnuser.sh
          ls -l /opt/src/ikev2.sh
          ls -l /opt/src/addvpnuser.sh
          ls -l /opt/src/delvpnuser.sh

          bash vpnunst.sh <<ANSWERS
          y
          ANSWERS
          rm -f /etc/ipsec.d/vpnclient*
          if [ "$os_type" = "alpine" ]; then
            killall pluto || true
            killall xl2tpd || true
          fi

          if [ "$os_type" = "alpine" ]; then
            cp -f "$GITHUB_WORKSPACE"/vpnsetup_alpine.sh ./vpnsetup.sh
          else
            cp -f "$GITHUB_WORKSPACE"/vpnsetup_ubuntu.sh ./vpnsetup.sh
          fi
          sed -i -e '/swan_ver_latest=/s/^/#/' \
            -e '/status=0/a sed -i "/swan_ver_latest=/s/^/#/" /opt/src/ikev2.sh' \
            vpnsetup.sh

          bash vpnsetup.sh

          VPN_IPSEC_PSK='your_ipsec_pre_shared_key' \
          VPN_USER='your_vpn_username' \
          VPN_PASSWORD='your_vpn_password' \
          VPN_DNS_SRV1='1.1.1.1' \
          VPN_DNS_SRV2='1.0.0.1' \
          bash vpnsetup.sh

          if [ "$os_type" = "alpine" ]; then
            xl2tpd -c /etc/xl2tpd/xl2tpd.conf
          fi
          restart_ipsec

          netstat -anpu | grep pluto
          netstat -anpu | grep xl2tpd
          iptables -nvL
          iptables -nvL | grep -q 'ppp+'
          iptables -nvL | grep -q '192\.168\.43\.0/24'
          iptables -nvL -t nat
          iptables -nvL -t nat | grep -q '192\.168\.42\.0/24'
          iptables -nvL -t nat | grep -q '192\.168\.43\.0/24'
          ipsec status
          ipsec status | grep -q l2tp-psk
          ipsec status | grep -q xauth-psk
          ipsec status | grep -q ikev2-cp

          grep -q "your_ipsec_pre_shared_key" /etc/ipsec.secrets
          grep -q "your_vpn_username" /etc/ppp/chap-secrets
          grep -q "your_vpn_password" /etc/ppp/chap-secrets
          grep -q "your_vpn_username" /etc/ipsec.d/passwd
          grep -q 'modecfgdns="1.1.1.1 1.0.0.1"' /etc/ipsec.conf
          grep -q 'ms-dns 1.1.1.1' /etc/ppp/options.xl2tpd
          grep -q 'ms-dns 1.0.0.1' /etc/ppp/options.xl2tpd

          ls -ld /etc/ipsec.d/vpnclient.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient.sswan
          ls -ld /etc/ipsec.d/vpnclient.p12

          ls -l /usr/bin/ikev2.sh
          ls -l /usr/bin/addvpnuser.sh
          ls -l /usr/bin/delvpnuser.sh
          ls -l /opt/src/ikev2.sh
          ls -l /opt/src/addvpnuser.sh
          ls -l /opt/src/delvpnuser.sh

          rm -f /usr/bin/ikev2.sh /opt/src/ikev2.sh
          rm -f /etc/ipsec.d/vpnclient*

          cp -f "$GITHUB_WORKSPACE"/extras/ikev2setup.sh ./ikev2.sh
          sed -i '/swan_ver_latest=/s/^/#/' ikev2.sh

          bash ikev2.sh --removeikev2 <<ANSWERS
          y
          ANSWERS

          restart_ipsec

          bash ikev2.sh <<ANSWERS







          ANSWERS

          grep -q 'modecfgdns="8.8.8.8 8.8.4.4"' /etc/ipsec.d/ikev2.conf
          ls -ld /etc/ipsec.d/vpnclient.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient.sswan
          ls -ld /etc/ipsec.d/vpnclient.p12
          pk12util -W "" -l /etc/ipsec.d/vpnclient.p12
          pk12util -W "" -l /etc/ipsec.d/vpnclient.p12 | grep AES-256 && exit 1

          restart_ipsec
          grep pluto "$log1" | tail -n 20
          ipsec status | grep -q ikev2-cp

          bash ikev2.sh <<ANSWERS
          1
          invalidclient:
          vpnclient
          vpnclient2

          ANSWERS

          ls -ld /etc/ipsec.d/vpnclient2.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient2.sswan
          ls -ld /etc/ipsec.d/vpnclient2.p12
          pk12util -W "" -l /etc/ipsec.d/vpnclient2.p12
          pk12util -W "" -l /etc/ipsec.d/vpnclient2.p12 | grep AES-256 && exit 1

          rm -f /etc/ipsec.d/vpnclient2*
          bash ikev2.sh <<ANSWERS
          2
          nonexistclient
          vpnclient2
          ANSWERS

          ls -ld /etc/ipsec.d/vpnclient2.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient2.sswan
          ls -ld /etc/ipsec.d/vpnclient2.p12
          pk12util -W "" -l /etc/ipsec.d/vpnclient2.p12
          pk12util -W "" -l /etc/ipsec.d/vpnclient2.p12 | grep AES-256 && exit 1

          bash ikev2.sh <<ANSWERS
          3
          ANSWERS

          bash ikev2.sh <<ANSWERS | grep -i "2 clients"
          3
          ANSWERS

          bash ikev2.sh <<ANSWERS
          4
          nonexistclient
          vpnclient2
          y
          ANSWERS

          bash ikev2.sh <<ANSWERS 2>&1 | grep -i "abort"
          4
          vpnclient2

          ANSWERS

          bash ikev2.sh <<ANSWERS
          5
          vpnclient2
          y
          ANSWERS

          bash ikev2.sh <<ANSWERS | grep -i "1 client"
          3
          ANSWERS

          bash ikev2.sh <<ANSWERS 2>&1 | grep -i "abort"
          2
          vpnclient2

          ANSWERS

          bash ikev2.sh <<ANSWERS
          100
          7
          ANSWERS

          bash ikev2.sh <<ANSWERS 2>&1 | grep -i "abort"
          6

          ANSWERS

          bash ikev2.sh <<ANSWERS
          6
          y
          ANSWERS

          restart_ipsec
          ls -ld /etc/ipsec.d/ikev2.conf && exit 1
          ipsec status | grep -q l2tp-psk
          ipsec status | grep -q xauth-psk
          ipsec status | grep -q ikev2-cp && exit 1
          certutil -L -d sql:/etc/ipsec.d

          rm -f /etc/ipsec.d/vpnclient*

          VPN_DNS_SRV1=invaliddns \
          bash ikev2.sh --auto 2>&1 | grep -i "invalid"

          if [ "$os_type" = "alpine" ]; then
            apk del uuidgen
          else
            apt-get -yqq remove uuid-runtime
          fi
          sed -i '/^include /d' /etc/ipsec.conf

          VPN_CLIENT_NAME=vpnclient1 \
          VPN_DNS_NAME=vpn.example.com \
          VPN_DNS_SRV1=1.1.1.1 \
          VPN_DNS_SRV2=1.0.0.1 \
          bash ikev2.sh --auto

          grep -q 'leftid=@vpn.example.com' /etc/ipsec.d/ikev2.conf
          grep -q 'modecfgdns="1.1.1.1 1.0.0.1"' /etc/ipsec.d/ikev2.conf
          ls -ld /etc/ipsec.d/vpnclient1.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient1.sswan
          ls -ld /etc/ipsec.d/vpnclient1.p12
          grep -q 'vpn.example.com' /etc/ipsec.d/vpnclient1.mobileconfig
          grep -q 'vpn.example.com' /etc/ipsec.d/vpnclient1.sswan

          restart_ipsec
          ipsec status | grep -q ikev2-cp

          bash ikev2.sh --addclient invalidclient: 2>&1 | grep -i "invalid"
          bash ikev2.sh --addclient vpnclient1 2>&1 | grep -i "already exists"

          bash ikev2.sh --addclient vpnclient2

          ls -ld /etc/ipsec.d/vpnclient2.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient2.sswan
          ls -ld /etc/ipsec.d/vpnclient2.p12

          bash ikev2.sh --exportclient nonexistclient 2>&1 | grep -i "does not exist"

          rm -f /etc/ipsec.d/vpnclient2*
          bash ikev2.sh --exportclient vpnclient2

          ls -ld /etc/ipsec.d/vpnclient2.mobileconfig
          ls -ld /etc/ipsec.d/vpnclient2.sswan
          ls -ld /etc/ipsec.d/vpnclient2.p12

          bash ikev2.sh --addclient vpnclient2 --exportclient vpnclient2 2>&1 | grep -i "invalid"

          bash ikev2.sh --listclients | grep "vpnclient1 \+valid"
          bash ikev2.sh --listclients | grep "vpnclient2 \+valid"
          bash ikev2.sh --listclients | grep "2 clients"

          bash ikev2.sh --revokeclient nonexistclient 2>&1 | grep -i "does not exist"
          bash ikev2.sh --revokeclient vpnclient2 <<ANSWERS
          y
          ANSWERS

          bash ikev2.sh --listclients | grep "vpnclient2 \+revoked"
          ls -ld /etc/ipsec.d/vpnclient2.mobileconfig && exit 1
          ls -ld /etc/ipsec.d/vpnclient2.sswan && exit 1
          ls -ld /etc/ipsec.d/vpnclient2.p12 && exit 1

          bash ikev2.sh --revokeclient vpnclient2 2>&1 | grep -i "already been revoked"
          bash ikev2.sh --exportclient vpnclient2 2>&1 | grep -i "revoked"

          bash ikev2.sh --deleteclient nonexistclient 2>&1 | grep -i "does not exist"
          bash ikev2.sh --deleteclient vpnclient1 <<ANSWERS
          y
          ANSWERS

          bash ikev2.sh --listclients | grep "1 client"
          ls -ld /etc/ipsec.d/vpnclient1.mobileconfig && exit 1
          ls -ld /etc/ipsec.d/vpnclient1.sswan && exit 1
          ls -ld /etc/ipsec.d/vpnclient1.p12 && exit 1

          bash ikev2.sh -h 2>&1 | grep -i "usage:"
          bash ikev2.sh --invalidoption 2>&1 | grep -i "usage:"

          bash ikev2.sh --removeikev2 --exportclient vpnclient1 2>&1 | grep -i "invalid"
          bash ikev2.sh --removeikev2 <<ANSWERS
          y
          ANSWERS

          restart_ipsec
          rm -f /etc/ipsec.d/vpnclient*

          bash ikev2.sh <<ANSWERS
          y
          invalidfqdn
          vpn.example.com


          y
          invaliddns
          1.1.1.1
          invaliddns
          1.0.0.1
          y

          ANSWERS

          grep -q 'leftid=@vpn.example.com' /etc/ipsec.d/ikev2.conf
          grep -q 'modecfgdns="1.1.1.1 1.0.0.1"' /etc/ipsec.d/ikev2.conf
          restart_ipsec
          ipsec status | grep -q ikev2-cp

          config_file="/etc/ipsec.d/.vpnconfig"
          p12_pw=$(grep -s '^IKEV2_CONFIG_PASSWORD=.\+' "$config_file" | tail -n 1 | cut -f2- -d= | sed -e "s/^'//" -e "s/'$//")
          pk12util -W "$p12_pw" -l /etc/ipsec.d/vpnclient.p12
          pk12util -W "$p12_pw" -l /etc/ipsec.d/vpnclient.p12 | grep AES-256 && exit 1

          bash ikev2.sh --addclient vpnclient2
          pk12util -W "$p12_pw" -l /etc/ipsec.d/vpnclient2.p12
          pk12util -W "$p12_pw" -l /etc/ipsec.d/vpnclient2.p12 | grep AES-256 && exit 1

          bash ikev2.sh --exportclient vpnclient2
          pk12util -W "$p12_pw" -l /etc/ipsec.d/vpnclient2.p12
          pk12util -W "$p12_pw" -l /etc/ipsec.d/vpnclient2.p12 | grep AES-256 && exit 1

          bash ikev2.sh --removeikev2 <<ANSWERS
          y
          ANSWERS

          grep -qs '^IKEV2_CONFIG_PASSWORD=.\+' "$config_file" && exit 1
          restart_ipsec
          bash ikev2.sh <<ANSWERS

          invalidip
          1.2.3.4
          invalidclient:
          vpnclient1
          1000
          12
          y
          1.1.1.1



          ANSWERS

          grep -q 'leftid=1.2.3.4' /etc/ipsec.d/ikev2.conf
          grep -q 'modecfgdns=1.1.1.1' /etc/ipsec.d/ikev2.conf
          restart_ipsec
          ipsec status | grep -q ikev2-cp

          bash ikev2.sh --removeikev2 <<ANSWERS
          y
          ANSWERS

          restart_ipsec
          VPN_DNS_SRV1=1.1.1.1 \
          bash ikev2.sh --auto

          grep -q 'modecfgdns=1.1.1.1' /etc/ipsec.d/ikev2.conf
          restart_ipsec
          ipsec status | grep -q ikev2-cp

          bash ikev2.sh --removeikev2 <<ANSWERS
          y
          ANSWERS

          restart_ipsec
          bash ikev2.sh --auto

          grep -qs '^IKEV2_CONFIG_PASSWORD=.\+' "$config_file" && exit 1
          grep -q 'modecfgdns="8.8.8.8 8.8.4.4"' /etc/ipsec.d/ikev2.conf
          restart_ipsec
          ipsec status | grep -q ikev2-cp

          cp -f "$GITHUB_WORKSPACE"/extras/vpnupgrade.sh ./vpnup.sh
          sed -i '/curl /a sed -i "/swan_ver_latest=/s/^/#/" "$tmpdir/vpnup.sh"' vpnup.sh

          for ver in 4.10 ""; do
            if [ "$os_type" = "alpine" ]; then
              ipsec whack --shutdown || true
            fi
            sed -i "s/^SWAN_VER=.*/SWAN_VER=$ver/" vpnup.sh
          bash vpnup.sh <<ANSWERS

          ANSWERS
            restart_ipsec
            [ -z "$ver" ] && ver=4.12
            ipsec --version | grep "$ver"
            ipsec status | grep -q l2tp-psk
            ipsec status | grep -q xauth-psk
            ipsec status | grep -q ikev2-cp
          done

          if [ "$os_type" = "alpine" ]; then
            cp -f "$GITHUB_WORKSPACE"/extras/vpnupgrade_alpine.sh ./vpnup.sh
          else
            cp -f "$GITHUB_WORKSPACE"/extras/vpnupgrade_ubuntu.sh ./vpnup.sh
          fi
          sed -i '/swan_ver_latest=/s/^/#/' vpnup.sh

          for ver in 4.11 ""; do
            if [ "$os_type" = "alpine" ]; then
              ipsec whack --shutdown || true
            fi
            sed -i "s/^SWAN_VER=.*/SWAN_VER=$ver/" vpnup.sh
          bash vpnup.sh <<ANSWERS

          ANSWERS
            restart_ipsec
            [ -z "$ver" ] && ver=4.12
            ipsec --version | grep "$ver"
            ipsec status | grep -q l2tp-psk
            ipsec status | grep -q xauth-psk
            ipsec status | grep -q ikev2-cp
          done

          bash ikev2.sh --removeikev2 <<ANSWERS
          y
          ANSWERS

          restart_ipsec
          ls -ld /etc/ipsec.d/ikev2.conf && exit 1
          ipsec status | grep -q l2tp-psk
          ipsec status | grep -q xauth-psk
          ipsec status | grep -q ikev2-cp && exit 1
          certutil -L -d sql:/etc/ipsec.d
