"""Automatische tests voor backup.py.  Starten met:  python3 -m unittest -v"""
import os
import tempfile
import unittest
from pathlib import Path

from backup import BackupFout, main, maak_backup


class TestBackup(unittest.TestCase):
    def setUp(self):
        self._tmp = tempfile.TemporaryDirectory()
        tmp = Path(self._tmp.name)
        self.bron = tmp / "Documenten"
        self.usb = tmp / "USB"
        (self.bron / "school").mkdir(parents=True)
        self.usb.mkdir()
        (self.bron / "brief.txt").write_text("Hallo")
        (self.bron / "school" / "verslag.docx").write_bytes(b"verslag v1")

    def tearDown(self):
        self._tmp.cleanup()

    def test_kopieert_alle_bestanden_met_submappen(self):
        t = maak_backup(self.bron, self.usb)
        self.assertEqual(t["gekopieerd"], 2)
        self.assertEqual((self.usb / "backup" / "brief.txt").read_text(), "Hallo")
        self.assertTrue((self.usb / "backup" / "school" / "verslag.docx").exists())

    def test_slaat_tijdelijke_bestanden_over(self):
        (self.bron / "~$verslag.docx").write_text("tijdelijk")
        (self.bron / "download.part").write_text("half")
        maak_backup(self.bron, self.usb)
        self.assertFalse((self.usb / "backup" / "~$verslag.docx").exists())
        self.assertFalse((self.usb / "backup" / "download.part").exists())

    def test_tweede_keer_alleen_nieuwe_bestanden(self):
        maak_backup(self.bron, self.usb)
        (self.bron / "nieuw.txt").write_text("nieuw")
        t = maak_backup(self.bron, self.usb)
        self.assertEqual((t["gekopieerd"], t["ongewijzigd"]), (1, 2))

    def test_gewijzigd_bestand_bewaart_oude_versie(self):
        maak_backup(self.bron, self.usb)
        verslag = self.bron / "school" / "verslag.docx"
        verslag.write_bytes(b"verslag v2 langer")
        later = verslag.stat().st_mtime + 10
        os.utime(verslag, (later, later))
        maak_backup(self.bron, self.usb)
        self.assertEqual((self.usb / "backup" / "school" / "verslag.docx").read_bytes(), b"verslag v2 langer")
        oude = list((self.usb / "oude_versies").rglob("verslag.docx"))
        self.assertEqual([o.read_bytes() for o in oude], [b"verslag v1"])

    def test_zonder_usb_duidelijke_fout_en_niets_aangemaakt(self):
        weg = self.usb / "niet_ingestoken"
        with self.assertRaisesRegex(BackupFout, "USB-stick is niet gevonden"):
            maak_backup(self.bron, weg)
        self.assertFalse(weg.exists())
        self.assertEqual(main(["backup.py", str(self.bron), str(weg)]), 1)

    def test_originele_bestanden_blijven_onaangeraakt(self):
        voor = {p: p.read_bytes() for p in self.bron.rglob("*") if p.is_file()}
        maak_backup(self.bron, self.usb)
        na = {p: p.read_bytes() for p in self.bron.rglob("*") if p.is_file()}
        self.assertEqual(voor, na)

    def test_backup_in_documentenmap_wordt_geweigerd(self):
        with self.assertRaises(BackupFout):
            maak_backup(self.bron, self.bron)


if __name__ == "__main__":
    unittest.main()
