From e41ae4d952e276d8497d38f5761806c14ea542d2 Mon Sep 17 00:00:00 2001
From: DmitriyEshenko <dmitriy.eshenko@vyos.io>
Date: Wed, 9 Sep 2020 06:45:40 +0000
Subject: openconnect: T2036: Move CLI commands under vpn openconnect

---
 src/conf_mode/vpn_anyconnect.py    | 135 -------------------------------------
 src/conf_mode/vpn_openconnect.py   | 135 +++++++++++++++++++++++++++++++++++++
 src/op_mode/anyconnect-control.py  |  67 ------------------
 src/op_mode/openconnect-control.py |  67 ++++++++++++++++++
 4 files changed, 202 insertions(+), 202 deletions(-)
 delete mode 100755 src/conf_mode/vpn_anyconnect.py
 create mode 100755 src/conf_mode/vpn_openconnect.py
 delete mode 100755 src/op_mode/anyconnect-control.py
 create mode 100755 src/op_mode/openconnect-control.py

(limited to 'src')

diff --git a/src/conf_mode/vpn_anyconnect.py b/src/conf_mode/vpn_anyconnect.py
deleted file mode 100755
index 158e1a117..000000000
--- a/src/conf_mode/vpn_anyconnect.py
+++ /dev/null
@@ -1,135 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright (C) 2018-2020 VyOS maintainers and contributors
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License version 2 or later as
-# published by the Free Software Foundation.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with this program.  If not, see <http://www.gnu.org/licenses/>.
-
-import os
-from sys import exit
-
-from vyos.config import Config
-from vyos.configdict import dict_merge
-from vyos.xml import defaults
-from vyos.template import render
-from vyos.util import call
-from vyos import ConfigError
-from crypt import crypt, mksalt, METHOD_SHA512
-
-from vyos import airbag
-airbag.enable()
-
-cfg_dir        = '/run/ocserv'
-ocserv_conf    = cfg_dir + '/ocserv.conf'
-ocserv_passwd  = cfg_dir + '/ocpasswd'
-radius_cfg     = cfg_dir + '/radiusclient.conf'
-radius_servers = cfg_dir + '/radius_servers'
-
-
-# Generate hash from user cleartext password
-def get_hash(password):
-    return crypt(password, mksalt(METHOD_SHA512))
-
-
-def get_config():
-    conf = Config()
-    base = ['vpn', 'anyconnect']
-    if not conf.exists(base):
-        return None
-
-    ocserv = conf.get_config_dict(base, key_mangling=('-', '_'), get_first_key=True)
-    default_values = defaults(base)
-    ocserv = dict_merge(default_values, ocserv)
-    return ocserv
-
-
-def verify(ocserv):
-    if ocserv is None:
-        return None
-
-    # Check authentication
-    if "authentication" in ocserv:
-        if "mode" in ocserv["authentication"]:
-            if "local" in ocserv["authentication"]["mode"]:
-                if not ocserv["authentication"]["local_users"] or not ocserv["authentication"]["local_users"]["username"]:
-                    raise ConfigError('Anyconect mode local required at leat one user')
-                else:
-                    for user in ocserv["authentication"]["local_users"]["username"]:
-                        if not "password" in ocserv["authentication"]["local_users"]["username"][user]:
-                            raise ConfigError(f'password required for user {user}')
-        else:
-            raise ConfigError('anyconnect authentication mode required')
-    else:
-        raise ConfigError('anyconnect authentication credentials required')
-
-    # Check ssl
-    if "ssl" in ocserv:
-        req_cert = ['ca_cert_file', 'cert_file', 'key_file']
-        for cert in req_cert:
-            if not cert in ocserv["ssl"]:
-                raise ConfigError('anyconnect ssl {0} required'.format(cert.replace('_', '-')))
-    else:
-        raise ConfigError('anyconnect ssl required')
-
-    # Check network settings
-    if "network_settings" in ocserv:
-        if "push_route" in ocserv["network_settings"]:
-            # Replace default route
-            if "0.0.0.0/0" in ocserv["network_settings"]["push_route"]:
-                ocserv["network_settings"]["push_route"].remove("0.0.0.0/0")
-                ocserv["network_settings"]["push_route"].append("default")
-        else:
-            ocserv["network_settings"]["push_route"] = "default"  
-    else:
-        raise ConfigError('anyconnect network settings required')
-
-
-def generate(ocserv):
-    if not ocserv:
-        return None
-
-    if "radius" in ocserv["authentication"]["mode"]:
-        # Render radius client configuration
-        render(radius_cfg, 'ocserv/radius_conf.tmpl', ocserv["authentication"]["radius"], trim_blocks=True)
-        # Render radius servers
-        render(radius_servers, 'ocserv/radius_servers.tmpl', ocserv["authentication"]["radius"], trim_blocks=True)
-    else:
-        if "local_users" in ocserv["authentication"]:
-            for user in ocserv["authentication"]["local_users"]["username"]:
-                ocserv["authentication"]["local_users"]["username"][user]["hash"] = get_hash(ocserv["authentication"]["local_users"]["username"][user]["password"])
-            # Render local users
-            render(ocserv_passwd, 'ocserv/ocserv_passwd.tmpl', ocserv["authentication"]["local_users"], trim_blocks=True)
-
-    # Render config
-    render(ocserv_conf, 'ocserv/ocserv_config.tmpl', ocserv, trim_blocks=True)
-    
-
-
-def apply(ocserv):
-    if not ocserv:
-        call('systemctl stop ocserv.service')
-        for file in [ocserv_conf, ocserv_passwd]:
-            if os.path.exists(file):
-                os.unlink(file)
-    else:
-        call('systemctl restart ocserv.service')
-
-
-if __name__ == '__main__':
-    try:
-        c = get_config()
-        verify(c)
-        generate(c)
-        apply(c)
-    except ConfigError as e:
-        print(e)
-        exit(1)
diff --git a/src/conf_mode/vpn_openconnect.py b/src/conf_mode/vpn_openconnect.py
new file mode 100755
index 000000000..af8604972
--- /dev/null
+++ b/src/conf_mode/vpn_openconnect.py
@@ -0,0 +1,135 @@
+#!/usr/bin/env python3
+#
+# Copyright (C) 2018-2020 VyOS maintainers and contributors
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2 or later as
+# published by the Free Software Foundation.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+
+import os
+from sys import exit
+
+from vyos.config import Config
+from vyos.configdict import dict_merge
+from vyos.xml import defaults
+from vyos.template import render
+from vyos.util import call
+from vyos import ConfigError
+from crypt import crypt, mksalt, METHOD_SHA512
+
+from vyos import airbag
+airbag.enable()
+
+cfg_dir        = '/run/ocserv'
+ocserv_conf    = cfg_dir + '/ocserv.conf'
+ocserv_passwd  = cfg_dir + '/ocpasswd'
+radius_cfg     = cfg_dir + '/radiusclient.conf'
+radius_servers = cfg_dir + '/radius_servers'
+
+
+# Generate hash from user cleartext password
+def get_hash(password):
+    return crypt(password, mksalt(METHOD_SHA512))
+
+
+def get_config():
+    conf = Config()
+    base = ['vpn', 'openconnect']
+    if not conf.exists(base):
+        return None
+
+    ocserv = conf.get_config_dict(base, key_mangling=('-', '_'), get_first_key=True)
+    default_values = defaults(base)
+    ocserv = dict_merge(default_values, ocserv)
+    return ocserv
+
+
+def verify(ocserv):
+    if ocserv is None:
+        return None
+
+    # Check authentication
+    if "authentication" in ocserv:
+        if "mode" in ocserv["authentication"]:
+            if "local" in ocserv["authentication"]["mode"]:
+                if not ocserv["authentication"]["local_users"] or not ocserv["authentication"]["local_users"]["username"]:
+                    raise ConfigError('openconnect mode local required at leat one user')
+                else:
+                    for user in ocserv["authentication"]["local_users"]["username"]:
+                        if not "password" in ocserv["authentication"]["local_users"]["username"][user]:
+                            raise ConfigError(f'password required for user {user}')
+        else:
+            raise ConfigError('openconnect authentication mode required')
+    else:
+        raise ConfigError('openconnect authentication credentials required')
+
+    # Check ssl
+    if "ssl" in ocserv:
+        req_cert = ['ca_cert_file', 'cert_file', 'key_file']
+        for cert in req_cert:
+            if not cert in ocserv["ssl"]:
+                raise ConfigError('openconnect ssl {0} required'.format(cert.replace('_', '-')))
+    else:
+        raise ConfigError('openconnect ssl required')
+
+    # Check network settings
+    if "network_settings" in ocserv:
+        if "push_route" in ocserv["network_settings"]:
+            # Replace default route
+            if "0.0.0.0/0" in ocserv["network_settings"]["push_route"]:
+                ocserv["network_settings"]["push_route"].remove("0.0.0.0/0")
+                ocserv["network_settings"]["push_route"].append("default")
+        else:
+            ocserv["network_settings"]["push_route"] = "default"  
+    else:
+        raise ConfigError('openconnect network settings required')
+
+
+def generate(ocserv):
+    if not ocserv:
+        return None
+
+    if "radius" in ocserv["authentication"]["mode"]:
+        # Render radius client configuration
+        render(radius_cfg, 'ocserv/radius_conf.tmpl', ocserv["authentication"]["radius"], trim_blocks=True)
+        # Render radius servers
+        render(radius_servers, 'ocserv/radius_servers.tmpl', ocserv["authentication"]["radius"], trim_blocks=True)
+    else:
+        if "local_users" in ocserv["authentication"]:
+            for user in ocserv["authentication"]["local_users"]["username"]:
+                ocserv["authentication"]["local_users"]["username"][user]["hash"] = get_hash(ocserv["authentication"]["local_users"]["username"][user]["password"])
+            # Render local users
+            render(ocserv_passwd, 'ocserv/ocserv_passwd.tmpl', ocserv["authentication"]["local_users"], trim_blocks=True)
+
+    # Render config
+    render(ocserv_conf, 'ocserv/ocserv_config.tmpl', ocserv, trim_blocks=True)
+    
+
+
+def apply(ocserv):
+    if not ocserv:
+        call('systemctl stop ocserv.service')
+        for file in [ocserv_conf, ocserv_passwd]:
+            if os.path.exists(file):
+                os.unlink(file)
+    else:
+        call('systemctl restart ocserv.service')
+
+
+if __name__ == '__main__':
+    try:
+        c = get_config()
+        verify(c)
+        generate(c)
+        apply(c)
+    except ConfigError as e:
+        print(e)
+        exit(1)
diff --git a/src/op_mode/anyconnect-control.py b/src/op_mode/anyconnect-control.py
deleted file mode 100755
index 6382016b7..000000000
--- a/src/op_mode/anyconnect-control.py
+++ /dev/null
@@ -1,67 +0,0 @@
-#!/usr/bin/env python3
-#
-# Copyright (C) 2020 VyOS maintainers and contributors
-#
-# This program is free software; you can redistribute it and/or modify
-# it under the terms of the GNU General Public License version 2 or later as
-# published by the Free Software Foundation.
-#
-# This program is distributed in the hope that it will be useful,
-# but WITHOUT ANY WARRANTY; without even the implied warranty of
-# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
-# GNU General Public License for more details.
-#
-# You should have received a copy of the GNU General Public License
-# along with this program.  If not, see <http://www.gnu.org/licenses/>.
-
-import sys
-import argparse
-import json
-
-from vyos.config import Config
-from vyos.util import popen, run, DEVNULL
-from tabulate import tabulate
-
-occtl        = '/usr/bin/occtl'
-occtl_socket = '/run/ocserv/occtl.socket'
-
-def show_sessions():
-    out, code = popen("sudo {0} -j -s {1} show users".format(occtl, occtl_socket),stderr=DEVNULL)
-    if code:
-        sys.exit('Cannot get anyconnect users information')
-    else:
-        headers = ["interface", "username", "ip", "remote IP", "RX", "TX", "state", "uptime"]
-        sessions = json.loads(out)
-        ses_list = []
-        for ses in sessions:
-            ses_list.append([ses["Device"], ses["Username"], ses["IPv4"], ses["Remote IP"], ses["_RX"], ses["_TX"], ses["State"], ses["_Connected at"]])
-        if len(ses_list) > 0:
-            print(tabulate(ses_list, headers))
-        else:
-            print("No active anyconnect sessions")
-
-def is_ocserv_configured():
-    if not Config().exists_effective('vpn anyconnect'):
-        print("vpn anyconnect server is not configured")
-        sys.exit(1)
-
-def main():
-    #parese args
-    parser = argparse.ArgumentParser()
-    parser.add_argument('--action', help='Control action', required=True)
-    parser.add_argument('--selector', help='Selector username|ifname|sid', required=False)
-    parser.add_argument('--target', help='Target must contain username|ifname|sid', required=False)
-    args = parser.parse_args()
-
-
-    # Check is IPoE configured
-    is_ocserv_configured()
-
-    if args.action == "restart":
-        run("systemctl restart ocserv")
-        sys.exit(0)
-    elif args.action == "show_sessions":
-        show_sessions()
-
-if __name__ == '__main__':
-    main()
diff --git a/src/op_mode/openconnect-control.py b/src/op_mode/openconnect-control.py
new file mode 100755
index 000000000..ef9fe618c
--- /dev/null
+++ b/src/op_mode/openconnect-control.py
@@ -0,0 +1,67 @@
+#!/usr/bin/env python3
+#
+# Copyright (C) 2020 VyOS maintainers and contributors
+#
+# This program is free software; you can redistribute it and/or modify
+# it under the terms of the GNU General Public License version 2 or later as
+# published by the Free Software Foundation.
+#
+# This program is distributed in the hope that it will be useful,
+# but WITHOUT ANY WARRANTY; without even the implied warranty of
+# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+# GNU General Public License for more details.
+#
+# You should have received a copy of the GNU General Public License
+# along with this program.  If not, see <http://www.gnu.org/licenses/>.
+
+import sys
+import argparse
+import json
+
+from vyos.config import Config
+from vyos.util import popen, run, DEVNULL
+from tabulate import tabulate
+
+occtl        = '/usr/bin/occtl'
+occtl_socket = '/run/ocserv/occtl.socket'
+
+def show_sessions():
+    out, code = popen("sudo {0} -j -s {1} show users".format(occtl, occtl_socket),stderr=DEVNULL)
+    if code:
+        sys.exit('Cannot get openconnect users information')
+    else:
+        headers = ["interface", "username", "ip", "remote IP", "RX", "TX", "state", "uptime"]
+        sessions = json.loads(out)
+        ses_list = []
+        for ses in sessions:
+            ses_list.append([ses["Device"], ses["Username"], ses["IPv4"], ses["Remote IP"], ses["_RX"], ses["_TX"], ses["State"], ses["_Connected at"]])
+        if len(ses_list) > 0:
+            print(tabulate(ses_list, headers))
+        else:
+            print("No active openconnect sessions")
+
+def is_ocserv_configured():
+    if not Config().exists_effective('vpn openconnect'):
+        print("vpn openconnect server is not configured")
+        sys.exit(1)
+
+def main():
+    #parese args
+    parser = argparse.ArgumentParser()
+    parser.add_argument('--action', help='Control action', required=True)
+    parser.add_argument('--selector', help='Selector username|ifname|sid', required=False)
+    parser.add_argument('--target', help='Target must contain username|ifname|sid', required=False)
+    args = parser.parse_args()
+
+
+    # Check is Openconnect server configured
+    is_ocserv_configured()
+
+    if args.action == "restart":
+        run("systemctl restart ocserv")
+        sys.exit(0)
+    elif args.action == "show_sessions":
+        show_sessions()
+
+if __name__ == '__main__':
+    main()
-- 
cgit v1.2.3