Wrote full test suite for housewars app
This commit is contained in:
parent
63a28a6813
commit
58e3b16455
26 changed files with 590 additions and 32 deletions
2
.github/workflows/draft-release.yml
vendored
2
.github/workflows/draft-release.yml
vendored
|
|
@ -2,7 +2,7 @@ name: Create release draft
|
|||
|
||||
on:
|
||||
push:
|
||||
branches: [dev]
|
||||
branches: [main]
|
||||
|
||||
jobs:
|
||||
draft:
|
||||
|
|
|
|||
4
.github/workflows/test-build.yml
vendored
4
.github/workflows/test-build.yml
vendored
|
|
@ -17,10 +17,12 @@ jobs:
|
|||
env:
|
||||
DOTENV: '${{ secrets.DOTENV }}'
|
||||
run: echo "$DOTENV" >> .env
|
||||
- name: Setup python
|
||||
- name: Setup Python
|
||||
uses: actions/setup-python@v4
|
||||
with:
|
||||
python-version: '3.10'
|
||||
- name: Setup Chrome
|
||||
uses: nanasess/setup-chromedriver@v1.0.8
|
||||
- name: Install dependencies
|
||||
run: python -m pip install -r requirements.txt
|
||||
- name: Test build
|
||||
|
|
|
|||
10
.gitignore
vendored
10
.gitignore
vendored
|
|
@ -260,14 +260,6 @@ cython_debug/
|
|||
### venv ###
|
||||
# Virtualenv
|
||||
# http://iamzed.com/2009/05/07/a-primer-on-virtualenv/
|
||||
[Bb]in
|
||||
[Ii]nclude
|
||||
[Ll]ib
|
||||
[Ll]ib64
|
||||
[Ll]ocal
|
||||
[Ss]cripts
|
||||
pyvenv.cfg
|
||||
pip-selfcheck.json
|
||||
venv
|
||||
|
||||
# End of https://www.toptal.com/developers/gitignore/api/django,python,pydev,venv
|
||||
|
||||
|
|
|
|||
|
|
@ -36,7 +36,7 @@ class UserEntryForm(Form):
|
|||
|
||||
# Verify that email domain matches
|
||||
if ('@slps.org' not in email):
|
||||
raise ValidationError("Please use your school email")
|
||||
raise ValidationError("Please use your school email.")
|
||||
# Verify that the email is unique
|
||||
if UserEntry.objects.filter(email=email).exists():
|
||||
raise ValidationError(
|
||||
|
|
|
|||
|
|
@ -0,0 +1,23 @@
|
|||
# Generated by Django 4.0.4 on 2022-09-07 12:05
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('housewars', '0004_alter_pointsentry_unique_together'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AddField(
|
||||
model_name='activity',
|
||||
name='room_number',
|
||||
field=models.IntegerField(blank=True, default=None, null=True),
|
||||
),
|
||||
migrations.AlterField(
|
||||
model_name='teacher',
|
||||
name='grade',
|
||||
field=models.IntegerField(blank=True, choices=[(9, '9th/Freshman'), (10, '10th/Sophomore'), (11, '11th/Junior'), (12, '12th/Senior')], default=None, null=True),
|
||||
),
|
||||
]
|
||||
18
housewars/migrations/0005_alter_teacher_grade.py
Normal file
18
housewars/migrations/0005_alter_teacher_grade.py
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
# Generated by Django 4.0.4 on 2022-09-06 13:44
|
||||
|
||||
from django.db import migrations, models
|
||||
|
||||
|
||||
class Migration(migrations.Migration):
|
||||
|
||||
dependencies = [
|
||||
('housewars', '0004_alter_pointsentry_unique_together'),
|
||||
]
|
||||
|
||||
operations = [
|
||||
migrations.AlterField(
|
||||
model_name='teacher',
|
||||
name='grade',
|
||||
field=models.IntegerField(blank=True, choices=[(9, '9th/Freshman'), (10, '10th/Sophomore'), (11, '11th/Junior'), (12, '12th/Senior')], default=None, null=True),
|
||||
),
|
||||
]
|
||||
|
|
@ -13,6 +13,7 @@ class Activity(models.Model):
|
|||
name = models.CharField(max_length=100)
|
||||
default_quota = models.IntegerField(default=0)
|
||||
time = models.IntegerField(choices=TimeslotChoices)
|
||||
room_number = models.IntegerField(blank=True, null=True, default=None)
|
||||
password = models.CharField(
|
||||
max_length=100, blank=True, null=True, default=None)
|
||||
|
||||
|
|
|
|||
|
|
@ -17,7 +17,8 @@ class Teacher(models.Model):
|
|||
last_name = models.CharField(max_length=100)
|
||||
house = models.ForeignKey(
|
||||
House, related_name='teacher', default=None, blank=True, null=True, on_delete=models.SET_NULL)
|
||||
grade = models.IntegerField(choices=GradeChoices)
|
||||
grade = models.IntegerField(
|
||||
choices=GradeChoices, default=None, blank=True, null=True)
|
||||
activity = models.OneToOneField(
|
||||
Activity, related_name='teacher', default=None, blank=True, null=True, on_delete=models.SET_NULL)
|
||||
|
||||
|
|
|
|||
0
housewars/tests/forms/__init__.py
Normal file
0
housewars/tests/forms/__init__.py
Normal file
33
housewars/tests/forms/test_activity_form.py
Normal file
33
housewars/tests/forms/test_activity_form.py
Normal file
|
|
@ -0,0 +1,33 @@
|
|||
from django.test import TestCase
|
||||
|
||||
from housewars.forms import ActivityForm
|
||||
from housewars.models import Activity, House
|
||||
|
||||
|
||||
class ActivityFormTest(TestCase):
|
||||
def setUp(self):
|
||||
self.activity30 = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.activity60 = Activity.objects.create(name='Dodgeball', time=60)
|
||||
|
||||
def test_valid_time(self):
|
||||
form = ActivityForm(data={
|
||||
'activity1': self.activity30.id,
|
||||
'activity2': self.activity30.id,
|
||||
})
|
||||
|
||||
self.assertTrue(form.is_valid())
|
||||
|
||||
def test_invalid_time(self):
|
||||
form = ActivityForm(data={
|
||||
'activity1': self.activity60.id,
|
||||
'activity2': self.activity30.id,
|
||||
})
|
||||
|
||||
self.assertFalse(form.is_valid())
|
||||
self.assertEquals(len(form.errors), 1)
|
||||
|
||||
def test_no_data(self):
|
||||
form = ActivityForm(data={})
|
||||
|
||||
self.assertFalse(form.is_valid())
|
||||
self.assertEquals(len(form.errors), 2)
|
||||
27
housewars/tests/forms/test_points_entry_form.py
Normal file
27
housewars/tests/forms/test_points_entry_form.py
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
from django.test import TestCase
|
||||
|
||||
from housewars.forms import PointsEntryForm
|
||||
from housewars.models import Activity, House, Award
|
||||
|
||||
|
||||
class ActivityFormTest(TestCase):
|
||||
def setUp(self):
|
||||
self.house = House.objects.create(name='Hawk')
|
||||
self.activity = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.activity2 = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.award = Award.objects.create(name='1st', activity=self.activity)
|
||||
|
||||
def test_valid_time(self):
|
||||
form = PointsEntryForm(data={
|
||||
'house': self.house.id,
|
||||
'activity': self.activity.id,
|
||||
'award': self.award.id
|
||||
})
|
||||
|
||||
self.assertTrue(form.is_valid())
|
||||
|
||||
def test_no_data(self):
|
||||
form = PointsEntryForm(data={})
|
||||
|
||||
self.assertFalse(form.is_valid())
|
||||
self.assertEquals(len(form.errors), 3)
|
||||
38
housewars/tests/forms/test_user_entry_form.py
Normal file
38
housewars/tests/forms/test_user_entry_form.py
Normal file
|
|
@ -0,0 +1,38 @@
|
|||
from django.test import TestCase
|
||||
|
||||
from housewars.forms import UserEntryForm
|
||||
from housewars.models import House
|
||||
|
||||
|
||||
class UserEntryFormTest(TestCase):
|
||||
def setUp(self):
|
||||
self.house = House.objects.create(name='Hawk', points=30)
|
||||
|
||||
def test_valid(self):
|
||||
form = UserEntryForm(data={
|
||||
'first_name': 'Test',
|
||||
'last_name': 'User',
|
||||
'email': 'test.user@slps.org',
|
||||
'grade': 9,
|
||||
'house': self.house.id
|
||||
})
|
||||
|
||||
self.assertTrue(form.is_valid())
|
||||
|
||||
def test_invalid_email(self):
|
||||
form = UserEntryForm(data={
|
||||
'first_name': 'Test',
|
||||
'last_name': 'User',
|
||||
'email': 'test.user@gmail.com',
|
||||
'grade': 9,
|
||||
'house': self.house.id
|
||||
})
|
||||
|
||||
self.assertFalse(form.is_valid())
|
||||
self.assertEqual(len(form.errors), 1)
|
||||
|
||||
def test_no_data(self):
|
||||
form = UserEntryForm(data={})
|
||||
|
||||
self.assertFalse(form.is_valid())
|
||||
self.assertEquals(len(form.errors), 5)
|
||||
0
housewars/tests/models/__init__.py
Normal file
0
housewars/tests/models/__init__.py
Normal file
23
housewars/tests/models/test_house.py
Normal file
23
housewars/tests/models/test_house.py
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
from django.test import TestCase
|
||||
|
||||
from housewars.models import Activity, House, Award, PointsEntry
|
||||
|
||||
|
||||
class HouseModelTest(TestCase):
|
||||
def setUp(self):
|
||||
self.house = House.objects.create(name='Hawk', points=30)
|
||||
self.activity = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.award = Award.objects.create(
|
||||
activity=self.activity, name='1st', points=30)
|
||||
|
||||
def test_current_points(self):
|
||||
PointsEntry.objects.create(
|
||||
activity=self.activity, house=self.house, award=self.award)
|
||||
|
||||
self.assertEquals(self.house.current_points, 30)
|
||||
|
||||
def test_total_points(self):
|
||||
PointsEntry.objects.create(
|
||||
activity=self.activity, house=self.house, award=self.award)
|
||||
|
||||
self.assertEquals(self.house.total_points, 60)
|
||||
18
housewars/tests/models/test_user_entry.py
Normal file
18
housewars/tests/models/test_user_entry.py
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
from django.test import TestCase, Client
|
||||
from django.urls import reverse
|
||||
|
||||
from housewars.models import Activity, House, Teacher, UserEntry
|
||||
|
||||
|
||||
class UserEntryTest(TestCase):
|
||||
def setUp(self):
|
||||
self.client = Client()
|
||||
self.house = House.objects.create(name='Hawk', points=30)
|
||||
self.activity = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.entry = UserEntry.objects.create(
|
||||
first_name='Test', last_name='User', email='test.user@slps.org', grade=9, house=self.house, activity1=self.activity, activity2=self.activity)
|
||||
self.teacher = Teacher.objects.create(
|
||||
first_name='Test', last_name='Teacher', grade=9, house=self.house)
|
||||
|
||||
def test_mentor(self):
|
||||
self.assertEquals(self.entry.mentor, self.teacher)
|
||||
14
housewars/tests/test_urls.py
Normal file
14
housewars/tests/test_urls.py
Normal file
|
|
@ -0,0 +1,14 @@
|
|||
from django.test import TestCase
|
||||
from django.urls import reverse, resolve
|
||||
|
||||
from housewars.views import EntryCreateView, PointsEntryCreateView
|
||||
|
||||
|
||||
class TestUrls(TestCase):
|
||||
def test_entry_create_is_resolved(self):
|
||||
url = reverse('housewars:signup')
|
||||
self.assertEquals(resolve(url).func.view_class, EntryCreateView)
|
||||
|
||||
def test_points_entry_create_is_resolved(self):
|
||||
url = reverse('housewars:add_points')
|
||||
self.assertEquals(resolve(url).func.view_class, PointsEntryCreateView)
|
||||
0
housewars/tests/utils/__init__.py
Normal file
0
housewars/tests/utils/__init__.py
Normal file
15
housewars/tests/utils/test_get_random_string.py
Normal file
15
housewars/tests/utils/test_get_random_string.py
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
from django.test import TestCase
|
||||
|
||||
from housewars.utils import get_random_string
|
||||
|
||||
|
||||
class GetRandomStringTest(TestCase):
|
||||
def test_string_of_length_8(self):
|
||||
"""The string generated is of the correct length"""
|
||||
string = get_random_string(8)
|
||||
self.assertEqual(len(string), 8)
|
||||
|
||||
def test_string_of_length_6(self):
|
||||
"""The string generated is of the correct length"""
|
||||
string = get_random_string(6)
|
||||
self.assertEqual(len(string), 6)
|
||||
25
housewars/tests/utils/test_unpack_values.py
Normal file
25
housewars/tests/utils/test_unpack_values.py
Normal file
|
|
@ -0,0 +1,25 @@
|
|||
from django.test import TestCase
|
||||
|
||||
from housewars.utils import unpack_values
|
||||
from housewars.models import House
|
||||
|
||||
|
||||
class UnpackValuesTest(TestCase):
|
||||
def setUp(self):
|
||||
House.objects.create(name="Hawk")
|
||||
House.objects.create(name="Snowy")
|
||||
|
||||
self.test_queryset = House.objects.all()
|
||||
|
||||
def test_valid_row_headers(self):
|
||||
"""Correctly unpacks the headers into the first index"""
|
||||
values = unpack_values(self.test_queryset)
|
||||
self.assertEqual(
|
||||
values[0], [field.name for field in House._meta.fields])
|
||||
|
||||
def test_complete_values(self):
|
||||
"""Maintains the complete queryset and returns it"""
|
||||
values = unpack_values(self.test_queryset)
|
||||
queryset = list(self.test_queryset.values_list())
|
||||
for row in queryset:
|
||||
self.assertIn(list(row), values)
|
||||
|
|
@ -1,15 +1,35 @@
|
|||
from django.test import TestCase
|
||||
from django.test import TestCase, Client
|
||||
from django.urls import reverse
|
||||
|
||||
from ...models import Activity, House
|
||||
from housewars.models import Activity, House, Award
|
||||
|
||||
|
||||
class PointsEntryCreateViewTest(TestCase):
|
||||
def test_view_url_accessible_by_name(self):
|
||||
response = self.client.get(reverse('housewars:add_points'))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
def setUp(self):
|
||||
self.client = Client()
|
||||
self.url = reverse('housewars:add_points')
|
||||
self.house = House.objects.create(name='Hawk')
|
||||
self.activity = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.award = Award.objects.create(activity=self.activity, name='1st')
|
||||
|
||||
def test_view_uses_correct_template(self):
|
||||
response = self.client.get(reverse('housewars:add_points'))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
def test_GET(self):
|
||||
response = self.client.get(self.url)
|
||||
|
||||
self.assertEquals(response.status_code, 200)
|
||||
self.assertTemplateUsed(response, 'housewars/pointsentry_form.html')
|
||||
|
||||
def test_POST(self):
|
||||
response = self.client.post(self.url, {
|
||||
'house': self.house.id,
|
||||
'activity': self.activity.id,
|
||||
'award': self.award.id
|
||||
})
|
||||
|
||||
self.assertEquals(response.status_code, 302)
|
||||
self.assertEquals(self.house.pointsentry_set.count(), 1)
|
||||
|
||||
def test_failed_POST(self):
|
||||
response = self.client.post(self.url)
|
||||
|
||||
self.assertEquals(response.status_code, 200)
|
||||
self.assertEquals(self.house.pointsentry_set.count(), 0)
|
||||
|
|
|
|||
|
|
@ -1,15 +1,68 @@
|
|||
from django.test import TestCase
|
||||
import enum
|
||||
from django.test import TestCase, Client
|
||||
from django.urls import reverse
|
||||
|
||||
from ...models import Activity, House
|
||||
from housewars.models import Activity, House
|
||||
|
||||
|
||||
class UserEntryCreateViewTest(TestCase):
|
||||
def test_view_url_accessible_by_name(self):
|
||||
response = self.client.get(reverse('housewars:signup'))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
def setUp(self):
|
||||
self.client = Client()
|
||||
self.url = reverse('housewars:signup')
|
||||
self.house = House.objects.create(name='Hawk')
|
||||
self.activity = Activity.objects.create(
|
||||
name='Dodgeball', time=30, default_quota=5)
|
||||
self.full_activity = Activity.objects.create(
|
||||
name='Dodgeball', time=30)
|
||||
|
||||
def test_view_uses_correct_template(self):
|
||||
response = self.client.get(reverse('housewars:signup'))
|
||||
self.assertEqual(response.status_code, 200)
|
||||
self.assertTemplateUsed(response, 'housewars/entry_form.html')
|
||||
def test_POST(self):
|
||||
user_info_form = {
|
||||
'user-first_name': 'Test',
|
||||
'user-last_name': 'User',
|
||||
'user-email': 'asdfasdf@slps.org',
|
||||
'user-grade': 9,
|
||||
'user-house': self.house.id,
|
||||
'entry_create_view-current_step': 'user'
|
||||
}
|
||||
|
||||
activity_form = {
|
||||
'activity-activity1': self.activity.id,
|
||||
'activity-activity2': self.activity.id,
|
||||
'entry_create_view-current_step': 'activity'
|
||||
}
|
||||
|
||||
steps_data = [user_info_form, activity_form]
|
||||
|
||||
for data in steps_data:
|
||||
self.client.post(self.url, data)
|
||||
|
||||
self.assertEquals(self.house.userentry_set.count(), 1)
|
||||
|
||||
def test_full_activity_POST(self):
|
||||
user_info_form = {
|
||||
'user-first_name': 'Test',
|
||||
'user-last_name': 'User',
|
||||
'user-email': 'asdfasdf@slps.org',
|
||||
'user-grade': 9,
|
||||
'user-house': self.house.id,
|
||||
'entry_create_view-current_step': 'user'
|
||||
}
|
||||
|
||||
activity_form = {
|
||||
'activity-activity1': self.full_activity.id,
|
||||
'activity-activity2': self.full_activity.id,
|
||||
'entry_create_view-current_step': 'activity'
|
||||
}
|
||||
|
||||
steps_data = [user_info_form, activity_form]
|
||||
|
||||
for data in steps_data:
|
||||
self.client.post(self.url, data)
|
||||
|
||||
self.assertEquals(self.house.userentry_set.count(), 0)
|
||||
|
||||
def test_empty_POST(self):
|
||||
response = self.client.post(self.url)
|
||||
|
||||
self.assertEquals(response.status_code, 400)
|
||||
self.assertEquals(self.house.pointsentry_set.count(), 0)
|
||||
|
|
|
|||
|
|
@ -48,7 +48,7 @@ class EntryCreateView(SessionWizardView):
|
|||
def done(self, form_list, **kwargs):
|
||||
UserEntry.objects.create(**self.get_all_cleaned_data())
|
||||
|
||||
messages.success(self.request, 'Your entry has been submitted')
|
||||
messages.success(self.request, 'Your signup has been submitted.')
|
||||
return redirect('housewars:signup')
|
||||
|
||||
def get_success_url(self):
|
||||
|
|
|
|||
|
|
@ -3,6 +3,7 @@ async-generator==1.10
|
|||
attrs==22.1.0
|
||||
autopep8==1.6.0
|
||||
certifi==2022.6.15
|
||||
charset-normalizer==2.1.1
|
||||
Django==4.0.4
|
||||
django-formtools==2.3
|
||||
django-smart-selects==1.6.0
|
||||
|
|
@ -16,14 +17,17 @@ pycodestyle==2.8.0
|
|||
PySocks==1.7.1
|
||||
python-dotenv==0.20.0
|
||||
reportlab==3.6.11
|
||||
requests==2.28.1
|
||||
selenium==4.4.3
|
||||
sniffio==1.3.0
|
||||
sortedcontainers==2.4.0
|
||||
sqlparse==0.4.2
|
||||
toml==0.10.2
|
||||
tqdm==4.64.1
|
||||
trio==0.21.0
|
||||
trio-websocket==0.9.2
|
||||
tzdata==2022.1
|
||||
urllib3==1.26.12
|
||||
webdriver-manager==3.8.3
|
||||
whitenoise==6.2.0
|
||||
wsproto==1.2.0
|
||||
|
|
|
|||
0
tests/__init__.py
Normal file
0
tests/__init__.py
Normal file
62
tests/test_points_entry_create.py
Normal file
62
tests/test_points_entry_create.py
Normal file
|
|
@ -0,0 +1,62 @@
|
|||
from django.urls import reverse
|
||||
from django.contrib.staticfiles.testing import StaticLiveServerTestCase
|
||||
|
||||
from selenium.webdriver import Chrome
|
||||
from selenium.webdriver.chrome.options import Options
|
||||
from webdriver_manager.chrome import ChromeDriverManager
|
||||
from selenium.webdriver.common.by import By
|
||||
from selenium.webdriver.support.wait import WebDriverWait
|
||||
from selenium.webdriver.support.select import Select
|
||||
from selenium.webdriver.support.expected_conditions import visibility_of
|
||||
|
||||
from housewars.models import House, Activity, Award
|
||||
|
||||
|
||||
class UserEntryCreatePageTest(StaticLiveServerTestCase):
|
||||
def setUp(self):
|
||||
options = Options()
|
||||
options.add_argument('--headless')
|
||||
|
||||
self.browser = Chrome(
|
||||
ChromeDriverManager().install(), chrome_options=options)
|
||||
self.url = self.live_server_url + reverse('housewars:add_points')
|
||||
|
||||
self.house = House.objects.create(name='Hawk')
|
||||
self.activity = Activity.objects.create(name='Dodgeball', time=30)
|
||||
self.award = Award.objects.create(name='1st', activity=self.activity)
|
||||
|
||||
def tearDown(self):
|
||||
self.browser.close()
|
||||
|
||||
def test_user_form_submission(self):
|
||||
self.browser.get(self.url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
# Fill in form with valid inputs
|
||||
Select(self.browser.find_element(By.ID, 'id_activity')
|
||||
).select_by_visible_text('Dodgeball (30)')
|
||||
Select(self.browser.find_element(By.ID, 'house')
|
||||
).select_by_visible_text('Hawk')
|
||||
Select(self.browser.find_element(By.ID, 'id_award')
|
||||
).select_by_visible_text('1st')
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
# Verify that success message is shown
|
||||
success_text = self.browser.find_element(
|
||||
By.CSS_SELECTOR, 'div.alert.alert-success').text
|
||||
self.assertEquals(
|
||||
success_text, 'Your points entry has been submitted.')
|
||||
|
||||
def test_no_awards_on_default(self):
|
||||
self.browser.get(self.url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
# Verify that only null option is in options
|
||||
award_select = Select(self.browser.find_element(By.ID, 'id_award'))
|
||||
self.assertEquals(len(award_select.options), 1)
|
||||
189
tests/test_user_entry_create.py
Normal file
189
tests/test_user_entry_create.py
Normal file
|
|
@ -0,0 +1,189 @@
|
|||
from django.urls import reverse
|
||||
from django.contrib.staticfiles.testing import StaticLiveServerTestCase
|
||||
|
||||
from selenium.webdriver import Chrome
|
||||
from selenium.webdriver.chrome.options import Options
|
||||
from selenium.webdriver.common.by import By
|
||||
from selenium.common.exceptions import NoSuchElementException
|
||||
from selenium.webdriver.support.wait import WebDriverWait
|
||||
from selenium.webdriver.support.select import Select
|
||||
from selenium.webdriver.support.expected_conditions import visibility_of
|
||||
from webdriver_manager.chrome import ChromeDriverManager
|
||||
|
||||
from housewars.models import House, Activity, UserEntry
|
||||
|
||||
|
||||
class UserEntryCreatePageTest(StaticLiveServerTestCase):
|
||||
def setUp(self):
|
||||
options = Options()
|
||||
options.add_argument('--headless')
|
||||
|
||||
self.browser = Chrome(
|
||||
ChromeDriverManager().install(), chrome_options=options)
|
||||
self.url = self.live_server_url + reverse('housewars:signup')
|
||||
|
||||
self.house = House.objects.create(name='Hawk')
|
||||
self.activity30 = Activity.objects.create(
|
||||
name='Dodgeball', time=30, default_quota=5)
|
||||
self.activity60 = Activity.objects.create(
|
||||
name='Volleyball', time=60, default_quota=5)
|
||||
self.hidden = Activity.objects.create(
|
||||
name='Hidden', time=30, default_quota=1)
|
||||
|
||||
def tearDown(self):
|
||||
self.browser.close()
|
||||
|
||||
def test_user_form_submission(self):
|
||||
self.browser.get(self.url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
self.assertEqual(self.browser.title, 'House Wars - Signup')
|
||||
|
||||
self.browser.find_element(By.ID, 'first-name').send_keys('Test')
|
||||
self.browser.find_element(By.ID, 'last-name').send_keys('User')
|
||||
self.browser.find_element(
|
||||
By.ID, 'email').send_keys('test.user@slps.org')
|
||||
Select(self.browser.find_element(By.ID, 'grade')
|
||||
).select_by_visible_text('9th/Freshman')
|
||||
Select(self.browser.find_element(By.ID, 'house')
|
||||
).select_by_visible_text('Hawk')
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'activity1')))
|
||||
|
||||
Select(self.browser.find_element(By.ID, 'activity1')
|
||||
).select_by_visible_text('Dodgeball (30)')
|
||||
Select(self.browser.find_element(By.ID, 'activity2')
|
||||
).select_by_visible_text('Dodgeball (30)')
|
||||
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
success_text = self.browser.find_element(
|
||||
By.CSS_SELECTOR, 'div.alert.alert-success').text
|
||||
|
||||
self.assertEquals(success_text, 'Your signup has been submitted.')
|
||||
|
||||
def test_user_invalid_email(self):
|
||||
self.browser.get(self.live_server_url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
# Fill in form with valid inputs except email
|
||||
self.browser.find_element(By.ID, 'first-name').send_keys('Test')
|
||||
self.browser.find_element(By.ID, 'last-name').send_keys('User')
|
||||
self.browser.find_element(
|
||||
By.ID, 'email').send_keys('test.user@gmail.com')
|
||||
Select(self.browser.find_element(By.ID, 'grade')
|
||||
).select_by_visible_text('9th/Freshman')
|
||||
Select(self.browser.find_element(By.ID, 'house')
|
||||
).select_by_visible_text('Hawk')
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
# Verify that there is a domain error on submit
|
||||
error_text = self.browser.find_element(
|
||||
By.CSS_SELECTOR, 'div.alert.alert-danger').text
|
||||
self.assertEquals(error_text, 'Please use your school email.')
|
||||
|
||||
def test_user_used_email(self):
|
||||
UserEntry.objects.create(first_name='Test', last_name='User', email='test.user@slps.org', grade=9, house=self.house,
|
||||
activity1=self.activity30, activity2=self.activity30)
|
||||
|
||||
self.browser.get(self.live_server_url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
# Fill in form with valid inputs and duplicate email
|
||||
self.browser.find_element(By.ID, 'first-name').send_keys('Test')
|
||||
self.browser.find_element(By.ID, 'last-name').send_keys('User')
|
||||
self.browser.find_element(
|
||||
By.ID, 'email').send_keys('test.user@slps.org')
|
||||
Select(self.browser.find_element(By.ID, 'grade')
|
||||
).select_by_visible_text('9th/Freshman')
|
||||
Select(self.browser.find_element(By.ID, 'house')
|
||||
).select_by_visible_text('Hawk')
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
# Verify that duplicate error shows up on submit
|
||||
error_text = self.browser.find_element(
|
||||
By.CSS_SELECTOR, 'div.alert.alert-danger').text
|
||||
self.assertEquals(
|
||||
error_text, 'A signup with this email already exists, if you want to change your signups, please email cpatino8605@slps.org.')
|
||||
|
||||
def test_invalid_select_elements_are_not_visible(self):
|
||||
UserEntry.objects.create(first_name='Test', last_name='User', email='user.exist@slps.org', grade=9, house=self.house,
|
||||
activity1=self.hidden, activity2=self.activity30)
|
||||
|
||||
self.browser.get(self.live_server_url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
# Fill in form with valid inputs
|
||||
self.browser.find_element(By.ID, 'first-name').send_keys('Test')
|
||||
self.browser.find_element(By.ID, 'last-name').send_keys('User')
|
||||
self.browser.find_element(
|
||||
By.ID, 'email').send_keys('test.user@slps.org')
|
||||
Select(self.browser.find_element(By.ID, 'grade')
|
||||
).select_by_visible_text('9th/Freshman')
|
||||
Select(self.browser.find_element(By.ID, 'house')
|
||||
).select_by_visible_text('Hawk')
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
# Wait until browser loads next step of form before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'activity1')))
|
||||
|
||||
activity1 = Select(self.browser.find_element(By.ID, 'activity1'))
|
||||
activity2 = Select(self.browser.find_element(By.ID, 'activity2'))
|
||||
|
||||
# Assert that full activity is now shown
|
||||
self.assertRaises(NoSuchElementException,
|
||||
activity1.select_by_visible_text, 'Hidden (30)')
|
||||
# Asser that 60 minute activity is not shown in second slot
|
||||
self.assertRaises(NoSuchElementException,
|
||||
activity2.select_by_visible_text, 'Volleyball (60)')
|
||||
|
||||
# Assert that valid activities are still shown in slot
|
||||
activity1.select_by_visible_text('Volleyball (60)')
|
||||
activity2.select_by_visible_text('Hidden (30)')
|
||||
|
||||
def test_full_activity_shows_for_other_houses(self):
|
||||
House.objects.create(name='Snowy')
|
||||
UserEntry.objects.create(first_name='Test', last_name='User', email='user.exist@slps.org', grade=9, house=self.house,
|
||||
activity1=self.hidden, activity2=self.hidden)
|
||||
|
||||
self.browser.get(self.url)
|
||||
|
||||
# Wait until browser loads page before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'header')))
|
||||
|
||||
# Fill in form with valid inputs and separate house
|
||||
self.browser.find_element(By.ID, 'first-name').send_keys('Test')
|
||||
self.browser.find_element(By.ID, 'last-name').send_keys('User')
|
||||
self.browser.find_element(
|
||||
By.ID, 'email').send_keys('test.user@slps.org')
|
||||
Select(self.browser.find_element(By.ID, 'grade')
|
||||
).select_by_visible_text('9th/Freshman')
|
||||
Select(self.browser.find_element(By.ID, 'house')
|
||||
).select_by_visible_text('Snowy')
|
||||
self.browser.find_element(By.ID, 'submit').click()
|
||||
|
||||
# Wait until browser loads next form step before continuing
|
||||
WebDriverWait(self.browser, timeout=5).until(
|
||||
visibility_of(self.browser.find_element(By.ID, 'activity1')))
|
||||
|
||||
# Verify that full activity is still showing for other house
|
||||
activity1 = Select(self.browser.find_element(By.ID, 'activity1'))
|
||||
activity2 = Select(self.browser.find_element(By.ID, 'activity2'))
|
||||
activity1.select_by_visible_text('Hidden (30)')
|
||||
activity2.select_by_visible_text('Hidden (30)')
|
||||
Reference in a new issue