diff options
author | Robin H. Johnson <robbat2@gentoo.org> | 2018-07-22 22:52:18 -0700 |
---|---|---|
committer | Robin H. Johnson <robbat2@gentoo.org> | 2018-07-22 23:04:56 -0700 |
commit | 45a2068b86d1c785def61bffe552b3ddac98d9b7 (patch) | |
tree | 2c1fa99887465f748120b36f74ccc7cab44d9971 | |
parent | Prepare trustees-201807 election (diff) | |
download | elections-45a2068b86d1c785def61bffe552b3ddac98d9b7.tar.gz elections-45a2068b86d1c785def61bffe552b3ddac98d9b7.tar.bz2 elections-45a2068b86d1c785def61bffe552b3ddac98d9b7.zip |
Add election state tracking
Add common election state tracking, with an optional slop factor in
collecting status for usage in statify runs (so we can collect final
stats right after the close of the election).
This adds a 'valid' (boolean), 'state' (human-readable), and
'valid_slop' (boolean) keys to the election objects.
Statify now prints the 'state' of the election during output phase, and
correctly respects the getopt parameters in long-standing usage output.
Signed-off-by: Robin H. Johnson <robbat2@gentoo.org>
-rw-r--r-- | Votify.pm | 44 | ||||
-rwxr-xr-x | countify | 2 | ||||
-rwxr-xr-x | listify | 2 | ||||
-rwxr-xr-x | statify | 60 | ||||
-rwxr-xr-x | votify | 2 |
5 files changed, 79 insertions, 31 deletions
@@ -110,7 +110,7 @@ sub get_elections_list { } sub grabfile_int { - my $f = shift; + my $f = shift || die "need filename"; #print "Checking $f\n"; my $i = 0; open my $fh, '<', $f or return -1; @@ -125,6 +125,9 @@ sub grabfile_int { sub get_single_election_hashref { my $election_name = shift; + die "need election_name" unless defined $election_name; + my $stoptime_slop = shift; + die "need stoptime_slop" unless defined $stoptime_slop; my $election_dir = validate_election_dir($election_name); return undef unless defined $election_dir; my %election; @@ -136,27 +139,42 @@ sub get_single_election_hashref { $election{"${fn}file"} = $filename; }; #print Dumper(%election); - $election{starttime} = grabfile_int($election{'startfile'}); - $election{stoptime} = grabfile_int($election{'stopfile'}); + my $starttime = $election{starttime} = grabfile_int($election{'startfile'}); + my $stoptime = $election{stoptime} = grabfile_int($election{'stopfile'}); + my $valid_noslop = ((not defined $starttime or $starttime < time) and + (not defined $stoptime or ($stoptime) > time)); + my $valid_slop = ((not defined $starttime or $starttime < time) and + (not defined $stoptime or ($stoptime+$stoptime_slop) > time)); + $election{valid} = $valid_noslop; + $election{valid_slop} = $valid_slop; + if(time < $starttime) { + $election{state} = 'not-yet-opened'; + } elsif(time >= $starttime and time < $stoptime) { + $election{state} = 'open'; + } elsif(time >= $stoptime) { + $election{state} = 'closed'; + } else { + die "Unable to determine state of election $election_name"; + } return \%election; } sub get_elections_hash { + my $stoptime_slop = shift; + die "need stoptime_slop" unless defined $stoptime_slop; my %elections; my @elections_list = get_elections_list(); #print Dumper(\@elections_list); - %elections = map { $_ => get_single_election_hashref($_) } @elections_list; + %elections = map { $_ => get_single_election_hashref($_, $stoptime_slop) } @elections_list; return %elections; } sub get_open_elections_hash { - my %elections = get_elections_hash(); + my $stoptime_slop = shift; + die "need stoptime_slop" unless defined $stoptime_slop; + my %elections = get_elections_hash($stoptime_slop); my @open_elections = grep { - my $starttime = $elections{$_}{'starttime'}; - my $stoptime = $elections{$_}{'stoptime'}; - my $valid = ((not defined $starttime or $starttime < time) and - (not defined $stoptime or $stoptime > time)); - $valid; + $elections{$_}{'valid_slop'}; } keys %elections; return map { $_ => $elections{$_} } @open_elections; } @@ -174,7 +192,7 @@ sub new { officials => [], }; - my $election = Votify::get_single_election_hashref($self->{'election'}); + my $election = Votify::get_single_election_hashref($self->{'election'}, 0); # no point in waiting to load open(F, '<', $election->{'officialsfile'}) or die("failed to open officials file"); @@ -211,7 +229,7 @@ sub new { }; # no point in waiting to load - my $election = Votify::get_single_election_hashref($self->{'election'}); + my $election = Votify::get_single_election_hashref($self->{'election'}, 0); open(F, '<', $election->{'votersfile'}) or die("failed to open voters file"); chomp(@voterlist = <F>); @@ -639,7 +657,7 @@ sub read { sub populate { my ($self) = @_; - my $election = Votify::get_single_election_hashref($self->{'election'}); + my $election = Votify::get_single_election_hashref($self->{'election'}, 0); $self->read($election->{'ballotfile'}); @{$self->{'choices'}} = List::Util::shuffle(@{$self->{'choices'}}); } @@ -35,7 +35,7 @@ my %opt; # Collect the open elections my (%open_elections, $usage_elections); -%open_elections = Votify::get_open_elections_hash(); +%open_elections = Votify::get_open_elections_hash(0); if (scalar keys %open_elections) { $usage_elections = join("\n ", keys %open_elections); } else { @@ -36,7 +36,7 @@ my (%opt, %elections); # Collect the open elections my ($usage_elections); -%elections = Votify::get_open_elections_hash(); +%elections = Votify::get_open_elections_hash(0); if (scalar(keys %elections) > 0) { $usage_elections = "Presently available elections:\n" . join('', map { @@ -38,7 +38,7 @@ my %opt; # Collect the open elections my (%open_elections, $usage_elections); -%open_elections = Votify::get_open_elections_hash(); +%open_elections = Votify::get_open_elections_hash(0); if (scalar keys %open_elections) { $usage_elections = join("\n ", keys %open_elections); } else { @@ -48,14 +48,18 @@ if (scalar keys %open_elections) { # rest of usage my $usage = <<EOT; -usage: - $zero [OPTS] <election> - $zero [OPTS] --all +usage: + $zero [OPTS] [options] <election> + $zero [OPTS] [options] --all where options are: - --all Run on all open elections + --all Run on all open elections + +where optional parameters are: + --write-to-officials Write statistics to officials homedirs + --stoptime-slop=N Extra time after election stop-time to consider for statistics gathering and <election> is one of the elections currently in-progress. The following elections are currently open: @@ -67,6 +71,28 @@ EOT ###################################################################### # Main ###################################################################### +package main; + +my ($result) = GetOptions( + \%opt, + 'all', + 'write-to-officials', + 'stoptime-slop=i', + 'help', + 'version', +); +if ($opt{'help'} or not %opt) { print STDERR $usage; exit 0 } +if ($opt{'version'}) { print STDERR $version; exit 0 } +die "$zero: election required; use --help for help\n" unless @ARGV == 1 || $opt{'all'}; + +%open_elections = Votify::get_open_elections_hash($opt{'stoptime-slop'}) if $opt{'stoptime-slop'} && $opt{'stoptime-slop'} >= 0; + +unless($opt{'all'}) { + for my $election_name (keys %open_elections) { + delete $open_elections{$election_name} unless $election_name eq $ARGV[0]; + } +} + for my $election_name (keys %open_elections) { my (@officials, @voters); open(F, '<', $open_elections{$election_name}{'officialsfile'}) @@ -98,8 +124,10 @@ for my $election_name (keys %open_elections) { submitted => $count_submit, pending => $count_pending, }; + my $election_state = $open_elections{$election_name}{'state'}; my $results_buffer = '' .sprintf("Election: %s\n", $election_name) + .sprintf("State: %s\n", $election_state) .sprintf("Timestamp: %s\n", POSIX::strftime($Votify::datefmt, gmtime)) .sprintf("Eligable voters: %d\n", $count_voters) .sprintf("Submitted votes: %d\n", $count_submit) @@ -108,16 +136,18 @@ for my $election_name (keys %open_elections) { .sprintf("Pending Turnout: %02.3f%%\n", ($count_submit+$count_pending)*100.0/$count_voters); print "$results_buffer\n"; - umask 057; - for my $officialname (@officials) { - my $fn = catfile('/home', $officialname, 'voter-turnout-'.$election_name); - open(F, '>', $fn) or - die("failed to open voter turnout file ($fn): $!"); - print F $results_buffer; - close F; - chown ((getpwnam($officialname))[2]), 0, ($fn) or - die("failed to chown voter turnout file ($fn): $!"); - } + if($opt{'write-to-officials'}) { + umask 057; + for my $officialname (@officials) { + my $fn = catfile('/home', $officialname, 'voter-turnout-'.$election_name); + open(F, '>', $fn) or + die("failed to open voter turnout file ($fn): $!"); + print F $results_buffer; + close F; + chown ((getpwnam($officialname))[2]), 0, ($fn) or + die("failed to chown voter turnout file ($fn): $!"); + } + } } @@ -35,7 +35,7 @@ my (%opt); # Collect the open elections my (%open_elections, $usage_elections); -%open_elections = Votify::get_open_elections_hash(); +%open_elections = Votify::get_open_elections_hash(0); if (scalar keys %open_elections) { $usage_elections = join("\n ", keys %open_elections); } else { |