Skip to content

Commit

Permalink
Merge pull request #303 from ciudadanointeligente/second_round_prima
Browse files Browse the repository at this point in the history
Second round prima
  • Loading branch information
lfalvarez committed Nov 10, 2015
2 parents 70aa8c2 + f703945 commit a651782
Show file tree
Hide file tree
Showing 11 changed files with 230 additions and 69 deletions.
57 changes: 55 additions & 2 deletions elections/bin/second_round.py
@@ -1,4 +1,12 @@
import copy
from django.db.models import AutoField


def copy_model_instance(obj):
initial = dict([(f.name, getattr(obj, f.name))
for f in obj._meta.fields
if not isinstance(f, AutoField) and\
not f in obj._meta.parents.values()])
return obj.__class__(**initial)


class SecondRoundCreator(object):
Expand All @@ -14,9 +22,54 @@ def set_name(self, name):
self.second_round_name = name

def get_second_round(self):
second_round = copy.copy(self.election)
second_round = copy_model_instance(self.election)
second_round.id = None
if self.second_round_name is not None:
second_round.name = self.second_round_name
second_round.save()
for candidate in self.candidates:
second_round.candidates.add(candidate)
self.copy_categories(second_round)
self.copy_messages(second_round)
return second_round

def copy_messages(self, second_round):
for message in self.election.messages.all():
_writeit_document = copy_model_instance(message.writeitdocument_ptr)
_writeit_document.id = None
_writeit_document.save()
_message = copy_model_instance(message)
_message.writeitdocument_ptr = _writeit_document
_message.id = None
_message.election = second_round
_message.save()
for answer in message.answers.all():
_answer = copy_model_instance(answer)
_answer.id = None
_answer.message = _message
_answer.save()

def copy_categories(self, second_round):
for category in self.election.categories.all():
category_copy = copy_model_instance(category)
category_copy.id = None
category_copy.save()
second_round.categories.add(category_copy)
for topic in category.topics.all():
_topic = copy_model_instance(topic)
_topic.id = None
_topic.category = category_copy
_topic.save()
for position in topic.positions.all():
_position = copy_model_instance(position)
_position.id = None
_position.topic = _topic
_position.save()
for taken_position in position.taken_positions.filter(person__in=self.candidates):
_taken_position = copy_model_instance(taken_position)
_taken_position.id = None
_taken_position.position = _position
_taken_position.topic = _topic
_taken_position.person = taken_position.person
_taken_position.save()

46 changes: 0 additions & 46 deletions elections/fixtures/example_data_mini.yaml

This file was deleted.

66 changes: 65 additions & 1 deletion elections/fixtures/mini_2.yaml
@@ -1,3 +1,49 @@
- fields: {description: '', extra_info_content: null, extra_info_title: null,
highlighted: true, name: "2a Circunscripcion Antofagasta",
searchable: true, slug: 2a-circunscripcion-antofagasta}
model: elections.election
pk: 1
- fields: {description: '', extra_info_content: null, extra_info_title: null,
highlighted: true, name: "4a Circunscripcion Coquimbo",
searchable: true, slug: 4a-circunscripcion-coquimbo}
model: elections.election
pk: 2
- fields: { name: Manuel Rojas }
model: popolo.person
pk: 1
- fields: { name: Alejandro Guillier}
model: popolo.person
pk: 2
- fields: { name: Pedro Araya}
model: popolo.person
pk: 3
- fields: { name: Gisela Contreras}
model: popolo.person
pk: 4
- fields: { name: Carlos Cantero}
model: popolo.person
pk: 5
- fields: { name: Daniel Guevara}
model: popolo.person
pk: 6
- fields: { name: Jimena Orrego}
model: popolo.person
pk: 7
- fields: { name: Gonzalo Uriarte}
model: popolo.person
pk: 8
- fields: { name: Mario Bertolino}
model: popolo.person
pk: 9
- fields: { name: Jorge Pizarro}
model: popolo.person
pk: 10
- fields: { name: "Adriana Munoz"}
model: popolo.person
pk: 11
- fields: { name: Luis Vega}
model: popolo.person
pk: 12
- fields: {name: Perros y gatos, slug: perros-y-gatos}
model: candidator.category
pk: 1
Expand Down Expand Up @@ -144,4 +190,22 @@
pk: 8
- fields: {topic: 6, position: 13, person: 3}
model: candidator.takenposition
pk: 9
pk: 9
- fields: {topic: 1, position: 1, person: 4}
model: candidator.takenposition
pk: 10
- fields: {topic: 1, position: 2, person: 5}
model: candidator.takenposition
pk: 11
- fields: {topic: 2, position: 4, person: 4}
model: candidator.takenposition
pk: 12
- fields: {topic: 2, position: 5, person: 5}
model: candidator.takenposition
pk: 13
- fields: {topic: 3, position: 6, person: 4}
model: candidator.takenposition
pk: 14
- fields: {topic: 3, position: 7, person: 5}
model: candidator.takenposition
pk: 15
23 changes: 23 additions & 0 deletions elections/management/commands/cloneelection.py
@@ -0,0 +1,23 @@
from django.core.management.base import BaseCommand
from elections.models import Election
from elections.bin import SecondRoundCreator


class Command(BaseCommand):
help = "Clones an election"

def add_arguments(self, parser):
parser.add_argument('election_slug', type=str)
parser.add_argument('candidates_slug', nargs='+', type=str)

def handle(self, *args, **options):
election = Election.objects.get(slug=options['election_slug'])
sc = SecondRoundCreator(election)
for candidate_slug in options['candidates_slug']:
candidate = election.candidates.get(id=candidate_slug)
sc.pick_one(candidate)
second_round = sc.get_second_round()
self.stdout.write("Clone created with name %s and slug %s" % (second_round.name, second_round.slug))
self.stdout.write("The url for it is %s" % (second_round.get_absolute_url()))


1 change: 0 additions & 1 deletion elections/migrations/0021_auto_20151008_1526.py
Expand Up @@ -13,7 +13,6 @@ def from_election_to_elections(apps, schema_editor):
candidate.elections.add(candidate.election)



class Migration(migrations.Migration):

dependencies = [
Expand Down
4 changes: 2 additions & 2 deletions elections/models.py
Expand Up @@ -40,8 +40,8 @@ class Candidate(Person, ExtraInfoMixin):

@property
def election(self):
if self.elections.all():
return self.elections.last()
if self.elections.count() == 1:
return self.elections.get()

@property
def twitter(self):
Expand Down
2 changes: 1 addition & 1 deletion elections/tests/__init__.py
Expand Up @@ -2,7 +2,7 @@

@override_settings(THEME=None)
class VotaInteligenteTestCase(TestCase):
fixtures = ['example_data_mini.yaml', 'mini_2.yaml']
fixtures = ['mini_2.yaml']

def setUp(self):
super(VotaInteligenteTestCase, self).setUp()
16 changes: 12 additions & 4 deletions elections/tests/election_detail_views_tests.py
Expand Up @@ -121,13 +121,21 @@ def test_it_has_a_percentage_of_similitude(self):
q_like_fiera = Topic.objects.filter(category__in=categories).get(label="Le gusta la Fiera??")
you_like_fiera_yes = Position.objects.get(topic=q_like_fiera, label="Si")
you_like_fiera_no = Position.objects.get(topic=q_like_fiera, label="No")
TakenPosition.objects.create(person=candidate1, position=you_like_fiera_yes, topic=q_like_fiera)
TakenPosition.objects.create(person=candidate2, position=you_like_fiera_no, topic=q_like_fiera)
tpf1 = TakenPosition.objects.get(person=candidate1, topic=q_like_fiera)
tpf1.position = you_like_fiera_yes
tpf1.save()
tpf2 = TakenPosition.objects.get(person=candidate2, topic=q_like_fiera)
tpf2.position = you_like_fiera_no
tpf2.save()
#this adds 1/3 to the similitude number
q_like_benito = Topic.objects.filter(category__in=categories).get(label="Le gusta Benito??")
you_like_benito_yes = Position.objects.get(topic=q_like_benito, label="Si")
TakenPosition.objects.create(person=candidate1, position=you_like_benito_yes, topic=q_like_benito)
TakenPosition.objects.create(person=candidate2, position=you_like_benito_yes, topic=q_like_benito)
tpb1 = TakenPosition.objects.get(person=candidate1, topic=q_like_benito)
tpb1.position = you_like_benito_yes
tpb1.save()
tpb2 = TakenPosition.objects.get(person=candidate2, topic=q_like_benito)
tpb2.position = you_like_benito_yes
tpb2.save()
#this guys didn't answer the same thing
#no one has answered this question
url = reverse('face_to_face_two_candidates_detail_view',
Expand Down
74 changes: 67 additions & 7 deletions elections/tests/second_round_tests.py
@@ -1,9 +1,10 @@
# coding=utf-8
from elections.tests import VotaInteligenteTestCase as TestCase
from elections import get_writeit_instance
from django.test.utils import override_settings
from elections.models import Election, Candidate
from elections.models import Election, Candidate, VotaInteligenteMessage, VotaInteligenteAnswer
from elections.bin import SecondRoundCreator
from candidator.models import TakenPosition
from django.core.management import call_command
from django.utils.six import StringIO


class SecondRoundCreationTestCase(TestCase):
Expand All @@ -18,14 +19,73 @@ def test_create_a_second_round(self):
sc.pick_one(self.carlos)
self.assertEquals(sc.candidates[0], self.adela)
self.assertEquals(sc.candidates[1], self.carlos)

sc.set_name('second Round election')

second_round = sc.get_second_round()

self.assertIsInstance(second_round, Election)

self.assertEquals(second_round.name, 'second Round election')
# self.assertEquals(second_round.candidates.count(), 2)
# self.assertIn(self.adela, second_round.candidates.all())
# self.assertIn(self.carlos, second_round.candidates.all())
self.assertNotEquals(second_round.slug, self.tarapaca.slug)
self.assertEquals(second_round.candidates.count(), 2)
self.assertIn(self.adela, second_round.candidates.all())
self.assertIn(self.carlos, second_round.candidates.all())

def test_copy_questions(self):
sc = SecondRoundCreator(self.tarapaca)
sc.pick_one(self.adela)
sc.pick_one(self.carlos)
second_round = sc.get_second_round()
self.assertEquals(second_round.categories.count(), self.tarapaca.categories.count())
for category in self.tarapaca.categories.all():
_category = second_round.categories.get(name=category.name)
self.assertEquals(_category.topics.count(), category.topics.count())
for topic in category.topics.all():
_topic = _category.topics.get(label=topic.label)
self.assertTrue(TakenPosition.objects.filter(topic=_topic, person=self.adela))
self.assertTrue(TakenPosition.objects.filter(topic=_topic, person=self.carlos))
for position in topic.positions.all():
self.assertTrue(_topic.positions.filter(label=position.label))

def test_copy_messages_and_answers(self):
candidate3 = Candidate.objects.get(id=6)
message = VotaInteligenteMessage.objects.create(election=self.tarapaca,
author_name='author',
author_email='author@email.com',
subject='subject',
content='content',
slug='subject-slugified',
moderated=True
)
message.people.add(self.adela)
message.people.add(self.carlos)
message.people.add(candidate3)

answer = VotaInteligenteAnswer.objects.create(content=u'Hey I\'ve had to speak english in the last couple of days',
message=message,
person=self.adela
)
sc = SecondRoundCreator(self.tarapaca)
sc.pick_one(self.adela)
sc.pick_one(self.carlos)
second_round = sc.get_second_round()
the_copied_message = second_round.messages.get()
self.assertNotEquals(the_copied_message.id, message.id)
self.assertEquals(the_copied_message.author_name, message.author_name)
self.assertEquals(the_copied_message.subject, message.subject)
self.assertEquals(the_copied_message.content, message.content)
the_copied_answer = the_copied_message.answers.get()
self.assertNotEquals(the_copied_answer.id, answer.id)
self.assertEquals(the_copied_answer.content, answer.content)
self.assertEquals(the_copied_answer.person, self.adela)

def test_management_command(self):
out = StringIO()
previous_count = Election.objects.all().count()
call_command('cloneelection', self.tarapaca.slug, self.adela.id, self.carlos.id, stdout=out)
after_count = Election.objects.all().count()
self.assertEquals(after_count, previous_count + 1)
second_round = Election.objects.last()
self.assertEquals(second_round.name, self.tarapaca.name)
self.assertIn(second_round.name, out.getvalue())
self.assertIn(second_round.get_absolute_url(), out.getvalue())
6 changes: 3 additions & 3 deletions elections/tests/version2/candidates_flatpages_tests.py
@@ -1,12 +1,12 @@
# coding=utf-8
from elections.tests import VotaInteligenteTestCase as TestCase
from elections.models import Candidate, CandidateFlatPage
from elections.models import Candidate, CandidateFlatPage, Election
from django.core.urlresolvers import reverse


class CandidateFlatpagesTestCase(TestCase):
def setUp(self):
pass
self.election = Election.objects.get(id=2)

def test_instanciate_a_flatpage(self):

Expand All @@ -23,7 +23,7 @@ def test_instanciate_a_flatpage(self):
self.assertTrue(page)
self.assertEquals(page.candidate, candidate)
self.assertTrue(page.get_absolute_url())
url = reverse('candidate_flatpage', kwargs={'election_slug': candidate.election.slug,
url = reverse('candidate_flatpage', kwargs={'election_slug': self.election.slug,
'slug': candidate.id,
'url': page.url
}
Expand Down

0 comments on commit a651782

Please sign in to comment.