alembic/versions/2b8f5a6f10a4_store_fas_name_locally.py | 27 +++
fedora_elections/__init__.py | 3
fedora_elections/admin.py | 32 +++
fedora_elections/default_config.py | 7
fedora_elections/elections.py | 138 +++++++---------
fedora_elections/forms.py | 6
fedora_elections/models.py | 3
fedora_elections/templates/admin/view_election.html | 1
fedora_elections/templates/index.html | 2
fedora_elections/utils.py | 16 -
files/fedora-elections.spec | 2
tests/test_flask_elections.py | 11 -
tests/test_flask_irc.py | 55 +++++-
tests/test_flask_range_voting.py | 11 +
tests/test_flask_simple_voting.py | 54 +++++-
15 files changed, 228 insertions(+), 140 deletions(-)
New commits:
commit d33ad98b8605f81fe4996635a02741029d29d297
Merge: 20889d6 f79dd09
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Fri Jan 22 15:44:09 2016 +0100
Merge pull request #56 from fedora-infra/lcl_cache_fas
Store locally the candidates' FAS name
commit f79dd094dec24318c35e20d9348449003898bd76
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:54:36 2016 +0100
Add the alembic revision to create the fas_name field in the candidates table
diff --git a/alembic/versions/2b8f5a6f10a4_store_fas_name_locally.py
b/alembic/versions/2b8f5a6f10a4_store_fas_name_locally.py
new file mode 100644
index 0000000..6d960df
--- /dev/null
+++ b/alembic/versions/2b8f5a6f10a4_store_fas_name_locally.py
@@ -0,0 +1,27 @@
+"""Store fas_name locally
+
+Revision ID: 2b8f5a6f10a4
+Revises: d07c5ef2d03
+Create Date: 2016-01-21 16:53:38.956503
+
+"""
+
+# revision identifiers, used by Alembic.
+revision = '2b8f5a6f10a4'
+down_revision = 'd07c5ef2d03'
+
+from alembic import op
+import sqlalchemy as sa
+
+
+def upgrade():
+ """ Add the fas_name column to the candidates table.
"""
+ op.add_column(
+ 'candidates',
+ sa.Column('fas_name', sa.Unicode(150), nullable=True)
+ )
+
+
+def downgrade():
+ """ Drop the fas_name column from the candidates table.
"""
+ op.drop_column('candidates', 'fas_name')
commit e158baa40f360b8e00efccdd5185d613620301ab
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:51:35 2016 +0100
Drop the dependency on dogpile-cache
diff --git a/files/fedora-elections.spec b/files/fedora-elections.spec
index 1fa4d0f..d8619e1 100644
--- a/files/fedora-elections.spec
+++ b/files/fedora-elections.spec
@@ -24,7 +24,6 @@ BuildRequires: python-setuptools
BuildRequires: python-wtforms
BuildRequires: python-nose
BuildRequires: python-coverage
-BuildRequires: python-dogpile-cache
Requires: python-fedora
Requires: python-fedora-flask
@@ -34,7 +33,6 @@ Requires: python-openid
Requires: python-openid-teams
Requires: python-openid-cla
Requires: python-wtforms
-Requires: python-dogpile-cache
# EPEL6
%if ( 0%{?rhel} && 0%{?rhel} == 6 )
commit 8ab35838245e7bce5c303cc537ade5f96e5b1a51
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:50:58 2016 +0100
Drop the cache with dogpile
diff --git a/fedora_elections/__init__.py b/fedora_elections/__init__.py
index c08a61c..2bd685e 100644
--- a/fedora_elections/__init__.py
+++ b/fedora_elections/__init__.py
@@ -84,8 +84,7 @@ from fedora_elections import models
SESSION = models.create_session(APP.config['DB_URL'])
from fedora_elections import forms
-cache = dogpile.cache.make_region()
-cache.configure(**APP.config['DOGPILE_CACHE'])
+
from fedora_elections.utils import build_name_map
diff --git a/fedora_elections/default_config.py b/fedora_elections/default_config.py
index e887840..979dd9d 100644
--- a/fedora_elections/default_config.py
+++ b/fedora_elections/default_config.py
@@ -22,10 +22,3 @@ FAS_BASE_URL = 'https://admin.stg.fedoraproject.org/accounts/'
FAS_USERNAME = ''
FAS_PASSWORD = ''
FAS_CHECK_CERT = False
-
-DOGPILE_CACHE = {
- 'backend': 'dogpile.cache.dbm',
- 'arguments': {
- 'filename': '/var/tmp/elections-cache.dbm',
- },
-}
commit b134c1f22ac3d56b2ea13c713f91dd7fd0a416d2
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:50:13 2016 +0100
Drop get_fas_human_name since we store the info in the DB
diff --git a/fedora_elections/utils.py b/fedora_elections/utils.py
index 66ce8cb..a36270f 100644
--- a/fedora_elections/utils.py
+++ b/fedora_elections/utils.py
@@ -11,20 +11,6 @@ def build_name_map(election):
return {}
return dict([
- (str(candidate.id), get_fas_human_name(candidate.name))
+ (str(candidate.id), candidate.fas_name)
for candidate in election.candidates
])
-
-
-(a)fedora_elections.cache.cache_on_arguments()
-def get_fas_human_name(username):
- """ Given a fas username, return the fas human_name if possible.
-
- If the user has their name set to private or they don't exist, we just
- return the given username as a stand-in.
- """
- try:
- return fedora_elections.FAS2.person_by_username(username)['human_name']
- except (KeyError, AuthError), err:
- fedora_elections.APP.logger.debug(err)
- return username
commit 97c32031ddbd18b7af163ae38d00ab81301ea6f7
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:49:52 2016 +0100
In the admin page show the candidate's FAS name next to the name
diff --git a/fedora_elections/templates/admin/view_election.html
b/fedora_elections/templates/admin/view_election.html
index c283de7..3448fb0 100644
--- a/fedora_elections/templates/admin/view_election.html
+++ b/fedora_elections/templates/admin/view_election.html
@@ -25,6 +25,7 @@
<ul>
{% for candidate in election.candidates.all() %}
<li>{{ candidate.name }}
+ {% if candidate.fas_name %} ({{ candidate.fas_name }}) {% endif %}
<a href="{{ url_for('admin_edit_candidate',
election_alias=election.alias,
candidate_id=candidate.id) }}">
commit 63770fc488df9f56fc91f07e4ffc491256b4f8e1
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:48:52 2016 +0100
Let's present the candidate's FAS name first if there is one
diff --git a/fedora_elections/forms.py b/fedora_elections/forms.py
index 7d04a90..3c1db97 100644
--- a/fedora_elections/forms.py
+++ b/fedora_elections/forms.py
@@ -122,7 +122,7 @@ def get_range_voting_form(candidates, max_range):
action = wtforms.HiddenField()
for candidate in candidates:
- title = candidate.name
+ title = candidate.fas_name or candidate.name
if candidate.url:
title = '%s <a href="%s">[Info]</a>' % (title,
candidate.url)
field = wtforms.SelectField(
@@ -140,7 +140,7 @@ def get_simple_voting_form(candidates, fasusers):
titles = []
for candidate in candidates:
- title = candidate.name
+ title = candidate.fas_name or candidate.name
if fasusers: # pragma: no cover
# We can't cover FAS integration
try:
@@ -179,7 +179,7 @@ def get_select_voting_form(candidates, max_selection):
action = wtforms.HiddenField()
for candidate in candidates:
- title = candidate.name
+ title = candidate.fas_name or candidate.name
if candidate.url:
title = '%s <a href="%s">[Info]</a>' % (title,
candidate.url)
field = wtforms.BooleanField(
commit c65dd9245077fb06cd0e5b219df8967e21f92ddd
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:48:44 2016 +0100
Little style clean up
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 14b777c..4ebd434 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -39,6 +39,7 @@ from fedora_elections import (
)
from fedora_elections.utils import build_name_map
+
def login_required(f):
@wraps(f)
def decorated_function(*args, **kwargs):
@@ -122,6 +123,7 @@ def vote(election_alias):
'Unknown election voting type: %s' % election.voting_type)
return safe_redirect_back()
+
def vote_range(election, revote):
votes = models.Vote.of_user_on_election(
SESSION, flask.g.fas_user.username, election.id)
@@ -142,10 +144,10 @@ def vote_range(election, revote):
if form.validate_on_submit():
if form.action.data == 'submit':
candidates = [
- candidate
- for candidate in form
- if candidate and candidate.short_name not in
['csrf_token', 'action']
- ]
+ candidate
+ for candidate in form
+ if candidate and candidate.short_name not in ['csrf_token',
'action']
+ ]
process_vote(candidates, election, votes, revote)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -219,6 +221,7 @@ def vote_select(election, revote):
usernamemap=usernamemap,
nextaction=next_action)
+
def vote_simple(election, revote):
votes = models.Vote.of_user_on_election(
SESSION, flask.g.fas_user.username, election.id)
@@ -371,6 +374,7 @@ def election_results_text(election_alias):
stats=stats,
)
+
def process_vote(candidates, election, votes, revote, cand_name=None, value=None):
for index in range(len(candidates)):
candidate = candidates[index]
commit d33e5283a1897238e31916be0a3b027d1e1c377c
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:48:25 2016 +0100
Store locally the user's FAS name when adding or editing candidates
diff --git a/fedora_elections/admin.py b/fedora_elections/admin.py
index ad7f072..98c877c 100644
--- a/fedora_elections/admin.py
+++ b/fedora_elections/admin.py
@@ -238,9 +238,10 @@ def admin_add_candidate(election_alias):
form = forms.CandidateForm()
if form.validate_on_submit():
+ fas_name = None
if election.candidates_are_fasusers: # pragma: no cover
try:
- FAS2.person_by_username(form.name.data)['human_name']
+ fas_name = FAS2.person_by_username(form.name.data)['human_name']
except (KeyError, AuthError), err:
flask.flash(
'User `%s` does not have a FAS account.'
@@ -253,7 +254,8 @@ def admin_add_candidate(election_alias):
candidate = models.Candidate(
election=election,
name=form.name.data,
- url=form.url.data
+ url=form.url.data,
+ fas_name=fas_name,
)
SESSION.add(candidate)
@@ -291,9 +293,11 @@ def admin_add_multi_candidate(election_alias):
for entry in form.candidate.data.strip().split("|"):
candidate = entry.split("!")
+ fas_name = None
if election.candidates_are_fasusers: # pragma: no cover
try:
- FAS2.person_by_username(candidate[0])['human_name']
+ fas_name = FAS2.person_by_username(
+ candidate[0])['human_name']
except (KeyError, AuthError), err:
SESSION.rollback()
flask.flash(
@@ -308,7 +312,8 @@ def admin_add_multi_candidate(election_alias):
if len(candidate) == 1:
cand = models.Candidate(
election=election,
- name=candidate[0])
+ name=candidate[0],
+ fas_name=fas_name)
SESSION.add(cand)
candidates_name.append(cand.name)
# With url
@@ -316,7 +321,8 @@ def admin_add_multi_candidate(election_alias):
cand = models.Candidate(
election=election,
name=candidate[0],
- url=candidate[1])
+ url=candidate[1],
+ fas_name=fas_name)
SESSION.add(cand)
candidates_name.append(cand.name)
else:
@@ -357,6 +363,22 @@ def admin_edit_candidate(election_alias, candidate_id):
form = forms.CandidateForm(obj=candidate)
if form.validate_on_submit():
form.populate_obj(candidate)
+
+ fas_name = None
+ if election.candidates_are_fasusers: # pragma: no cover
+ try:
+ candidate.fas_name = FAS2.person_by_username(
+ candidate[0])['human_name']
+ except (KeyError, AuthError), err:
+ SESSION.rollback()
+ flask.flash(
+ 'User `%s` does not have a FAS account.'
+ % candidate[0], 'error')
+ return flask.redirect(flask.url_for(
+ 'admin_edit_candidate',
+ election_alias=election_alias,
+ candidate_id=candidate_id))
+
SESSION.commit()
flask.flash('Candidate "%s" saved' % candidate.name)
fedmsgshim.publish(
commit 10b484ebb7c437bd84a83ee221359c7e2f562e68
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Jan 21 16:47:55 2016 +0100
Add a fas_name field to the candidate table where the fas_name is stored
diff --git a/fedora_elections/models.py b/fedora_elections/models.py
index 31d6fea..e7d9d3d 100644
--- a/fedora_elections/models.py
+++ b/fedora_elections/models.py
@@ -263,6 +263,7 @@ class Candidate(BASE):
nullable=False)
# FAS username if candidates_are_fasusers
name = sa.Column(sa.Unicode(150), nullable=False)
+ fas_name = sa.Column(sa.Unicode(150), nullable=True)
url = sa.Column(sa.Unicode(250))
election = relationship(
commit 20889d67f5fc1f7f81ab5987fdf819e3093a44f9
Merge: 03d775b f132a47
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Thu Oct 8 09:57:42 2015 +0200
Merge pull request #55 from NerdsvilleCEO/fix_candidate_modification_bug
Candidate modification revote bug
commit f132a478397eebac23bba987a4aa323a75a907ef
Author: Joshua Santos <Nerdsville(a)nerdsville.net>
Date: Thu Oct 8 00:55:03 2015 -0700
Remove Trailing Spaces :)
diff --git a/tests/test_flask_range_voting.py b/tests/test_flask_range_voting.py
index 5107af2..494c6e5 100644
--- a/tests/test_flask_range_voting.py
+++ b/tests/test_flask_range_voting.py
@@ -312,7 +312,7 @@ class FlaskRangeElectionstests(ModelFlasktests):
self.assertEqual(votes[1].value, 0)
self.assertEqual(votes[2].value, 2)
#Let's not do repetition of what is tested above we aren't testing the
- #functionality of voting as that has already been asserted
+ #functionality of voting as that has already been asserted
obj = fedora_elections.models.Candidate( # id:16
election_id=3,
commit 7e54b8a9a5b74d3090848642a915d9b60157b654
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Sat Oct 3 21:39:19 2015 -0700
Add range voting revote candidate modification test
diff --git a/tests/test_flask_range_voting.py b/tests/test_flask_range_voting.py
index c18aca9..5107af2 100644
--- a/tests/test_flask_range_voting.py
+++ b/tests/test_flask_range_voting.py
@@ -312,13 +312,23 @@ class FlaskRangeElectionstests(ModelFlasktests):
self.assertEqual(votes[1].value, 0)
self.assertEqual(votes[2].value, 2)
#Let's not do repetition of what is tested above we aren't testing the
- #functionality of voting as that has already been asserted
+ #functionality of voting as that has already been asserted
+
+ obj = fedora_elections.models.Candidate( # id:16
+ election_id=3,
+ name='Josh',
+
url='https://fedoraproject.org/wiki/User:Nerdsville';,
+ )
+ self.session.add(obj)
+ self.session.commit()
+
#Next, we need to try revoting
newdata = {
'4': 2,
'5': 1,
'6': 1,
+ '16': 0,
'action': 'submit',
'csrf_token': csrf_token,
}
@@ -336,6 +346,7 @@ class FlaskRangeElectionstests(ModelFlasktests):
self.assertEqual(votes[0].value, 2)
self.assertEqual(votes[1].value, 1)
self.assertEqual(votes[2].value, 1)
+ self.assertEqual(votes[3].value, 0)
#If we haven't failed yet, HOORAY!
commit 677dff9bb60e5827ef29e2d58517927f6dde8db5
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Fri Sep 25 14:48:12 2015 -0700
Fix logic to apply for any index
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 339645f..14b777c 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -374,7 +374,7 @@ def election_results_text(election_alias):
def process_vote(candidates, election, votes, revote, cand_name=None, value=None):
for index in range(len(candidates)):
candidate = candidates[index]
- if revote and (index+1 == len(votes)):
+ if revote and (index+1 <= len(votes)):
vote = votes[index]
if value is not None:
vote.candidate_id = candidate.data
commit 689aa799bd94fa2ed419868ddc17f818c8291b7b
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Fri Sep 25 14:30:21 2015 -0700
Candidate modification revote bug
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 4b65e75..339645f 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -374,7 +374,7 @@ def election_results_text(election_alias):
def process_vote(candidates, election, votes, revote, cand_name=None, value=None):
for index in range(len(candidates)):
candidate = candidates[index]
- if revote:
+ if revote and (index+1 == len(votes)):
vote = votes[index]
if value is not None:
vote.candidate_id = candidate.data
commit 03d775bf5b66b91a6569aafe026fcfad2fa1e28d
Merge: c4e93d5 49d2f75
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Fri Sep 25 10:26:15 2015 +0200
Merge pull request #54 from NerdsvilleCEO/add-simple-revote
Add simple revote
commit 49d2f75a3e57f6e543dbbc66f63b123cc347a67a
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Thu Sep 24 10:24:25 2015 -0700
Prefer UTC time over now()
diff --git a/fedora_elections/models.py b/fedora_elections/models.py
index b3e72cc..31d6fea 100644
--- a/fedora_elections/models.py
+++ b/fedora_elections/models.py
@@ -136,7 +136,7 @@ class Election(BASE):
@property
def locked(self):
- return datetime.now() >= self.start_date
+ return datetime.utcnow() >= self.start_date
@classmethod
def search(cls, session, alias=None, shortdesc=None,
commit f1fc0829ef765296d96252c595f8d320b438cdde
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Thu Sep 24 10:24:14 2015 -0700
Prefer UTC time over now()
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index c35a5d7..4b65e75 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -392,7 +392,7 @@ def process_vote(candidates, election, votes, revote, cand_name=None,
value=None
new_vote = models.Vote(
election_id=election.id,
voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
+ timestamp=datetime.utcnow(),
candidate_id=cand_id,
value= value if value else int(candidate.data),
)
commit a526590d90408b738bb3346eb5a2611b4144e78d
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 16:36:11 2015 -0400
Cleanup
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 03c6821..c35a5d7 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -238,7 +238,7 @@ def vote_simple(election, revote):
for candidate in form
if candidate and candidate.short_name not in ['csrf_token',
'action']
]
- process_vote(candidates, election, votes, revote, None, 1)
+ process_vote(candidates, election, votes, revote, value=1)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -376,13 +376,13 @@ def process_vote(candidates, election, votes, revote,
cand_name=None, value=None
candidate = candidates[index]
if revote:
vote = votes[index]
- if value == 1:
+ if value is not None:
vote.candidate_id = candidate.data
else:
vote.value = value if value else int(candidate.data)
SESSION.add(vote)
else:
- if value == 1:
+ if value is not None:
cand_id = candidate.data
elif cand_name:
cand_id = cand_name[candidate.short_name]
commit 211eb0456f1d312ebf16f12833b87168508d75db
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 11:32:57 2015 -0400
Fix final failed test
diff --git a/tests/test_flask_elections.py b/tests/test_flask_elections.py
index 90a0230..fd24ce9 100644
--- a/tests/test_flask_elections.py
+++ b/tests/test_flask_elections.py
@@ -155,17 +155,6 @@ class FlaskElectionstests(ModelFlasktests):
'<input type="hidden" name="action"
value="preview" />'
in output.data)
- user = FakeUser(['voters'], username='toshio')
- with user_set(fedora_elections.APP, user):
-
- # Election in progress
- output = self.app.get(
- '/vote/test_election3', follow_redirects=True)
- self.assertTrue(
- 'class="message">You have already voted in the
election!</'
- in output.data)
- self.assertTrue('<h3>Current elections</h3>' in
output.data)
-
def test_election_results(self):
""" Test the election_results function - the preview part.
"""
output = self.app.get(
commit 9abdca3fd5cc0343f5f5b32ef6a5f161e2d66590
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 11:28:00 2015 -0400
Further cleanup :)
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 6eac5f7..03c6821 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -200,7 +200,7 @@ def vote_select(election, revote):
for candidate in form
if candidate and candidate.short_name not in ['csrf_token',
'action']
]
- process_vote_by_cand_name(candidates, cand_name, election, votes,
revote)
+ process_vote(candidates, election, votes, revote, cand_name)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -238,22 +238,7 @@ def vote_simple(election, revote):
for candidate in form
if candidate and candidate.short_name not in ['csrf_token',
'action']
]
- for index in range(len(candidates)):
- candidate = candidates[index]
- if revote:
- vote = votes[index]
- vote.candidate_id = candidate.data
- SESSION.add(vote)
- else:
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=candidate.data,
- value=1,
- )
- SESSION.add(new_vote)
- SESSION.commit()
+ process_vote(candidates, election, votes, revote, None, 1)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -290,7 +275,7 @@ def vote_irc(election, revote):
for candidate in form
if candidate and candidate.short_name not in ['csrf_token',
'action']
]
- process_vote_by_cand_name(candidates, cand_name, election, votes, revote)
+ process_vote(candidates, election, votes, revote, cand_name)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -386,38 +371,30 @@ def election_results_text(election_alias):
stats=stats,
)
-def process_vote(candidates, election, votes, revote):
+def process_vote(candidates, election, votes, revote, cand_name=None, value=None):
for index in range(len(candidates)):
candidate = candidates[index]
if revote:
vote = votes[index]
- vote.value = int(candidate.data)
+ if value == 1:
+ vote.candidate_id = candidate.data
+ else:
+ vote.value = value if value else int(candidate.data)
SESSION.add(vote)
else:
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=candidate.short_name,
- value=int(candidate.data),
- )
- SESSION.add(new_vote)
- SESSION.commit()
+ if value == 1:
+ cand_id = candidate.data
+ elif cand_name:
+ cand_id = cand_name[candidate.short_name]
+ else:
+ cand_id = candidate.short_name
-def process_vote_by_cand_name(candidates, cand_name, election, votes, revote):
- for index in range(len(candidates)):
- candidate = candidates[index]
- if revote:
- vote = votes[index]
- vote.value = int(candidate.data)
- SESSION.add(vote)
- else:
new_vote = models.Vote(
election_id=election.id,
voter=flask.g.fas_user.username,
timestamp=datetime.now(),
- candidate_id=cand_name[candidate.short_name],
- value=int(candidate.data),
+ candidate_id=cand_id,
+ value= value if value else int(candidate.data),
)
SESSION.add(new_vote)
SESSION.commit()
commit 92ae688e1d2a907480d51b4417c33628941062af
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 10:49:36 2015 -0400
Else for revote logic
diff --git a/fedora_elections/templates/index.html
b/fedora_elections/templates/index.html
index c944703..5d15ef8 100644
--- a/fedora_elections/templates/index.html
+++ b/fedora_elections/templates/index.html
@@ -32,10 +32,11 @@
<a href="{{ url_for('vote', election_alias=election.alias)
}}">
Vote now!
</a>
- {% endif %}
+ {% else %}
<a href="{{ url_for('vote', election_alias=election.alias)
}}">
Change your vote!
</a>
+ {% endif %}
{% endif %}
</td>
</tr>
commit 436ce71fe918cb7d47fa065964e0acc9217186ec
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 10:41:50 2015 -0400
Update tests
diff --git a/tests/test_flask_simple_voting.py b/tests/test_flask_simple_voting.py
index 1eaa339..c0ea957 100644
--- a/tests/test_flask_simple_voting.py
+++ b/tests/test_flask_simple_voting.py
@@ -55,14 +55,6 @@ class FlaskSimpleElectionstests(ModelFlasktests):
self.setup_db()
- user = FakeUser(['packager'], username='toshio')
- with user_set(fedora_elections.APP, user):
- output = self.app.get(
- '/vote/test_election5', follow_redirects=True)
- self.assertTrue(
- 'class="message">You have already voted in the
election!</'
- in output.data)
-
user = FakeUser(['packager'], username='pingou')
with user_set(fedora_elections.APP, user):
output = self.app.get(
@@ -244,6 +236,52 @@ class FlaskSimpleElectionstests(ModelFlasktests):
self.assertTrue('<h3>Next 1 elections</h3>' in
output.data)
self.assertTrue('<h3>Last 2 elections</h3>' in
output.data)
+ def test_vote_simple_revote(self):
+ """ Test the vote_simple function - the re-voting part.
"""
+ #First we need to vote
+ self.setup_db()
+
+ user = FakeUser(['voters'], username='nerdsville')
+ with user_set(fedora_elections.APP, user):
+ retrieve_csrf = self.app.post('/vote/test_election5')
+ csrf_token = retrieve_csrf.data.split(
+ 'name="csrf_token" type="hidden"
value="')[1].split('">')[0]
+ # Valid input
+ data = {
+ 'candidate': 8,
+ 'action': 'submit',
+ 'csrf_token': csrf_token,
+ }
+
+ self.app.post('/vote/test_election5', data=data,
follow_redirects=True)
+ vote = fedora_elections.models.Vote
+ votes = vote.of_user_on_election(self.session, "nerdsville",
'5')
+ self.assertEqual(votes[0].candidate_id, 8)
+ #Let's not do repetition of what is tested above we aren't testing the
+ #functionality of voting as that has already been asserted
+
+ #Next, we need to try revoting
+ # Valid input
+ newdata = {
+ 'candidate': 9,
+ 'action': 'submit',
+ 'csrf_token': csrf_token,
+ }
+ output = self.app.post('/vote/test_election5', data=newdata,
follow_redirects=True)
+ #Next, we need to check if the vote has been recorded
+ self.assertEqual(output.status_code, 200)
+ self.assertTrue(
+ 'class="message">Your vote has been recorded. Thank
you!</'
+ in output.data)
+ self.assertTrue('<h3>Current elections</h3>' in
output.data)
+ self.assertTrue('<h3>Next 1 elections</h3>' in
output.data)
+ self.assertTrue('<h3>Last 2 elections</h3>' in
output.data)
+ vote = fedora_elections.models.Vote
+ votes = vote.of_user_on_election(self.session, "nerdsville",
'5')
+ self.assertEqual(votes[0].candidate_id, 9)
+
+ #If we haven't failed yet, HOORAY!
+
if __name__ == '__main__':
SUITE = unittest.TestLoader().loadTestsFromTestCase(
commit 5e2964bdd72a8bc40b7707b67d44cd9549d32b12
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 10:41:40 2015 -0400
No need to check if revote exists anymore
diff --git a/fedora_elections/templates/index.html
b/fedora_elections/templates/index.html
index abfcdd1..c944703 100644
--- a/fedora_elections/templates/index.html
+++ b/fedora_elections/templates/index.html
@@ -32,11 +32,10 @@
<a href="{{ url_for('vote', election_alias=election.alias)
}}">
Vote now!
</a>
- {% elif election.voting_type != "simple" %}
+ {% endif %}
<a href="{{ url_for('vote', election_alias=election.alias)
}}">
Change your vote!
</a>
- {% endif %}
{% endif %}
</td>
</tr>
commit f0660ec8291325607f2657c4ee077bae025afd81
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 10:39:20 2015 -0400
Add simple revoting
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 3ccc00e..6eac5f7 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -112,7 +112,7 @@ def vote(election_alias):
if election.voting_type.startswith('range'):
return vote_range(election, revote)
elif election.voting_type == 'simple':
- return vote_simple(election)
+ return vote_simple(election, revote)
elif election.voting_type == 'select':
return vote_select(election, revote)
elif election.voting_type == 'irc':
@@ -219,9 +219,9 @@ def vote_select(election, revote):
usernamemap=usernamemap,
nextaction=next_action)
-def vote_simple(election):
+def vote_simple(election, revote):
votes = models.Vote.of_user_on_election(
- SESSION, flask.g.fas_user.username, election.id, count=True)
+ SESSION, flask.g.fas_user.username, election.id)
num_candidates = election.candidates.count()
@@ -233,20 +233,27 @@ def vote_simple(election):
if form.validate_on_submit():
if form.action.data == 'submit':
- for candidate in form:
- if candidate.short_name in ['csrf_token', 'action']:
- continue
-
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=candidate.data,
- value=1,
- )
- SESSION.add(new_vote)
- SESSION.commit()
-
+ candidates = [
+ candidate
+ for candidate in form
+ if candidate and candidate.short_name not in ['csrf_token',
'action']
+ ]
+ for index in range(len(candidates)):
+ candidate = candidates[index]
+ if revote:
+ vote = votes[index]
+ vote.candidate_id = candidate.data
+ SESSION.add(vote)
+ else:
+ new_vote = models.Vote(
+ election_id=election.id,
+ voter=flask.g.fas_user.username,
+ timestamp=datetime.now(),
+ candidate_id=candidate.data,
+ value=1,
+ )
+ SESSION.add(new_vote)
+ SESSION.commit()
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
commit c4e93d5d01b0f1136423e60443741348f64c625a
Merge: 258625a b97dcc0
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Tue Sep 1 16:37:11 2015 +0200
Merge pull request #52 from NerdsvilleCEO/refactor
Some cleanup/refactoring
commit b97dcc099fe54bf9a6cec86898423c61ac86049b
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 10:22:54 2015 -0400
Some cleanup/refactoring
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index 2ca8800..3ccc00e 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -146,23 +146,7 @@ def vote_range(election, revote):
for candidate in form
if candidate and candidate.short_name not in
['csrf_token', 'action']
]
- for index in range(len(candidates)):
- candidate = candidates[index]
- if revote:
- vote = votes[index]
- vote.value = candidate.data
- SESSION.add(vote)
- else:
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=candidate.short_name,
- value=candidate.data,
- )
- SESSION.add(new_vote)
- SESSION.commit()
-
+ process_vote(candidates, election, votes, revote)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -202,14 +186,12 @@ def vote_select(election, revote):
max_selection=max_selection)
if form.validate_on_submit():
-
- cnt = 0
- for candidate in form:
- if candidate.short_name in ['csrf_token', 'action']:
- continue
- if candidate.data:
- cnt += 1
- if cnt > max_selection:
+ cnt = [
+ candidate
+ for candidate in form
+ if candidate.data and candidate.short_name not in ['csrf_token',
'action']
+ ]
+ if len(cnt) > max_selection:
flask.flash('Too many candidates submitted', 'error')
else:
if form.action.data == 'submit':
@@ -218,22 +200,7 @@ def vote_select(election, revote):
for candidate in form
if candidate and candidate.short_name not in ['csrf_token',
'action']
]
- for index in range(len(candidates)):
- candidate = candidates[index]
- if revote:
- vote = votes[index]
- vote.value = int(candidate.data)
- SESSION.add(vote)
- else:
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=cand_name[candidate.short_name],
- value=int(candidate.data),
- )
- SESSION.add(new_vote)
- SESSION.commit()
+ process_vote_by_cand_name(candidates, cand_name, election, votes,
revote)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -252,7 +219,6 @@ def vote_select(election, revote):
usernamemap=usernamemap,
nextaction=next_action)
-
def vote_simple(election):
votes = models.Vote.of_user_on_election(
SESSION, flask.g.fas_user.username, election.id, count=True)
@@ -317,22 +283,7 @@ def vote_irc(election, revote):
for candidate in form
if candidate and candidate.short_name not in ['csrf_token',
'action']
]
- for index in range(len(candidates)):
- candidate = candidates[index]
- if revote:
- vote = votes[index]
- vote.value = int(candidate.data)
- SESSION.add(vote)
- else:
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=cand_name[candidate.short_name],
- value=int(candidate.data),
- )
- SESSION.add(new_vote)
- SESSION.commit()
+ process_vote_by_cand_name(candidates, cand_name, election, votes, revote)
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()
@@ -427,3 +378,39 @@ def election_results_text(election_alias):
usernamemap=usernamemap,
stats=stats,
)
+
+def process_vote(candidates, election, votes, revote):
+ for index in range(len(candidates)):
+ candidate = candidates[index]
+ if revote:
+ vote = votes[index]
+ vote.value = int(candidate.data)
+ SESSION.add(vote)
+ else:
+ new_vote = models.Vote(
+ election_id=election.id,
+ voter=flask.g.fas_user.username,
+ timestamp=datetime.now(),
+ candidate_id=candidate.short_name,
+ value=int(candidate.data),
+ )
+ SESSION.add(new_vote)
+ SESSION.commit()
+
+def process_vote_by_cand_name(candidates, cand_name, election, votes, revote):
+ for index in range(len(candidates)):
+ candidate = candidates[index]
+ if revote:
+ vote = votes[index]
+ vote.value = int(candidate.data)
+ SESSION.add(vote)
+ else:
+ new_vote = models.Vote(
+ election_id=election.id,
+ voter=flask.g.fas_user.username,
+ timestamp=datetime.now(),
+ candidate_id=cand_name[candidate.short_name],
+ value=int(candidate.data),
+ )
+ SESSION.add(new_vote)
+ SESSION.commit()
commit 258625ae57f4205afa88fa111e8e929ae47b3465
Merge: 8dfa932 24d827d
Author: Pierre-Yves Chibon <pingou(a)pingoured.fr>
Date: Tue Sep 1 15:20:55 2015 +0200
Merge pull request #51 from NerdsvilleCEO/add-irc-revote
Add irc revote
commit 24d827d00633b1320b6d6e1c8b7839eb094e5852
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 06:49:06 2015 -0400
Modify template condition
diff --git a/fedora_elections/templates/index.html
b/fedora_elections/templates/index.html
index c796319..abfcdd1 100644
--- a/fedora_elections/templates/index.html
+++ b/fedora_elections/templates/index.html
@@ -32,7 +32,7 @@
<a href="{{ url_for('vote', election_alias=election.alias)
}}">
Vote now!
</a>
- {% elif election.voting_type == 'range' or election.voting_type ==
'select' %}
+ {% elif election.voting_type != "simple" %}
<a href="{{ url_for('vote', election_alias=election.alias)
}}">
Change your vote!
</a>
commit abb42bcbb8748f3df10a681d11095c351d6bfa7a
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 06:46:47 2015 -0400
Add IRC Revote tests
diff --git a/tests/test_flask_irc.py b/tests/test_flask_irc.py
index 9c45fa4..4fc6b69 100644
--- a/tests/test_flask_irc.py
+++ b/tests/test_flask_irc.py
@@ -55,14 +55,6 @@ class FlaskIrcElectionstests(ModelFlasktests):
self.setup_db()
- user = FakeUser(['packager'], username='toshio')
- with user_set(fedora_elections.APP, user):
- output = self.app.get(
- '/vote/test_election7', follow_redirects=True)
- self.assertTrue(
- 'class="message">You have already voted in the
election!</'
- in output.data)
-
user = FakeUser(['packager'], username='nerdsville')
with user_set(fedora_elections.APP, user):
output = self.app.get(
@@ -151,6 +143,53 @@ class FlaskIrcElectionstests(ModelFlasktests):
self.assertTrue('<h3>Next 1 elections</h3>' in
output.data)
self.assertTrue('<h3>Last 2 elections</h3>' in
output.data)
+ def test_vote_irc_revote(self):
+ """ Test the vote_irc function - the re-voting part.
"""
+ #First we need to vote
+ self.setup_db()
+
+ user = FakeUser(['voters'], username='nerdsville')
+ with user_set(fedora_elections.APP, user):
+ retrieve_csrf = self.app.post('/vote/test_election7')
+ csrf_token = retrieve_csrf.data.split(
+ 'name="csrf_token" type="hidden"
value="')[1].split('">')[0]
+ # Valid input
+ data = {
+ 'Kevin': -1,
+ 'Toshio': 1,
+ 'action': 'submit',
+ 'csrf_token': csrf_token,
+ }
+ self.app.post('/vote/test_election7', data=data,
follow_redirects=True)
+ vote = fedora_elections.models.Vote
+ votes = vote.of_user_on_election(self.session, "nerdsville",
'7')
+ self.assertEqual(votes[0].value, 1)
+ self.assertEqual(votes[1].value, -1)
+ #Let's not do repetition of what is tested above we aren't testing the
+ #functionality of voting as that has already been asserted
+
+ #Next, we need to try revoting
+ newdata = {
+ 'Kevin': 1,
+ 'Toshio': -1,
+ 'action': 'submit',
+ 'csrf_token': csrf_token,
+ }
+ output = self.app.post('/vote/test_election7', data=newdata,
follow_redirects=True)
+ #Next, we need to check if the vote has been recorded
+ self.assertEqual(output.status_code, 200)
+ self.assertTrue(
+ 'class="message">Your vote has been recorded. Thank
you!</'
+ in output.data)
+ self.assertTrue('<h3>Current elections</h3>' in
output.data)
+ self.assertTrue('<h3>Next 1 elections</h3>' in
output.data)
+ self.assertTrue('<h3>Last 2 elections</h3>' in
output.data)
+ vote = fedora_elections.models.Vote
+ votes = vote.of_user_on_election(self.session, "nerdsville",
'7')
+ self.assertEqual(votes[0].value, -1)
+ self.assertEqual(votes[1].value, 1)
+
+ #If we haven't failed yet, HOORAY!
if __name__ == '__main__':
SUITE = unittest.TestLoader().loadTestsFromTestCase(FlaskIrcElectionstests)
commit d1499f0d4a7a4df5f98b532de837aa7b1f1e9af8
Author: Joshua Santos <nerdsville(a)nerdsville.net>
Date: Tue Sep 1 06:46:28 2015 -0400
Add IRC Revoting
diff --git a/fedora_elections/elections.py b/fedora_elections/elections.py
index f37cbfa..2ca8800 100644
--- a/fedora_elections/elections.py
+++ b/fedora_elections/elections.py
@@ -116,7 +116,7 @@ def vote(election_alias):
elif election.voting_type == 'select':
return vote_select(election, revote)
elif election.voting_type == 'irc':
- return vote_irc(election)
+ return vote_irc(election, revote)
else: # pragma: no cover
flask.flash(
'Unknown election voting type: %s' % election.voting_type)
@@ -296,9 +296,9 @@ def vote_simple(election):
nextaction=next_action)
-def vote_irc(election):
+def vote_irc(election, revote):
votes = models.Vote.of_user_on_election(
- SESSION, flask.g.fas_user.username, election.id, count=True)
+ SESSION, flask.g.fas_user.username, election.id)
cand_name = {}
for candidate in election.candidates:
@@ -312,18 +312,27 @@ def vote_irc(election):
fasusers=election.candidates_are_fasusers)
if form.validate_on_submit():
if form.action.data == 'submit':
- for candidate in form:
- if candidate.short_name in ['csrf_token', 'action']:
- continue
- new_vote = models.Vote(
- election_id=election.id,
- voter=flask.g.fas_user.username,
- timestamp=datetime.now(),
- candidate_id=cand_name[candidate.short_name],
- value=candidate.data,
- )
- SESSION.add(new_vote)
- SESSION.commit()
+ candidates = [
+ candidate
+ for candidate in form
+ if candidate and candidate.short_name not in ['csrf_token',
'action']
+ ]
+ for index in range(len(candidates)):
+ candidate = candidates[index]
+ if revote:
+ vote = votes[index]
+ vote.value = int(candidate.data)
+ SESSION.add(vote)
+ else:
+ new_vote = models.Vote(
+ election_id=election.id,
+ voter=flask.g.fas_user.username,
+ timestamp=datetime.now(),
+ candidate_id=cand_name[candidate.short_name],
+ value=int(candidate.data),
+ )
+ SESSION.add(new_vote)
+ SESSION.commit()
flask.flash("Your vote has been recorded. Thank you!")
return safe_redirect_back()