diff --git a/files/build_templates/sonic_debian_extension.j2 b/files/build_templates/sonic_debian_extension.j2 index a1e102759e6e..b745b46c034b 100644 --- a/files/build_templates/sonic_debian_extension.j2 +++ b/files/build_templates/sonic_debian_extension.j2 @@ -272,6 +272,19 @@ sudo dpkg --root=$FILESYSTEM_ROOT -i $debs_path/sonic-device-data_*.deb || \ # package for supporting password hardening sudo LANG=C DEBIAN_FRONTEND=noninteractive chroot $FILESYSTEM_ROOT apt-get -y install libpam-pwquality +# Install pam-ldap, nss-ldap, ldap-utils +sudo LANG=C DEBIAN_FRONTEND=noninteractive chroot $FILESYSTEM_ROOT apt-get -y install \ + libnss-ldapd \ + libpam-ldapd \ + ldap-utils + +# add networking.service dependancy to nslcd +sudo LANG=C chroot $FILESYSTEM_ROOT sed -i '/# Required-Start:/ s/$/ networking.service/' /etc/init.d/nslcd + +# nslcd disable default +sudo LANG=C chroot $FILESYSTEM_ROOT systemctl stop nslcd.service +sudo LANG=C chroot $FILESYSTEM_ROOT systemctl mask nslcd.service + # Install pam-tacplus and nss-tacplus sudo dpkg --root=$FILESYSTEM_ROOT -i $debs_path/libtac2_*.deb || \ sudo LANG=C DEBIAN_FRONTEND=noninteractive chroot $FILESYSTEM_ROOT apt-get -y install -f @@ -285,14 +298,14 @@ sudo dpkg --root=$FILESYSTEM_ROOT -i $debs_path/bash-tacplus_*.deb || \ # Install audisp-tacplus sudo dpkg --root=$FILESYSTEM_ROOT -i $debs_path/audisp-tacplus_*.deb || \ sudo LANG=C DEBIAN_FRONTEND=noninteractive chroot $FILESYSTEM_ROOT apt-get -y install -f -# Disable tacplus by default +# Disable tacplus and LDAP by default ## NOTE: this syntax of pam-auth-update is meant to be used when the package gets removed, not for specifying ## some local configuration of a PAM module. Currently, there's no clean way of noninteractively specifying ## whether some PAM module needs to be enabled or disabled on a system (there are hacky ways, though). ## ## If there is some PAM module that's installed/removed after this point, then this setting will end up having ## no impact, and there may be errors/test failures related to authentication. -sudo LANG=C chroot $FILESYSTEM_ROOT pam-auth-update --remove tacplus +sudo LANG=C chroot $FILESYSTEM_ROOT pam-auth-update --remove tacplus ldap sudo sed -i -e '/^passwd/s/ tacplus//' $FILESYSTEM_ROOT/etc/nsswitch.conf # Install pam-radius-auth and nss-radius diff --git a/src/sonic-yang-models/setup.py b/src/sonic-yang-models/setup.py index 95f98bd53dd8..dee8559bccb4 100644 --- a/src/sonic-yang-models/setup.py +++ b/src/sonic-yang-models/setup.py @@ -163,6 +163,7 @@ def run(self): './yang-models/sonic-system-aaa.yang', './yang-models/sonic-system-tacacs.yang', './yang-models/sonic-system-radius.yang', + './yang-models/sonic-system-ldap.yang', './yang-models/sonic-telemetry.yang', './yang-models/sonic-telemetry_client.yang', './yang-models/sonic-gnmi.yang', diff --git a/src/sonic-yang-models/tests/files/sample_config_db.json b/src/sonic-yang-models/tests/files/sample_config_db.json index 050f4433bac6..f3656501fb85 100644 --- a/src/sonic-yang-models/tests/files/sample_config_db.json +++ b/src/sonic-yang-models/tests/files/sample_config_db.json @@ -1612,6 +1612,22 @@ "timeout": "5" } }, + "LDAP": { + "global": { + "bind_dn": "test_bind", + "bind_password": "secret", + "bind_timeout": "5", + "version": "3", + "base_dn": "test_base", + "port": "389", + "timeout": "5" + } + }, + "LDAP_SERVER": { + "192.168.1.1": { + "priority": "5" + } + }, "NAT_BINDINGS": { "bind1": { "nat_pool": "pool1", diff --git a/src/sonic-yang-models/tests/yang_model_tests/tests/ldap.json b/src/sonic-yang-models/tests/yang_model_tests/tests/ldap.json new file mode 100644 index 000000000000..93a6032bcf1b --- /dev/null +++ b/src/sonic-yang-models/tests/yang_model_tests/tests/ldap.json @@ -0,0 +1,16 @@ +{ + "LDAP_TABLE": { + "desc": "Configure LDAP global fields." + }, + "LDAP_INVALID_TIMEOUT_TEST": { + "desc": "LDAP global configuration with invalid timeout value in LDAP table.", + "eStr": "LDAP timeout must be 1..60" + }, + "LDAP_SERVER_TEST" : { + "desc": "LDAP server configuration in LDAP_SERVER table." + }, + "LDAP_SERVER_INVALID_PRIORITY_TEST": { + "desc": "LDAP server configuration with invalid priority value in LDAP_SERVER table.", + "eStr": "LDAP server priority must be 1..8" + } +} \ No newline at end of file diff --git a/src/sonic-yang-models/tests/yang_model_tests/tests_config/ldap.json b/src/sonic-yang-models/tests/yang_model_tests/tests_config/ldap.json new file mode 100644 index 000000000000..39ff556cb2a8 --- /dev/null +++ b/src/sonic-yang-models/tests/yang_model_tests/tests_config/ldap.json @@ -0,0 +1,61 @@ +{ + "LDAP_TABLE": { + "sonic-system-ldap:sonic-system-ldap": { + "sonic-system-ldap:LDAP": { + "global":{ + "bind_dn": "test_bind", + "bind_password": "secret", + "bind_timeout": "5", + "version": "3", + "base_dn": "test_base", + "port": "389", + "timeout": "5" + } + } + } + }, + "LDAP_INVALID_TIMEOUT_TEST": { + "sonic-system-ldap:sonic-system-ldap": { + "sonic-system-ldap:LDAP": { + "global": { + "bind_dn": "test_bind", + "bind_password": "secret", + "bind_timeout": "5", + "version": "3", + "base_dn": "test_base", + "port": "389", + "timeout": 150 + } + } + } + }, + "LDAP_SERVER_TEST": { + "sonic-system-ldap:sonic-system-ldap": { + "sonic-system-ldap:LDAP_SERVER": { + "LDAP_SERVER_LIST": [ + { + "hostname": "192.168.1.1", + "priority": 1 + }, + { + "hostname": "ldap_server_1", + "priority": 2 + } + ] + } + } + }, + + "LDAP_SERVER_INVALID_PRIORITY_TEST": { + "sonic-system-ldap:sonic-system-ldap": { + "sonic-system-ldap:LDAP_SERVER": { + "LDAP_SERVER_LIST": [ + { + "hostname": "192.168.1.1", + "priority": 70 + } + ] + } + } + } +} \ No newline at end of file diff --git a/src/sonic-yang-models/yang-models/sonic-system-aaa.yang b/src/sonic-yang-models/yang-models/sonic-system-aaa.yang index 1b1a8c4931a7..61fc9ab61841 100644 --- a/src/sonic-yang-models/yang-models/sonic-system-aaa.yang +++ b/src/sonic-yang-models/yang-models/sonic-system-aaa.yang @@ -35,11 +35,11 @@ module sonic-system-aaa { leaf login { type string { - pattern '((tacacs\+|local|radius|default),)*(tacacs\+|local|radius|default)' { + pattern '((ldap|tacacs\+|local|radius|default),)*(ldap|tacacs\+|local|radius|default)' { error-message "Invalid login choice"; } } - description "AAA authentication/authorization/accounting methods - radius/tacacs+/local/default"; + description "AAA authentication/authorization/accounting methods - radius/tacacs+/ldap|local/default"; default "local"; } diff --git a/src/sonic-yang-models/yang-models/sonic-system-ldap.yang b/src/sonic-yang-models/yang-models/sonic-system-ldap.yang new file mode 100644 index 000000000000..82fe4624005f --- /dev/null +++ b/src/sonic-yang-models/yang-models/sonic-system-ldap.yang @@ -0,0 +1,108 @@ +module sonic-system-ldap { + yang-version 1.1; + namespace "http://github.com/Azure/sonic-system-ldap"; + prefix ssys-ldap; + + import ietf-inet-types { + prefix inet; + } + + description "LDAP YANG Module for SONiC OS"; + + revision 2023-10-01 { + description "First Revision"; + } + + container sonic-system-ldap { + + container LDAP_SERVER { + list LDAP_SERVER_LIST { + max-elements 8; + key "hostname"; + + leaf hostname { + type inet:host; + description + "LDAP server's Domain name or IP address (IPv4 or IPv6)"; + } + + leaf priority { + default 1; + type uint8 { + range "1..8" { + error-message "LDAP server priority must be 1..8"; + } + } + description "Server priority"; + } + } + } + + container LDAP { + + container global { + + + leaf bind_dn { + type string { + length "1..65"; + } + description + 'LDAP global bind dn'; + } + + leaf bind_password { + type string { + length "1..65"; + pattern "[^ #,]*" { + error-message 'LDAP shared secret (Valid chars are ASCII printable except SPACE, "#", and ",")'; + } + } + description "Shared secret used for encrypting the communication"; + } + + leaf bind_timeout { + default 5; + type uint16 { + range "1..120" { + error-message "Ldap bind timeout must be 1..120"; + } + } + description "Ldap bind timeout"; + } + + leaf version { + default 3; + type uint16 { + range "1..3" { + error-message "Ldap version must be 1..3"; + } + } + description "Ldap version"; + } + + leaf base_dn { + type string { + length "1..65"; + } + description "Ldap user base dn"; + } + + leaf port { + type inet:port-number; + default 389; + description "TCP port to communicate with LDAP server"; + } + + leaf timeout { + description "Ldap timeout duration in sec"; + type uint16 { + range "1..60" { + error-message "LDAP timeout must be 1..60"; + } + } + } + } /* container global */ + } /* container LDAP */ + }/* container sonic-system-ldap */ +}/* end of module sonic-system-ldap */