Skip to content
Closed
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
228 changes: 228 additions & 0 deletions src/tests/system/tests/test_authentication.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,22 @@

from __future__ import annotations

<<<<<<< HEAD

Check failure

Code scanning / CodeQL

Syntax error Error test

Syntax Error (in Python 3).
import pytest
from sssd_test_framework.roles.client import Client
from sssd_test_framework.roles.generic import GenericProvider
from sssd_test_framework.topology import KnownTopologyGroup
=======
import re
from inspect import cleandoc

import pytest
from sssd_test_framework.roles.client import Client
from sssd_test_framework.roles.generic import GenericProvider
from sssd_test_framework.roles.kdc import KDC
from sssd_test_framework.roles.ldap import LDAP
from sssd_test_framework.topology import KnownTopology, KnownTopologyGroup
>>>>>>> e95d3fe01 (test: check is an2ln plugin is disabled or not)


@pytest.mark.topology(KnownTopologyGroup.AnyProvider)
Expand Down Expand Up @@ -226,3 +238,219 @@

assert client.auth.parametrize(method).password(user, correct), "User failed login!"
assert not client.auth.parametrize(method).password(user, wrong), "User logged in with an incorrect password!"
<<<<<<< HEAD
=======


@pytest.mark.topology(KnownTopologyGroup.AnyProvider)
@pytest.mark.preferred_topology(KnownTopology.LDAP)
@pytest.mark.parametrize(
"home_key",
["user", "uid", "fqn", "domain", "first_char", "upn", "default", "lowercase", "substring", "literal%"],
)
@pytest.mark.importance("medium")
def test_authentication__user_login_with_overriding_home_directory(
client: Client, provider: GenericProvider, home_key: str
):
"""
:title: Override the user's home directory
:description:
For simplicity, the home directory is set to '/home/user1' because some providers homedirs are different.
:setup:
1. Create user and set home directory to '/home/user1'
2. Configure SSSD with 'override_homedir' home_key value and restart SSSD
3. Get entry for 'user1'
:steps:
1. Login as 'user1' and check working directory
:expectedresults:
1. Login is successful and working directory matches the expected value
:customerscenario: False
"""
provider.user("user1").add(password="Secret123", home="/home/user1")
client.sssd.common.mkhomedir()
client.sssd.start()

user = client.tools.getent.passwd("user1")
assert user is not None

home_map: dict[str, list[str]] = {
"user": ["/home/%u", f"/home/{user.name}"],
"uid": ["/home/%U", f"/home/{user.uid}"],
"fqn": ["/home/%f", f"/home/{user.name}@{client.sssd.default_domain}"],
"domain": ["/home/%d/%u", f"/home/{client.sssd.default_domain}/{user.name}"],
"first_char": ["/home/%l", f"/home/{str(user.name)[0]}"],
"upn": ["/home/%P", f"/home/{user.name}@{provider.domain.upper()}"],
"default": ["%o", f"{user.home}"],
"lowercase": ["%h", f"{str(user.home).lower()}"],
"substring": ["%H/%u", f"/home/homedir/{user.name}"],
"literal%": ["/home/%%/%u", f"/home/%/{user.name}"],
}

if home_key == "upn" and isinstance(provider, LDAP):
pytest.skip("Skipping provider, userPrincipal attribute is not set!")

if home_key == "domain":
client.fs.mkdir_p(f"/home/{client.sssd.default_domain}")

home_fmt, home_exp = home_map[home_key]
client.sssd.domain["homedir_substring"] = "/home/homedir"
client.sssd.domain["override_homedir"] = home_fmt
client.sssd.restart(clean=True)

with client.ssh("user1", "Secret123") as ssh:
result = ssh.run("pwd").stdout
assert result is not None, "Getting path failed!"
assert result == home_exp, f"Current path {result} is not {home_exp}!"


@pytest.mark.topology(KnownTopologyGroup.AnyProvider)
@pytest.mark.parametrize("method", ["ssh", "su"])
@pytest.mark.parametrize("sssd_service_user", ("root", "sssd"))
@pytest.mark.importance("medium")
@pytest.mark.require(
lambda client, sssd_service_user: ((sssd_service_user == "root") or client.features["non-privileged"]),
"SSSD was built without support for running under non-root",
)
def test_authentication__user_login_with_modified_PAM_stack_provider_is_offline(
client: Client, provider: GenericProvider, method: str, sssd_service_user: str
):
"""
:title: Authenticate with modified PAM when the provider is offline
:setup:
1. Create user
2. Configure SSSD with "cache_credentials = true" and "krb5_store_password_if_offline = true" and
"offline_credentials_expiration = 0"
3. Back up /etc/pam.d/system-auth and /etc/pam.d/password-auth files
3. Modify PAM configuration files /etc/pam.d/system-auth, and /etc/pam.d/password-auth so that pam_sss.so
is using the 'use_first_pass' option and allow another PAM module ask for the password.
4 Start SSSD
:steps:
1. Login as user
2. Offline, login as user
3. Offline, login as user with bad password
:expectedresults:
1. User can log in
2. User can log in
3. User cannot log in
:customerscenario: True
"""
user = "user1"
correct = "Secret123"
wrong = "Wrong123"
provider.user(user).add(password=correct)
client.sssd.domain["cache_credentials"] = "True"
client.sssd.domain["krb5_store_password_if_offline"] = "True"
client.sssd.pam["offline_credentials_expiration"] = "0"
client.host.conn.exec(["authselect", "apply-changes", "--backup=mybackup"])
custom_pam_stack = """
auth required pam_env.so
auth sufficient pam_unix.so try_first_pass likeauth nullok
auth required pam_sss.so forward_pass use_first_pass
account sufficient pam_unix.so
account required pam_sss.so forward_pass
password sufficient pam_unix.so sha512 shadow
password required pam_krb5.so minimum_uid=1000
session required pam_limits.so
session required pam_mkhomedir.so umask=0077
session required pam_env.so
session required pam_unix.so
session optional pam_sss.so forward_pass\n
"""
client.fs.write("/etc/pam.d/system-auth", cleandoc(custom_pam_stack))
client.fs.write("/etc/pam.d/password-auth", cleandoc(custom_pam_stack))

client.sssd.start(service_user=sssd_service_user)

try:

assert client.auth.parametrize(method).password(user, correct), "User failed login!"

client.firewall.outbound.reject_host(provider)

# There might be active connections that are not terminated by creating firewall rule.
# We need to terminate it by forcing SSSD offline.
client.sssd.bring_offline()

assert client.auth.parametrize(method).password(user, correct), "User failed login!"
assert not client.auth.parametrize(method).password(user, wrong), "User logged in with an incorrect password!"

finally:
client.host.conn.exec(["authselect", "backup-restore", "mybackup"])


@pytest.mark.importance("critical")
@pytest.mark.topology(KnownTopology.IPA)
@pytest.mark.topology(KnownTopology.Samba)
@pytest.mark.topology(KnownTopology.AD)
def test_disable_an2ln(client: Client, provider: GenericProvider):
"""
:title: Check localauth plugin config file (IPA/AD version)
:setup:
1. Create user
:steps:
1. Login as user
2. Run klist
3. Read localauth plugin config file
:expectedresults:
1. User can log in
2. Kerberos TGT is available
3. localauth plugin config file is present and has expected content
:customerscenario: False
"""
provider.user("tuser").add()

pattern = (
r"\[plugins\]\n localauth = {\n disable = an2ln\n"
" module = sssd:/.*/sssd/modules/sssd_krb5_localauth_plugin.so\n }"
)

client.fs.rm("/var/lib/sss/pubconf/krb5.include.d/localauth_plugin")
client.sssd.start()

with client.ssh("tuser", "Secret123") as ssh:
with client.auth.kerberos(ssh) as krb:
result = krb.klist()
assert f"krbtgt/{provider.realm}@{provider.realm}" in result.stdout

try:
out = client.fs.read("/var/lib/sss/pubconf/krb5.include.d/localauth_plugin")
except Exception as e:
assert False, f"Reading plugin config file caused exception: {e}"

assert re.match(pattern, out), "Content of plugin config file does not match"


@pytest.mark.importance("high")
@pytest.mark.topology(KnownTopology.LDAP)
def test_ensure_localauth_plugin_is_not_configured(client: Client, provider: GenericProvider, kdc: KDC):
"""
:title: Check localauth plugin config file (LDAP with Kerberos version)
:setup:
1. Create user in LDAP and KDC
2. Setup SSSD to use Kerberos authentication
:steps:
1. Login as user
2. Run klist
3. Read localauth plugin config file
:expectedresults:
1. User can log in
2. Kerberos TGT is available
3. localauth plugin config file is not present
:customerscenario: False
"""
provider.user("tuser").add()
kdc.principal("tuser").add()

client.sssd.common.krb5_auth(kdc)

client.fs.rm("/var/lib/sss/pubconf/krb5.include.d/localauth_plugin")
client.sssd.start()

with client.ssh("tuser", "Secret123") as ssh:
with client.auth.kerberos(ssh) as krb:
result = krb.klist()
assert f"krbtgt/{kdc.realm}@{kdc.realm}" in result.stdout

with pytest.raises(Exception):
client.fs.read("/var/lib/sss/pubconf/krb5.include.d/localauth_plugin")
>>>>>>> e95d3fe01 (test: check is an2ln plugin is disabled or not)
Loading