# Copyright 2021 Offensive Security
# SPDX-license-identifier: GPL-3.0-only

import os
import shutil
import tempfile
import unittest
from pathlib import Path

from kali_tweaks.settings.samba import SambaSetting


class TestSambaSetting(unittest.TestCase):
    def setUp(self):
        self.workfile_fn = None  # file basename
        self.workfile = None  # path to working copy

    def tearDown(self):
        if self.workfile:
            os.remove(self.workfile)

    def get_fixture_path(self, file):
        path = Path(".") / "tests" / "fixtures-samba" / file
        return str(path)

    def init_workfile(self, file):
        file_path = self.get_fixture_path(file)
        fd, temp_path = tempfile.mkstemp(text=True)
        os.close(fd)
        shutil.copyfile(file_path, temp_path)
        self.workfile_fn = file
        self.workfile = temp_path

    def load_samba_config(self):
        return SambaSetting(self.workfile).load()

    def apply_samba_config(self, conf):
        SambaSetting(self.workfile).apply(conf)

    def assert_config_value(self, value):
        conf = self.load_samba_config()
        self.assertIn("hardening", conf)
        self.assertEqual(conf["hardening"], value)

    def assert_file_equal(self, sfx):
        reference_file = self.get_fixture_path(self.workfile_fn + sfx)
        with open(self.workfile) as f1, open(reference_file) as f2:
            content1 = f1.read().splitlines()
            content2 = f2.read().splitlines()
            self.assertListEqual(content1, content2)

    def set_and_test(self, value, sfx):
        conf = {"hardening": value}
        self.apply_samba_config(conf)
        self.assert_file_equal(sfx)
        self.assert_config_value(value)

    def test_with_kali_config(self):
        """Config file is pre-configured with Kali's default"""
        self.init_workfile("with-kali-defaults.conf")
        self.assert_config_value("compat")
        self.set_and_test("secure", ".1")
        self.set_and_test("compat", ".2")

    def test_param_unset(self):
        """Config file isn't configured for Kali, param is not set"""
        self.init_workfile("param-unset.conf")
        self.assert_config_value("secure")
        self.set_and_test("compat", ".1")
        self.set_and_test("secure", ".2")

    def test_param_set_by_user(self):
        """Parameter set by user to something not supported by kali-tweaks"""
        self.init_workfile("param-set-by-user.conf")
        self.assert_config_value("COREPLUS")
        self.set_and_test("compat", ".1")
        self.set_and_test("secure", ".2")

    def test_param_set_twice(self):
        """Parameter set twice in the config file"""
        self.init_workfile("param-set-twice.conf")
        self.assert_config_value("compat")
        self.set_and_test("secure", ".1")
        self.set_and_test("compat", ".2")

    def test_funny_case(self):
        """Config file mixes lowercase and uppercase"""
        self.init_workfile("funny-case.conf")
        self.assert_config_value("compat")
        self.set_and_test("secure", ".1")
        self.set_and_test("compat", ".2")
