run-through of quickvotes. Also added support for tracking IP addresses
into the database.
15 files changed:
session.session_id, @election.id])[0]
unless @voter
@voter = QuickVoter.new
session.session_id, @election.id])[0]
unless @voter
@voter = QuickVoter.new
- @voter.election = Election.find_all( [ "name = ?", params[:votename] ] )[0]
+ @voter.election = QuickVote.find_all( [ "name = ?", params[:votename] ] )[0]
@voter = QuickVoter.new()
@voter.election = election
@voter.session_id = session.session_id
@voter = QuickVoter.new()
@voter.election = election
@voter.session_id = session.session_id
+ @voter.ipaddress = request.env["REMOTE_ADDR"]
@voter.save
@voter.reload
@voter.save
@voter.reload
- @election = Election.find_all( ["name = ?", params[:votename]] )[0]
+ @election = QuickVote.find_all( ["name = ?", params[:votename]] )[0]
preference_tally = []
plurality_tally = []
preference_tally = []
plurality_tally = []
+ def shortdesc
+ shortdesc = description.split(/\n/)[0]
+ end
+
+ def longdesc
+ longdesc = description.split(/\n/)[1..-1].join("")
+ longdesc.length > 0 ? longdesc : nil
+ end
self.votes = rel_votes.collect { |vote| candidate_ids[ vote - 1 ] }
end
self.votes = rel_votes.collect { |vote| candidate_ids[ vote - 1 ] }
end
+ def votestring
+ self.votes.join("")
+ end
+
vote.destroy if vote
super
end
vote.destroy if vote
super
end
<% %>
<% if result.winner? and result.winners.length == 1%>
<p><em>The winner is:
<% %>
<% if result.winner? and result.winners.length == 1%>
<p><em>The winner is:
- <strong><%= @candidates[result.winner].name %></strong></em></p>
+ <strong><%= @candidates[result.winner].name.capitalize %></strong></em></p>
<% elsif result.winner? and result.winners.length > 1 %>
<p><em>There was a tie. The winners are: <strong><%=
<% elsif result.winner? and result.winners.length > 1 %>
<p><em>There was a tie. The winners are: <strong><%=
- result.winners.collect {|w| @candidates[w]}.join(", ") %></strong></em></p>
+ result.winners.collect {|w| @candidates[w].to_s.capitalize}.join(", ") %></strong></em></p>
<% else %>
<p><em>There is no winner using this method. </em></strong></p>
<% end %>
<% else %>
<p><em>There is no winner using this method. </em></strong></p>
<% end %>
-<h1>Create QuickVote</h1>
+<h1><%= @quickvote ? "Review and Confirm" : "Create QuickVote" %></h1>
<%= error_messages_for 'quickvote' %>
<% if @quickvote %>
<%= error_messages_for 'quickvote' %>
<% if @quickvote %>
-<p>Please review the data you've entered and confirm. The candidates for
-the election submitted include:</p>
+
+<p>Please review the data you've entered and confirm it. The candidates
+for the vote you've submitted include:</p>
<ul>
<% for candidate in @quickvote.raw_candidates %>
<ul>
<% for candidate in @quickvote.raw_candidates %>
- <li><%= candidate %></li>
+ <li><%= candidate.capitalize %></li>
<%= form_tag :action => 'create' %>
<!--[form:election]-->
<%= form_tag :action => 'create' %>
<!--[form:election]-->
-<p><label for="quickvote_name">Vote Name<br />
+<p><label for="quickvote_name">Super-short name (for URL)<br />
-<em><font size="-1">Required; 5-12 characters; only letters and numbers; no spaces</font></em></label><br/>
+<em><font size="-1">required; 5-12 characters; only letters and numbers; no spaces</font></em></label><br/>
-<%= text_field 'quickvote', 'name' %></p>
+<%= text_field 'quickvote', 'name', :size => 15, :maxsize => 12 %></p>
-<p><label for="quickvote_description">Description <em><font
-size="-1">Optional</font></em></label><br/>
+<p><label for="quickvote_description">Description<em><br />
+<font size="-1">optional; one line summary on the first line</font></em></label><br/>
-<%= text_area 'quickvote', 'description', :rows => 2 %></p>
+<%= text_area 'quickvote', 'description', :cols => 50, :rows => 4 %></p>
<p><label for="quickvote_candidatelist">Choices/Candidates<em><br />
<p><label for="quickvote_candidatelist">Choices/Candidates<em><br />
-<font size="-1">Seperate choices with a ";". At least two are required.</font></em></label><br/>
+<font size="-1">seperate choices with a ";"; at least two are required</font></em></label><br/>
-<%= text_area 'quickvote', 'candidatelist', :rows => 3 %></p>
+<%= text_area 'quickvote', 'candidatelist', :cols => 50, :rows => 2 %></p>
<p><% if @quickvote -%>
<%= submit_tag "Confirm" -%>
<%= hidden_field :quickvote, :reviewed, :value => 1 %>
<% else %>
<p><% if @quickvote -%>
<%= submit_tag "Confirm" -%>
<%= hidden_field :quickvote, :reviewed, :value => 1 %>
<% else %>
- <%= submit_tag "Create QuickVote" -%>
+ <%= submit_tag "Submit" -%>
-<h1>QuickVote: <em><%= @voter.election.name %></em></h1>
-<p><strong>Description:</strong></p>
-<blockquote><%= @voter.election.description %></blockquote>
+<% if @voter.election.shortdesc %>
+ <h1><%= @voter.election.shortdesc %></h1>
+<% else %>
+ <h1>QuickVote</h1>
+<% end %>
+
+<% if @voter.election.longdesc %>
+ <p><strong>Description:</strong></p>
+ <blockquote><%= @voter.election.longdesc %></blockquote>
+
+<h2>Vote</h2>
+<% end %>
-<h2>Vote in Election</h2>
<% if @voter.session_id %>
<p>You have already voted. You can:</p>
<% if @voter.session_id %>
<p>You have already voted. You can:</p>
-<h1><em><%= @election.name %></em> Results</h1>
+<% if @election.shortdesc %>
+ <p><strong>Description:</strong></p>
+ <blockquote><em><%= @election.shortdesc %></em>
+ <% if @election.longdesc -%>
+ <br />
+ <%= h(@election.longdesc) -%>
+ <% end -%>
+ </blockquote>
+<% end %>
+
+<p><strong>Candidates/choices:</strong></p>
+
+<ol>
+ <% for candidate in @election.candidates.sort %>
+ <li><%= candidate.name.capitalize %></li>
+ <% end %>
+</ol>
+
+<p><strong>Number of voters:</strong></p>
+ <blockquote>
+ <%= @election.voters.length %> (see below for details)
+ </blockquote>
+
+<h2>Winners</h2>
-<p>Total Votes: <strong><%= @election.voters.length %></strong></p>
<div class="mainresultbox">
<div class="mainresultbox">
-<h2>Condorcet (w/ Cloneproof SSD) Results</h2>
+<center><h3>Condorcet (w/ Cloneproof SSD) Results</h3></center>
<%= render :partial => 'result', :object => @ssd_result %>
</div>
<div class="resultbox">
<%= render :partial => 'result', :object => @ssd_result %>
</div>
<div class="resultbox">
-<h2>Plurality Results</h2>
+<h3>Plurality Results</h3>
<%= render :partial => 'result', :object => @plurality_result %>
</div>
<div class="resultbox">
<%= render :partial => 'result', :object => @plurality_result %>
</div>
<div class="resultbox">
-<h2>Approval Result</h2>
+<h3>Approval Result</h3>
<p><font size="-1">(Assuming top two choices are "approved.")</font></p>
<%= render :partial => 'result', :object => @approval_result %>
</div>
<div class="resultbox">
<p><font size="-1">(Assuming top two choices are "approved.")</font></p>
<%= render :partial => 'result', :object => @approval_result %>
</div>
<div class="resultbox">
-<h2>Simple Condorcet Results</h2>
+<h3>Simple Condorcet Results</h3>
<%= render :partial => 'result', :object => @condorcet_result %>
</div>
<div class="resultbox">
<%= render :partial => 'result', :object => @condorcet_result %>
</div>
<div class="resultbox">
-<h2>Borda Count Results</h2>
+<h3>Borda Count Results</h3>
<%= render :partial => 'result', :object => @borda_result %>
</div>
<div class="resultbox">
<%= render :partial => 'result', :object => @borda_result %>
</div>
<div class="resultbox">
-<h2>Instant Runoff (IRV) Results</h2>
+<h3>Instant Runoff (IRV) Results</h3>
<%= render :partial => 'result', :object => @runoff_result %>
</div>
<%= render :partial => 'result', :object => @runoff_result %>
</div>
+
+<div class="clearbox"></div>
+
+<h2>Voters</h2>
+
+<table border="1">
+<tr>
+<th>IP Address</th>
+<th>DNS/Host</th>
+<th>Vote</th>
+</tr>
+<% for voter in @election.voters %>
+ <tr>
+ <td><%= voter.ipaddress %></td>
+ <td><%= `host #{voter.ipaddress}`.sub(/^.*pointer (.*)\.$/, '\1') %></td>
+ <td><%= voter.vote.votestring %></td>
+ </tr>
+<% end %>
+</table>
+<% -%>
+<h2>Your QuickVote Was Created</h2>
+<p>Please direct voters to:</p>
+
+<blockquote><strong>
+ <%= quickvote_url( :votename => @quickvote.name ) -%>
+</strong></blockquote>
+
+<p>This vote will close on <em><%= @quickvote.enddate %></em></p>
<p>QuickVotes are open to the public but are not publicly listed on the
HyperChad site. Voters do not need to log in or authenticate to
participate in this election.</p>
<p>QuickVotes are open to the public but are not publicly listed on the
HyperChad site. Voters do not need to log in or authenticate to
participate in this election.</p>
-<p>Direct voters to:</p>
-<blockquote><strong><%= quickvote_url( :votename => @quickvote.name ) %></strong></blockquote>
-
-<p>This vote will expire on <em><%= @quickvote.enddate %></em></p>
-
-<p><%= link_to "Visit in or vote in your QuickVote", quickvote_url( :votename => @quickvote.name ) %></p>
+<p><%= link_to "Jump to your QuickVote.", quickvote_url( :votename => @quickvote.name ) %></p>
<p>Your vote has been recorded with the following ranked
preferences:</p>
<ol>
<% for rank in @voter.vote.rankings.sort %>
<p>Your vote has been recorded with the following ranked
preferences:</p>
<ol>
<% for rank in @voter.vote.rankings.sort %>
- <li><%= rank.candidate.name %> </li>
+ <li><%= rank.candidate.name.capitalize %> </li>
-<p><em>QuickVotes</em> are unstructured votes, more like polls, without
-the voter verifiability, anonymity, and other more complex features of
-HyperChad. They are the quickest way to make a decision using a variety
-of preferential and non-preficial election methods, or to compare
-between methods.</p>
+<p><em>QuickVotes</em> are like polls: unstructured, non-anonymous and
+without the complex features of <em>HyperChad</em>. They are the
+quickest way to make a decision or to compare between voting
+methods.</p>
<p><%= link_to "Create QuickVote.", :controller => 'quickvote', :action => 'create' %></p>
<p><%= link_to "Create QuickVote.", :controller => 'quickvote', :action => 'create' %></p>
<p><strong>Candidates or choices:</strong></p>
<ol>
<% for candidate in @voter.election.candidates.sort %>
<p><strong>Candidates or choices:</strong></p>
<ol>
<% for candidate in @voter.election.candidates.sort %>
- <li><%= candidate.name %></li>
+ <li><%= candidate.name.capitalize %></li>
<% end %>
</ol>
<p>In the box below, list each choice in order of most preferred to
<% end %>
</ol>
<p>In the box below, list each choice in order of most preferred to
-least preferred. <em>(For example, 123 or 321 or 213, etc.)</em></p>
+least preferred. Please list <em>all</em> choices in every vote.
+<em>(For example, 123 or 321 or 213, etc.)</em></p>
<% if @voter.election.quickvote? %>
<%= form_tag quickaction_url( :votename => @voter.election.name, :action => 'confirm') %>
<% if @voter.election.quickvote? %>
<%= form_tag quickaction_url( :votename => @voter.election.name, :action => 'confirm') %>
require 'randarray'
require 'rubyvote'
require 'randarray'
require 'rubyvote'
+class String
+ def capitalize
+ if self.length <= 1
+ self.upcase
+ else
+ self.split(//)[0].upcase + self..split(//)[1..-1].join("")
+ end
+ end
+end
+
module LoginEngine
config :salt, "voothingboat"
config :email_from, MAIL_CONFIG[:from]
module LoginEngine
config :salt, "voothingboat"
config :email_from, MAIL_CONFIG[:from]
contacted tinyint NOT NULL DEFAULT 0,
election_id int NOT NULL,
session_id varchar(32) DEFAULT NULL,
contacted tinyint NOT NULL DEFAULT 0,
election_id int NOT NULL,
session_id varchar(32) DEFAULT NULL,
+ ipaddress varchar(32) DEFAULT NULL,
constraint fk_election_voter foreign key (election_id) references election(id),
primary key (id)
);
constraint fk_election_voter foreign key (election_id) references election(id),
primary key (id)
);
text-shadow: #999999 0.2em 0.2em 3px;
}
text-shadow: #999999 0.2em 0.2em 3px;
}
a:link { font-weight: bold; color: #BD7589; text-decoration: underline; }
a:link { font-weight: bold; color: #BD7589; text-decoration: underline; }
-a:visited { color: #BD7589; text-decoration: underline; }
+a:visited { font-weight: bold; color: #BD7589; text-decoration: underline; }
a:hover { color: #FFFFFF; text-decoration: none; background: #0063DC; }
a:active { color: #FFFFFF; text-decoration: none; background: #0259C4; }
a:hover { color: #FFFFFF; text-decoration: none; background: #0063DC; }
a:active { color: #FFFFFF; text-decoration: none; background: #0259C4; }
#top h3 { font-size: 30px; }
#links { text-align : right; }
#top h3 { font-size: 30px; }
#links { text-align : right; }
-#links a { color: #FFF; }
-#links a:visited { font-weight: bold; }
+#links a { color: #FFF; font-weight: bold; }
+#links a:visited { color: #FFF; font-weight: bold; }
.ListLine0 {
background: #e0f8f8;
.ListLine0 {
background: #e0f8f8;
.mainresultbox {
width: 100%;
padding: 7px;
.mainresultbox {
width: 100%;
padding: 7px;
- margin-right: 10px;
- margin-bottom: 10px;
+ margin-right: 30px;
+ margin-bottom: 30px;
border-style: dotted;
border-width: 1px;
}
border-style: dotted;
border-width: 1px;
}
+.clearbox {
+ clear: both;
+ margin: 30px;
+}