2
0
mirror of https://expo.survex.com/repositories/troggle/.git synced 2024-11-21 23:01:52 +00:00

Nearly fixed test suite

This commit is contained in:
Philip Sargent 2024-07-04 22:10:49 +03:00
parent b28b590b60
commit 57bab53cec
4 changed files with 170 additions and 140 deletions

View File

@ -6,10 +6,24 @@ import re
from http import HTTPStatus
from django.test import Client, TestCase
from django.contrib.auth.models import User
from troggle.core.models.caves import Cave
from troggle.core.models.troggle import Person, PersonExpedition
from troggle.core.models.troggle import Person, PersonExpedition, Expedition
from troggle.core.utils import current_expo
current_year = current_expo()
def create_user(name=None, last_name="Caver", is_superuser=False):
u = User()
u.username = name
u.email = f"philip.sargent+{name}@gmail.com"
u.first_name, u.last_name = name, last_name
u.set_password("secretword") # all test users have same password
u.save()
return u
# import troggle.settings as settings
# FIXTURE_DIRS = settings.PYTHON_PATH / "core" /"fixtures"
@ -18,24 +32,52 @@ class FixtureTests(TestCase):
They do not exercise the GET and url functions
"""
fixtures = ["auth_users", "expo_caves", "expo_exped"]
fixtures = ["expo_caves", "expo_exped"]
ph = r"and leads in 800m of tortuous going to"
def setUp(self):
pass
create_user(name="expo") # needed for current_year()
def tearDown(self):
pass
User.objects.all().delete()
def test_fix_person_loaded(self):
def test_fix_person_loaded_byname(self):
p = Person.objects.get(fullname="Michael Sargent")
self.assertEqual(str(p.first_name), "Michael")
def test_fix_person_loaded(self):
def test_fix_personexped_loaded_bypk(self):
pe = PersonExpedition.objects.get(pk="681")
self.assertEqual(str(pe.person.fullname), "Michael Sargent")
self.assertEqual(str(pe.expedition.year), "2019")
def test_fix_expedition_loaded(self):
e = Expedition.objects.get(pk="44")
self.assertEqual(str(e.year), "2019")
def test_page_person(self):
response = self.client.get("/person/michael-sargent")
content = response.content.decode()
# with open('testresponseperson.html','w') as tr:
# tr.writelines(content)
self.assertEqual(response.status_code, HTTPStatus.OK)
for ph in [r"Michael Sargent", r"has been on expo in the following years"]:
phmatch = re.search(ph, content)
self.assertIsNotNone(phmatch, "Failed to find expected text: '" + ph + "'")
def test_page_personexpedition(self):
# Not working despite all components present and correct
response = self.client.get("/personexpedition/michael-sargent/2019")
content = response.content.decode()
# with open('testresponse.html','w') as tr:
# tr.writelines(content)
self.assertEqual(response.status_code, HTTPStatus.OK)
for ph in [r"Michael Sargent", r"Table of all trips and surveys aligned by date"]:
phmatch = re.search(ph, content)
self.assertIsNotNone(phmatch, "Failed to find expected text: '" + ph + "'")
# Need to add a fixture so that this actually has a logbook entry and a trip/svx in it.
def test_fix_cave_loaded115(self):
c = Cave.objects.get(kataster_number="115")
self.assertEqual(str(c.description_file), "1623/115.htm")
@ -43,9 +85,6 @@ class FixtureTests(TestCase):
self.assertEqual(str(c.filename), "1623-115.html")
self.assertEqual(str(c.areacode), "1623")
# c.area is a 'ManyRelatedManager' object and not iterable
# self.assertEqual(str(c.[0].short_name), "1623")
ph = self.ph
phmatch = re.search(ph, c.underground_description)
self.assertIsNotNone(phmatch, "In fixture-loaded cave, failed to find expected text: '" + ph + "'")
@ -60,16 +99,6 @@ class FixtureTests(TestCase):
phmatch = re.search(ph, c.notes)
self.assertIsNotNone(phmatch, "In fixture-loaded cave, failed to find expected text: '" + ph + "'")
def test_page_personexpedition(self):
response = self.client.get("/personexpedition/michael-sargent/2019")
content = response.content.decode()
# with open('testresponse.html','w') as tr:
# tr.writelines(content)
self.assertEqual(response.status_code, HTTPStatus.OK)
for ph in [r"Michael Sargent", r"Table of all trips and surveys aligned by date"]:
phmatch = re.search(ph, content)
self.assertIsNotNone(phmatch, "Failed to find expected text: '" + ph + "'")
# Need to add a fixture so that this actually has a logbook entry and a trip/svx in it.
class FixturePageTests(TestCase):
@ -81,7 +110,7 @@ class FixturePageTests(TestCase):
# The fixtures have a password hash which is compatible with plain-text password 'secretword'
# The hash CHANGES whenever Django upgrades the encryption key length. Better to create the test uses
# algorithmically and not via a fixture.
fixtures = ["auth_users", "expo_caves", "expo_exped"]
fixtures = ["expo_caves", "expo_exped"]
ph = r"and leads in 800m of tortuous going to"
@classmethod
@ -89,7 +118,9 @@ class FixturePageTests(TestCase):
pass
def setUp(self):
from django.contrib.auth.models import User
create_user(name="expo")
create_user(name="expotest")
create_user(name="expotestadmin", is_superuser = True)
self.user = User.objects.get(username="expotest")
@ -97,7 +128,7 @@ class FixturePageTests(TestCase):
self.client = Client()
def tearDown(self):
pass
User.objects.all().delete()
def test_fix_expedition(self):
response = self.client.get("/expedition/2019")

View File

@ -14,56 +14,53 @@ from django.test import Client, TestCase
import troggle.settings as settings
from troggle.core.models.wallets import Wallet
from troggle.core.models.troggle import Expedition
from django.contrib.auth.models import User
from troggle.core.utils import current_expo
current_year = current_expo()
def create_user(name=None, last_name="Caver", is_superuser=False):
u = User()
u.username = name
u.email = f"philip.sargent+{name}@gmail.com"
u.first_name, u.last_name = name, last_name
u.set_password("secretword") # all test users have same password
u.save()
return u
class DataTests(TestCase):
"""These check that the NULL and NON-UNIQUE constraints are working in the database"""
"""These check that the NULL and NON-UNIQUE constraints are working in the database
no tests here... !"""
@classmethod
def setUpTestData(cls):
pass
def setUp(self):
from django.contrib.auth.models import User
u = User()
u.pk = 9000
u.user_id = 8000
u.username, u.password = "stinker", "secretword"
u.email = "philip.sargent+SP@gmail.com"
u.first_name, u.last_name = "Stinker", "Pinker"
u.save()
self.user = u
create_user(name="expo")
def tearDown(self):
# self.member.delete() # must delete member before user
# self.user.delete() # horrible crash, why?
pass
Users.objects.all().delete()
class FixturePageTests(TestCase):
# The fixtures have a password hash which is compatible with plain-text password 'secretword'
fixtures = ["auth_users"]
class LoginTests(TestCase):
def setUp(self):
from django.contrib.auth.models import User
self.user = User.objects.get(username="expotest")
create_user(name="expo")
create_user(name="expotest")
create_user(name="expotestadmin", is_superuser = True)
def tearDown(self):
pass
User.objects.all().delete()
def test_fix_admin_login_fail(self):
c = self.client
from django.contrib.auth.models import User
u = User.objects.get(username="expotest")
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
logged_in = c.login(username=u.username, password="secretword") # fails to work if password=u.password !
self.assertTrue(logged_in, "FAILED to login as '" + u.username + "'")
response = c.get("/admin/")
content = response.content.decode()
# with open('admin-op.html', 'w') as f:
@ -75,17 +72,16 @@ class FixturePageTests(TestCase):
class PostTests(TestCase):
"""Tests walletedit form"""
fixtures = ["auth_users"]
@classmethod
def setUpTestData(cls):
pass
def setUp(self):
from django.contrib.auth.models import User
self.user = User.objects.get(username="expotest")
self.client = Client()
create_user(name="expo")
create_user(name="expotestadmin", is_superuser = True)
self.user = create_user(name="expotest")
c = self.client
testyear = "2022"
wname = f"{testyear}:00"
@ -102,14 +98,17 @@ class PostTests(TestCase):
e.save()
self.expedition = e
def tearDown(self):
User.objects.all().delete()
Wallet.objects.all().delete()
Expedition.objects.all().delete()
def test_file_permissions(self):
"""Expect to be allowed to write to SCANS_ROOT, DRAWINGS_DATA, SURVEX_DATA, EXPOWEB
Need to login first.
"""
c = self.client
from django.contrib.auth.models import User
u = User.objects.get(username="expotest")
u = self.user
testyear = self.testyear
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
@ -173,14 +172,12 @@ class PostTests(TestCase):
def test_photo_upload(self):
"""Expect photo upload to work on any file (contrary to msg on screen)
Upload into current default year. settings.PHOTOS_YEAR
Upload into current default year.
Deletes file afterwards
Need to login first.
"""
c = self.client
from django.contrib.auth.models import User
u = User.objects.get(username="expotest")
u = self.user
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
c.login(username=u.username, password="secretword")
@ -192,11 +189,11 @@ class PostTests(TestCase):
content = response.content.decode()
self.assertEqual(response.status_code, HTTPStatus.OK)
self.assertEqual(response.status_code, HTTPStatus.OK)
# with open('_test_response.html', 'w') as f:
# f.write(content)
with open('_test_response.html', 'w') as f:
f.write(content)
for ph in [
r"test_upload_",
r"Upload photos into /photos/" + str(settings.PHOTOS_YEAR),
r"Upload photos into /photos/" + str(current_year),
r" you can create a new folder in your name",
r"Create new Photographer folder",
r"only photo image files are accepted",
@ -206,19 +203,17 @@ class PostTests(TestCase):
# Does not use the filename Django actually uses, assumes it is unchanged. Bug: accumulates one file with random name
# added each time it is run. The name of the uploaded file is only available within the code where it happens
remove_file = pathlib.Path(settings.PHOTOS_ROOT, settings.PHOTOS_YEAR) / "test_upload_file.txt"
remove_file = pathlib.Path(settings.PHOTOS_ROOT, current_year) / "test_upload_file.txt"
remove_file.unlink()
def test_photo_upload_rename(self):
"""Expect photo upload to work on any file (contrary to msg on screen)
Upload into current default year. settings.PHOTOS_YEAR
Upload into current default year.
Deletes file afterwards
Need to login first.
"""
c = self.client
from django.contrib.auth.models import User
u = User.objects.get(username="expotest")
u = self.user
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
c.login(username=u.username, password="secretword")
@ -239,19 +234,20 @@ class PostTests(TestCase):
# Does not use the filename Django actually uses, assumes it is unchanged. Bug: accumulates one file with random name
# added each time it is run. The name of the uploaded file is only available within the code where it happens
remove_file = pathlib.Path(settings.PHOTOS_ROOT, settings.PHOTOS_YEAR) / rename
remove_file.unlink()
remove_file = pathlib.Path(settings.PHOTOS_ROOT, current_year) / rename
if remove_file.is_file():
remove_file.unlink()
def test_photo_folder_create(self):
"""Create folder for new user
Create in current default year. settings.PHOTOS_YEAR
Create in current year.
Deletes folder afterwards
Need to login first.
"""
c = self.client
from django.contrib.auth.models import User
u = User.objects.get(username="expotest")
u = self.user
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
c.login(username=u.username, password="secretword")
@ -268,17 +264,17 @@ class PostTests(TestCase):
# Does not use the filename Django actually uses, assumes it is unchanged. Bug: accumulates one file with random name
# added each time it is run. The name of the uploaded file is only available within the code where it happens
remove_dir = pathlib.Path(settings.PHOTOS_ROOT, settings.PHOTOS_YEAR) / "GussieFinkNottle"
remove_dir.rmdir()
remove_dir = pathlib.Path(settings.PHOTOS_ROOT, current_year) / "GussieFinkNottle"
if remove_dir.is_dir():
remove_dir.rmdir()
def test_dwg_upload_txt(self):
"""Expect .pdf file to be refused upload
Need to login first.
"""
c = self.client
from django.contrib.auth.models import User
u = self.user
u = User.objects.get(username="expotest")
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
c.login(username=u.username, password="secretword")
@ -298,9 +294,8 @@ class PostTests(TestCase):
Need to login first.
"""
c = self.client
from django.contrib.auth.models import User
u = self.user
u = User.objects.get(username="expotest")
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
c.login(username=u.username, password="secretword")
@ -327,7 +322,8 @@ class PostTests(TestCase):
# added each time it is run. The name of the uploaded file is only available within the code where it happens
# UploadedFile.name see https://docs.djangoproject.com/en/4.1/ref/files/uploads/#django.core.files.uploadedfile.UploadedFile
remove_file = pathlib.Path(settings.DRAWINGS_DATA) / "uploads" / "test_upload_nosuffix"
remove_file.unlink()
if remove_file.is_file():
remove_file.unlink()
class ComplexLoginTests(TestCase):
@ -335,27 +331,14 @@ class ComplexLoginTests(TestCase):
def setUp(self):
"""setUp runs once for each test in this class"""
from django.contrib.auth.models import User
u = User()
u.pk = 9000
u.user_id = 8000
u.username, u.password = "expotest", "secretword"
u.email = "philip.sargent+ET@gmail.com"
u.first_name, u.last_name = "ExpoTest", "Caver"
u.is_staff = True
u.is_superuser = True
u.set_password(u.password) # This creates a new salt and thus a new key for EACH test
u.save() # vital that we save all this before attempting login
# print ('\n',u.password)
self.user = u
create_user(name="expo")
create_user(name="expotest")
create_user(name="expotestadmin", is_superuser = True)
def tearDown(self):
self.client.logout() # not needed as each test creates a new self.client
# self.member.delete()
##self.user.delete() # id attribute set to None !
pass
User.objects.all().delete()
# def test_login_redirect_for_non_logged_on_user(self): # need to fix this in real system
# c = self.client
@ -365,11 +348,11 @@ class ComplexLoginTests(TestCase):
def test_ordinary_login(self):
c = self.client
u = self.user
u = User.objects.get(username="expotest")
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
logged_in = c.login(username=u.username, password="secretword") # fails to work if password=u.password !
logged_in = c.login(username=u.username, password="secretword")
self.assertTrue(logged_in, "FAILED to login as '" + u.username + "'")
response = c.get("/accounts/login/") # defined by auth system
@ -379,14 +362,14 @@ class ComplexLoginTests(TestCase):
def test_authentication_login(self):
c = self.client
u = self.user
u = User.objects.get(username="expotest")
self.assertTrue(u.is_active, "User '" + u.username + "' is INACTIVE")
# This is weird. I thought that the user had to login before she was in the authenticated state
self.assertTrue(u.is_authenticated, "User '" + u.username + "' is NOT AUTHENTICATED before login")
logged_in = c.login(username=u.username, password="secretword") # fails to work if password=u.password !
logged_in = c.login(username=u.username, password="secretword")
self.assertTrue(logged_in, "FAILED to login as '" + u.username + "'")
self.assertTrue(u.is_authenticated, "User '" + u.username + "' is NOT AUTHENTICATED after login")
@ -396,24 +379,26 @@ class ComplexLoginTests(TestCase):
def test_admin_login(self):
c = self.client
u = self.user
u = User.objects.get(username="expotestadmin")
logged_in = c.login(username=u.username, password="secretword") # fails to work if password=u.password !
logged_in = c.login(username=u.username, password="secretword")
self.assertTrue(logged_in, "FAILED to login as '" + u.username + "'")
response = c.get("/admin/")
response = c.get("/admin/login/")
content = response.content.decode()
# with open('admin-op.html', 'w') as f:
# f.write(content)
# fn='admin-op.html'
# print(f"Writing {fn}")
# with open(fn, 'w') as f:
# f.write(content)
t = re.search(r"Troggle database administration", content)
self.assertIsNotNone(t, "Logged in as '" + u.username + "' but failed to get the Troggle Admin page")
def test_noinfo_login(self):
c = self.client # inherited from TestCase
u = self.user
u = User.objects.get(username="expotest")
logged_in = c.login(username=u.username, password="secretword") # fails if password=u.password !
logged_in = c.login(username=u.username, password="secretword")
self.assertTrue(logged_in, "FAILED to login as '" + u.username + "'")
response = c.get("/stats") # a page with the Troggle menus
content = response.content.decode()
@ -428,7 +413,7 @@ class ComplexLoginTests(TestCase):
def test_user_force(self):
c = self.client
u = self.user
u = User.objects.get(username="expotest")
try:
c.force_login(u)

View File

@ -23,33 +23,45 @@ import unittest
from http import HTTPStatus
from django.test import Client, SimpleTestCase, TestCase
from django.contrib.auth.models import User
from troggle.core.models.logbooks import LogbookEntry
from troggle.core.models.troggle import Expedition, DataIssue, Person, PersonExpedition
from troggle.core.utils import current_expo
import troggle.parsers.logbooks as lbp
current_year = current_expo()
def create_user(name=None, last_name="Caver", is_superuser=False):
u = User()
u.username = name
u.email = f"philip.sargent+{name}@gmail.com"
u.first_name, u.last_name = name, last_name
u.set_password("secretword") # all test users have same password
u.save()
return u
def create_person(firstname, lastname, nickname=False, vfho=False, exped=None):
fullname = f"{firstname} {lastname}"
slug=f"{firstname.lower()}-{lastname.lower()}"
coUniqueAttribs = {"first_name": firstname, "last_name": (lastname or ""), "slug": slug,}
otherAttribs = {"is_vfho": vfho, "fullname": fullname, "nickname": nickname}
person = Person.objects.create(**otherAttribs, **coUniqueAttribs)
coUniqueAttribs = {"person": person, "expedition": exped}
otherAttribs = {}
pe = PersonExpedition.objects.create(**otherAttribs, **coUniqueAttribs)
return person
TEST_YEAR = "1986"
lbp.ENTRIES[TEST_YEAR] = 4 # number of entries in the test logbook
class ImportTest(TestCase):
# see test_logins.py for the tests to check that logged-in users work
fixtures = ["auth_users"] # contains user 'expotest' with a hash => password = 'secretword'
@classmethod
def setUpTestData(cls):
def make_person(firstname, lastname, nickname=False, vfho=False):
fullname = f"{firstname} {lastname}"
slug=f"{firstname.lower()}-{lastname.lower()}"
coUniqueAttribs = {"first_name": firstname, "last_name": (lastname or ""), "slug": slug,}
otherAttribs = {"is_vfho": vfho, "fullname": fullname, "nickname": nickname}
person = Person.objects.create(**otherAttribs, **coUniqueAttribs)
coUniqueAttribs = {"person": person, "expedition": cls.test_expo}
otherAttribs = {}
pe = PersonExpedition.objects.create(**otherAttribs, **coUniqueAttribs)
return person
def setUpTestData(cls):
import troggle.settings as settings
LOGBOOKS_PATH = settings.EXPOWEB / lbp.LOGBOOKS_DIR
@ -63,21 +75,23 @@ class ImportTest(TestCase):
otherAttribs = {"name": f"CUCC expo-test {TEST_YEAR}"}
cls.test_expo = Expedition.objects.create(**otherAttribs, **coUniqueAttribs)
fred = make_person("Fred", "Smartarse", nickname="freddy")
phil = make_person("Phil", "Tosser", nickname="tosspot")
dave = make_person("David", "Smartarse", "")
mike = make_person("Michael", "Wideboy", "WB", vfho=True)
fred = create_person("Fred", "Smartarse", nickname="freddy", exped=cls.test_expo)
phil = create_person("Phil", "Tosser", nickname="tosspot", exped=cls.test_expo)
dave = create_person("David", "Smartarse", "", exped=cls.test_expo)
mike = create_person("Michael", "Wideboy", "WB", vfho=True, exped=cls.test_expo)
# NOT created Kurt, as the whole point is that he is a guest.
def setUp(self):
from django.contrib.auth.models import User
self.user = User.objects.get(username="expotest") # has password 'secretword' from fixture
create_user(name="expo") # needed for current_year()
self.user = create_user(name="expotest")
self.client = Client()
def tearDown(self):
pass
User.objects.all().delete()
Person.objects.all().delete()
PersonExpedition.objects.all().delete()
Expedition.objects.all().delete()
def test_logbook_exists(self):
self.assertTrue(self.test_logbook.is_file())
@ -184,7 +198,7 @@ class ImportTest(TestCase):
response = self.client.get(f"/aliases/{TEST_YEAR}")
self.assertEqual(response.status_code, HTTPStatus.OK)
content = response.content.decode()
# with open('_test_response.html', 'w') as f:
# with open('_test_responsealiases.html', 'w') as f:
# f.write(content)
ph = f"'fsmartarse'"
phmatch = re.search(ph, content)

View File

@ -124,7 +124,7 @@ def current_expo():
last_expo = expos[0].year
if int(last_expo) < int(year): # coming year, after Dec.31st
for y in range(int(last_expo)+1, int(year)+1):
print(f"--!{year}---")
#print(f"--!{year}---")
make_new_expo(str(y))
make_new_expo_dir(str(y))