passing tests - teams can be created
This commit is contained in:
@@ -346,8 +346,9 @@ class Team(models.Model):
|
||||
def save(self, *args, **kwargs):
|
||||
manager = self.manager
|
||||
if manager.rower.rowerplan == 'basic':
|
||||
raise ValidationError(
|
||||
"Basic user cannot be team manager"
|
||||
if manager.rower.protrialexpires < datetime.date.today() and manager.rower.plantrialexpires < datetime.date.today():
|
||||
raise ValidationError(
|
||||
"Basic user cannot be team manager"
|
||||
)
|
||||
|
||||
if manager.rower.rowerplan in ['plan','pro']:
|
||||
@@ -695,8 +696,8 @@ class Rower(models.Model):
|
||||
planexpires = models.DateField(default=current_day)
|
||||
teamplanexpires = models.DateField(default=current_day)
|
||||
clubsize = models.IntegerField(default=0)
|
||||
protrialexpires = models.DateField(blank=True,null=True)
|
||||
plantrialexpires = models.DateField(blank=True,null=True)
|
||||
protrialexpires = models.DateField(default=datetime.date(1970,1,1))
|
||||
plantrialexpires = models.DateField(default=datetime.date(1970,1,1))
|
||||
|
||||
|
||||
# Privacy Data
|
||||
@@ -875,11 +876,12 @@ def check_teams_on_change(sender, **kwargs):
|
||||
action = kwargs.pop('action', None)
|
||||
pk_set = kwargs.pop('pk_set',None)
|
||||
if action == 'pre_add' and instance.rowerplan=='basic':
|
||||
for id in pk_set:
|
||||
team = Team.objects.get(id=id)
|
||||
if team.manager.rower.rowerplan not in ['coach']:
|
||||
raise ValidationError(
|
||||
"You cannot join a team led by a Pro or Self-Coach user"
|
||||
if instance.protrialexpires < datetime.date.today() and instance.plantrialexpires < datetime.date.today():
|
||||
for id in pk_set:
|
||||
team = Team.objects.get(id=id)
|
||||
if team.manager.rower.rowerplan not in ['coach']:
|
||||
raise ValidationError(
|
||||
"You cannot join a team led by a Pro or Self-Coach user"
|
||||
)
|
||||
|
||||
m2m_changed.connect(check_teams_on_change, sender=Rower.team.through)
|
||||
@@ -1905,9 +1907,10 @@ class PlannedSession(models.Model):
|
||||
manager = self.manager
|
||||
if self.sessiontype not in ['race','indoorrace']:
|
||||
if manager.rower.rowerplan in ['basic','pro']:
|
||||
raise ValidationError(
|
||||
"Basic user cannot be team manager"
|
||||
)
|
||||
if manager.rower.plantrialexpires < timezone.now().date():
|
||||
raise ValidationError(
|
||||
"You must be a Self-Coach user or higher to create a planned session"
|
||||
)
|
||||
|
||||
|
||||
# sort units
|
||||
|
||||
@@ -61,6 +61,14 @@ def update_team(t,name,manager,private,notes,viewing):
|
||||
|
||||
def create_team(name,manager,private='open',notes='',viewing='allmembers'):
|
||||
# needs some error testing
|
||||
if manager.rower.rowerplan == 'basic':
|
||||
if manager.rower.protrialexpires < timezone.now().date() and manager.rower.plantrialexpires < timezone.now().date():
|
||||
return (0,'You need to upgrade to a paid plan to establish a team')
|
||||
elif manager.rower.rowerplan != 'coach':
|
||||
ts = Team.objects.filter(manager=manager)
|
||||
if len(ts)>=1:
|
||||
return (0,'You need to upgrade to the Coach plan to have more than one team')
|
||||
|
||||
try:
|
||||
t = Team(name=name,manager=manager,notes=notes,
|
||||
private=private,viewing=viewing)
|
||||
@@ -77,17 +85,18 @@ def remove_team(id):
|
||||
send_team_delete_mail(t,r)
|
||||
return t.delete()
|
||||
|
||||
def set_teamplanexpires(rower):
|
||||
ts = Team.objects.filter(rower=rower)
|
||||
#def set_teamplanexpires(rower):
|
||||
# ts = Team.objects.filter(rower=rower)
|
||||
|
||||
texp = datetime.date(timezone.now())
|
||||
# texp = datetime.date(timezone.now())
|
||||
|
||||
for t in ts:
|
||||
mr = Rower.objects.get(user=t.manager)
|
||||
if mr.teamplanexpires > texp:
|
||||
rower.teamplanexpires = mr.teamplanexpires
|
||||
# for t in ts:
|
||||
# print t.name
|
||||
# mr = Rower.objects.get(user=t.manager)
|
||||
# if mr.teamplanexpires > texp:
|
||||
# rower.teamplanexpires = mr.teamplanexpires
|
||||
|
||||
t.save()
|
||||
# t.save()
|
||||
|
||||
return (1,'Updated rower team expiry')
|
||||
|
||||
@@ -99,7 +108,7 @@ def add_member(id,rower):
|
||||
|
||||
res = handle_add_workouts_team(ws,t)
|
||||
|
||||
set_teamplanexpires(rower)
|
||||
# set_teamplanexpires(rower)
|
||||
|
||||
return (id,'Member added')
|
||||
|
||||
@@ -111,7 +120,7 @@ def remove_member(id,rower):
|
||||
|
||||
res = handle_remove_workouts_team(ws,t)
|
||||
|
||||
set_teamplanexpires(rower)
|
||||
# set_teamplanexpires(rower)
|
||||
return (id,'Member removed')
|
||||
|
||||
def mgr_remove_member(id,manager,rower):
|
||||
|
||||
@@ -56,7 +56,6 @@
|
||||
</li>
|
||||
{% endif %}
|
||||
|
||||
{% if user.rower.rowerplan == 'coach' %}
|
||||
<li >
|
||||
<h2>Teams I manage</h2>
|
||||
<p>Number of members: {{ clubsize }}</p>
|
||||
@@ -85,7 +84,6 @@
|
||||
{% endif %}
|
||||
<a class="button green" href="/rowers/team/create/">New Team</a>
|
||||
</li>
|
||||
{% endif %}
|
||||
{% if invites or requests or myrequests or myinvites %}
|
||||
<li class="grid_2">
|
||||
<h2>Invitations and Requests</h2>
|
||||
|
||||
@@ -112,7 +112,7 @@ class PermissionsBasicsTests(TestCase):
|
||||
## Low level
|
||||
|
||||
## Coach can have any number of groups
|
||||
def test_plan_groupmanager(self):
|
||||
def test_coach_groupmanager(self):
|
||||
team1 = Team.objects.create(
|
||||
name = 'FirstTeam',
|
||||
notes = faker.text(),
|
||||
@@ -131,7 +131,7 @@ class PermissionsBasicsTests(TestCase):
|
||||
|
||||
|
||||
team3 = Team.objects.create(
|
||||
name = 'SecondTeam',
|
||||
name = 'ThirdTeam',
|
||||
notes = faker.text(),
|
||||
manager = self.ucoach,
|
||||
)
|
||||
@@ -447,8 +447,6 @@ class PermissionsViewTests(TestCase):
|
||||
'name': faker.word(),
|
||||
}
|
||||
|
||||
print 'posting to sessions/create'
|
||||
|
||||
form = PlannedSessionForm(post_data)
|
||||
self.assertTrue(form.is_valid())
|
||||
|
||||
@@ -545,7 +543,7 @@ class PermissionsViewTests(TestCase):
|
||||
)
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,200)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
## Self coach can create one group
|
||||
## Self coach cannot create more than one group
|
||||
@@ -629,7 +627,6 @@ class PermissionsViewTests(TestCase):
|
||||
'name': faker.word(),
|
||||
}
|
||||
|
||||
print 'posting to sessions/create'
|
||||
|
||||
form = PlannedSessionForm(post_data)
|
||||
self.assertTrue(form.is_valid())
|
||||
@@ -641,7 +638,7 @@ class PermissionsViewTests(TestCase):
|
||||
|
||||
## Self Coach cannot edit on behalf of athlete
|
||||
def test_plan_edit_athlete_settings(self):
|
||||
self.rbasic.team.add(self.teamplan)
|
||||
self.rpro.team.add(self.teamplan)
|
||||
|
||||
login = self.c.login(username=self.uplan2.username, password=self.uplan2password)
|
||||
self.assertTrue(login)
|
||||
@@ -649,12 +646,12 @@ class PermissionsViewTests(TestCase):
|
||||
url = reverse('rower_prefs_view',kwargs={'userid':self.ubasic.id})
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
## Self Coach cannot run analytics on behalf of athlete
|
||||
@patch('rowers.dataprep.read_cols_df_sql', side_effect = mocked_read_df_cols_sql_multistats)
|
||||
def test_plan_edit_athlete_analysis(self,mocked_df):
|
||||
self.rbasic.team.add(self.teamplan)
|
||||
self.rpro.team.add(self.teamplan)
|
||||
|
||||
login = self.c.login(username=self.uplan2.username, password=self.uplan2password)
|
||||
self.assertTrue(login)
|
||||
@@ -668,13 +665,13 @@ class PermissionsViewTests(TestCase):
|
||||
|
||||
response = self.c.get(url)
|
||||
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
## Self Coach cannot upload on behalf of athlete
|
||||
@patch('rowers.dataprep.create_engine')
|
||||
@patch('rowers.dataprep.getsmallrowdata_db',side_effect=mocked_getsmallrowdata_db)
|
||||
def test_plan_edit_athlete_upload(self,mocked_sqlalchemy,mocked_getsmallrowdata_db):
|
||||
self.rbasic.team.add(self.teamplan)
|
||||
self.rpro.team.add(self.teamplan)
|
||||
|
||||
login = self.c.login(username=self.uplan2.username, password=self.uplan2password)
|
||||
self.assertTrue(login)
|
||||
@@ -682,7 +679,7 @@ class PermissionsViewTests(TestCase):
|
||||
url = reverse('team_workout_upload_view')
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
|
||||
## Pro can have one group
|
||||
@@ -763,7 +760,7 @@ class PermissionsViewTests(TestCase):
|
||||
|
||||
## Pro cannot edit on behalf of athlete
|
||||
def test_pro_edit_athlete_settings(self):
|
||||
self.rbasic.team.add(self.teampro)
|
||||
self.rpro.team.add(self.teampro)
|
||||
|
||||
login = self.c.login(username=self.upro2.username, password=self.upro2password)
|
||||
self.assertTrue(login)
|
||||
@@ -771,12 +768,12 @@ class PermissionsViewTests(TestCase):
|
||||
url = reverse('rower_prefs_view',kwargs={'userid':self.ubasic.id})
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
## Pro cannot run analytics on behalf of athlete
|
||||
@patch('rowers.dataprep.read_cols_df_sql', side_effect = mocked_read_df_cols_sql_multistats)
|
||||
def test_pro_edit_athlete_analysis(self,mocked_df):
|
||||
self.rbasic.team.add(self.teampro)
|
||||
self.rpro.team.add(self.teampro)
|
||||
|
||||
login = self.c.login(username=self.upro2.username, password=self.upro2password)
|
||||
self.assertTrue(login)
|
||||
@@ -790,40 +787,45 @@ class PermissionsViewTests(TestCase):
|
||||
|
||||
response = self.c.get(url)
|
||||
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
## Self Coach cannot upload on behalf of athlete
|
||||
@patch('rowers.dataprep.create_engine')
|
||||
@patch('rowers.dataprep.getsmallrowdata_db',side_effect=mocked_getsmallrowdata_db)
|
||||
def test_plan_edit_athlete_upload(self,mocked_sqlalchemy,mocked_getsmallrowdata_db):
|
||||
self.rbasic.team.add(self.teamplan)
|
||||
self.rpro.team.add(self.teamplan)
|
||||
|
||||
login = self.c.login(username=self.uplan2.username, password=self.uplan2password)
|
||||
self.assertTrue(login)
|
||||
|
||||
url = reverse('team_workout_upload_view')
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,404)
|
||||
response = self.c.get(url,follow=True)
|
||||
self.assertEqual(response.status_code,200)
|
||||
|
||||
expected_url = reverse('paidplans')
|
||||
self.assertRedirects(response,
|
||||
expected_url = expected_url,
|
||||
status_code=302,target_status_code=200)
|
||||
|
||||
|
||||
## Pro users can see team members' workout, but not edit
|
||||
def test_coach_edit_athlete_workout(self,mocked_sqlalchemy,mocked_getsmallrowdata_db):
|
||||
self.rbasic.team.add(self.proplan)
|
||||
self.rpro2.team.add(self.proplan)
|
||||
def test_pro_edit_athlete_workout(self):
|
||||
self.rpro.team.add(self.teampro)
|
||||
self.rpro2.team.add(self.teampro)
|
||||
|
||||
login = self.c.login(username=self.upro2.username, password=self.upro2password)
|
||||
self.assertTrue(login)
|
||||
|
||||
url = reverse('workout_edit_view',
|
||||
kwargs={'id':encoder.encode_hex(self.ubasic_workouts[0].id)}
|
||||
kwargs={'id':encoder.encode_hex(self.upro_workouts[0].id)}
|
||||
)
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
url = reverse('workout_view',
|
||||
kwargs={'id':encoder.encode_hex(self.ubasic_workouts[0].id)}
|
||||
kwargs={'id':encoder.encode_hex(self.upro_workouts[0].id)}
|
||||
)
|
||||
|
||||
response = self.c.get(url)
|
||||
@@ -831,8 +833,8 @@ class PermissionsViewTests(TestCase):
|
||||
|
||||
|
||||
## Self Coach users can see team members' workout, but not edit
|
||||
def test_coach_edit_athlete_workout(self,mocked_sqlalchemy,mocked_getsmallrowdata_db):
|
||||
self.rbasic.team.add(self.teamplan)
|
||||
def test_plan_edit_athlete_workout(self):
|
||||
self.rpro.team.add(self.teamplan)
|
||||
|
||||
login = self.c.login(username=self.uplan2.username, password=self.uplan2password)
|
||||
self.assertTrue(login)
|
||||
@@ -842,7 +844,7 @@ class PermissionsViewTests(TestCase):
|
||||
)
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,200)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
url = reverse('workout_view',
|
||||
kwargs={'id':encoder.encode_hex(self.ubasic_workouts[0].id)}
|
||||
@@ -853,9 +855,9 @@ class PermissionsViewTests(TestCase):
|
||||
|
||||
|
||||
## Basic users can see team members' workout, but not edit
|
||||
def test_basic_edit_athlete_workout(self,mocked_sqlalchemy,mocked_getsmallrowdata_db):
|
||||
self.rbasic.team.add(self.teamplan)
|
||||
self.rplan2.team.add(self.teamplan)
|
||||
def test_basic_edit_athlete_workout(self):
|
||||
self.rbasic.team.add(self.teamcoach)
|
||||
self.rplan2.team.add(self.teamcoach)
|
||||
|
||||
login = self.c.login(username=self.ubasic.username, password=self.ubasicpassword)
|
||||
self.assertTrue(login)
|
||||
@@ -865,7 +867,7 @@ class PermissionsViewTests(TestCase):
|
||||
)
|
||||
|
||||
response = self.c.get(url)
|
||||
self.assertEqual(response.status_code,404)
|
||||
self.assertEqual(response.status_code,403)
|
||||
|
||||
url = reverse('workout_view',
|
||||
kwargs={'id':encoder.encode_hex(self.uplan2_workouts[0].id)}
|
||||
@@ -902,7 +904,7 @@ class PermissionsViewTests(TestCase):
|
||||
url = reverse('team_requestmembership_view',
|
||||
kwargs = {
|
||||
'teamid':self.teampro.id,
|
||||
'userid':self.upro.id
|
||||
'userid':self.ubasic.id
|
||||
})
|
||||
|
||||
response = self.c.get(url,follow=True)
|
||||
@@ -913,3 +915,8 @@ class PermissionsViewTests(TestCase):
|
||||
expected_url = expected_url,
|
||||
status_code=302,target_status_code=200)
|
||||
|
||||
# Race related
|
||||
|
||||
## Basic and Pro users can create races
|
||||
|
||||
## Basic users can subscribe to any race
|
||||
|
||||
BIN
rowers/tests/testdata/testdata.csv.gz
vendored
BIN
rowers/tests/testdata/testdata.csv.gz
vendored
Binary file not shown.
@@ -928,6 +928,23 @@ def iscoachmember(user):
|
||||
|
||||
return result
|
||||
|
||||
def cancreateteam(user):
|
||||
if user.is_anonymous():
|
||||
return False
|
||||
|
||||
try:
|
||||
r = Rower.objects.get(user=user)
|
||||
except Rower.DoesNotExist:
|
||||
r = Rower(user=user)
|
||||
r.save()
|
||||
|
||||
if user.is_authenticated() and (r.rowerplan=='coach'):
|
||||
return True
|
||||
elif user.is_athenticated() and r.rowerplan in ['plan','pro']:
|
||||
ts = Team.objects.filter(manager=user)
|
||||
if len(otherteams) >= 1:
|
||||
return False
|
||||
|
||||
# Check if a user can create planned sessions
|
||||
def hasplannedsessions(user):
|
||||
if not user.is_anonymous():
|
||||
|
||||
@@ -254,6 +254,15 @@ def team_requestmembership_view(request,teamid,userid):
|
||||
t = Team.objects.get(id=teamid)
|
||||
except Team.DoesNotExist:
|
||||
raise Http404("Team doesn't exist")
|
||||
|
||||
r = getrequestrower(request,userid=userid)
|
||||
|
||||
if t.manager.rower.rowerplan in ['plan','pro'] and r.rowerplan == 'basic':
|
||||
messages.error(request,
|
||||
"You have to be on a paid plan (Pro or higher) to join this team. As a basic user you can only join teams managed by users on the Coach plan.")
|
||||
|
||||
url = reverse('paidplans')
|
||||
return HttpResponseRedirect(url)
|
||||
|
||||
res,text = teams.create_request(t,userid)
|
||||
if res:
|
||||
@@ -395,8 +404,19 @@ def team_edit_view(request,id=0):
|
||||
'team':t,
|
||||
})
|
||||
|
||||
@user_passes_test(iscoachmember,login_url="/rowers/paidplans",redirect_field_name=None)
|
||||
#@user_passes_test(cancreateteam,login_url="/rowers/paidplans",redirect_field_name=None)
|
||||
@login_required()
|
||||
def team_create_view(request):
|
||||
r = getrequestrower(request)
|
||||
|
||||
if r.rowerplan == 'basic':
|
||||
if r.protrialexpires < timezone.now().date() and r.plantrialexpires < timezone.now().date():
|
||||
messages.error(request,"You must upgrade to Pro or higher to create teams/training groups")
|
||||
url = reverse('paidplans')
|
||||
return HttpResponseRedirect(url)
|
||||
|
||||
|
||||
|
||||
if request.method == 'POST':
|
||||
teamcreateform = TeamForm(request.POST)
|
||||
if teamcreateform.is_valid():
|
||||
@@ -408,6 +428,12 @@ def team_create_view(request):
|
||||
viewing = cd['viewing']
|
||||
res,message=teams.create_team(name,manager,private,notes,
|
||||
viewing)
|
||||
|
||||
if not res:
|
||||
messages.error(request,message)
|
||||
url = reverse('paidplans')
|
||||
return HttpResponseRedirect(url)
|
||||
|
||||
url = reverse('rower_teams_view')
|
||||
response = HttpResponseRedirect(url)
|
||||
return response
|
||||
@@ -438,7 +464,7 @@ def team_create_view(request):
|
||||
'breadcrumbs':breadcrumbs,
|
||||
})
|
||||
|
||||
@user_passes_test(iscoachmember,login_url="/rowers/paidplans",redirect_field_name=None)
|
||||
@login_required()
|
||||
def team_deleteconfirm_view(request,id):
|
||||
r = getrower(request.user)
|
||||
try:
|
||||
@@ -474,7 +500,7 @@ def team_deleteconfirm_view(request,id):
|
||||
'active':'nav-teams',
|
||||
})
|
||||
|
||||
@user_passes_test(iscoachmember,login_url="/rowers/paidplans",redirect_field_name=None)
|
||||
@login_required()
|
||||
def team_delete_view(request,id):
|
||||
r = getrower(request.user)
|
||||
try:
|
||||
|
||||
Reference in New Issue
Block a user