/// <Summary>Update the Ballot status of this ballot, based on these Votes.</Summary> /// <param name="ballot">The Ballot or vBallotInfo to check and update.</param> /// <param name="currentVotes">The list of Votes in this Ballot</param> /// <param name="refreshVoteStatus"></param> /// <returns>Returns the updated status code</returns> public BallotStatusWithSpoilCount UpdateBallotStatus(Ballot ballot, List <VoteInfo> currentVotes, bool refreshVoteStatus, bool forceSave = false) { //double check: currentVotes.ForEach(vi => AssertAtRuntime.That(vi.BallotGuid == ballot.BallotGuid)); if (refreshVoteStatus) { VoteAnalyzer.UpdateAllStatuses(currentVotes, new VoteCacher(Db).AllForThisElection, new Savers(Db).VoteSaver); } if (DetermineStatusFromVotesList(ballot.StatusCode, currentVotes, out var newStatus, out var spoiledCount) || forceSave) { BallotSaver(DbAction.Attach, ballot); ballot.StatusCode = newStatus; // BallotSaver(DbAction.Save, ballot); new BallotCacher(Db).UpdateItemAndSaveCache(ballot); Db.SaveChanges(); } Db.SaveChanges(); return(new BallotStatusWithSpoilCount { Status = BallotStatusEnum.Parse(newStatus), SpoiledCount = spoiledCount }); }
private string GetSmsTemplate(string emailTemplate) { var path = $"{AppDomain.CurrentDomain.BaseDirectory}/MessageTemplates/Sms/{emailTemplate}.txt"; AssertAtRuntime.That(File.Exists(path), "Missing SMS template"); return File.ReadAllText(path); }
private string GetEmailTemplate(string emailTemplate) { var path = $"{AppDomain.CurrentDomain.BaseDirectory}/MessageTemplates/Email/{emailTemplate}.html"; AssertAtRuntime.That(File.Exists(path), "Missing email template"); return(File.ReadAllText(path)); }
/// <Summary>Update the Ballot status of this ballot, based on these Votes.</Summary> /// <param name="ballot">The Ballot or vBallotInfo to check and update.</param> /// <param name="currentVotes">The list of Votes in this Ballot</param> /// <param name="refreshVoteStatus"></param> /// <returns>Returns the updated status code</returns> public BallotStatusWithSpoilCount UpdateBallotStatus(Ballot ballot, List <VoteInfo> currentVotes, bool refreshVoteStatus) { //double check: currentVotes.ForEach(vi => AssertAtRuntime.That(vi.BallotGuid == ballot.BallotGuid)); if (refreshVoteStatus) { VoteAnalyzer.UpdateAllStatuses(currentVotes, new VoteCacher(Db).AllForThisElection, new Savers(Db).VoteSaver); } string newStatus; int spoiledCount; //if (IsSingleNameElection) //{ // if (ballot.StatusCode != BallotStatusEnum.Ok) // { // BallotSaver(DbAction.Attach, ballot); // ballot.StatusCode = BallotStatusEnum.Ok; // BallotSaver(DbAction.Save, ballot); // } // return new BallotStatusWithSpoilCount // { // Status = BallotStatusEnum.Ok, // SpoiledCount = 0 // }; //} if (DetermineStatusFromVotesList(ballot.StatusCode, currentVotes, out newStatus, out spoiledCount)) { BallotSaver(DbAction.Attach, ballot); ballot.StatusCode = newStatus; BallotSaver(DbAction.Save, ballot); } return(new BallotStatusWithSpoilCount { Status = BallotStatusEnum.Parse(newStatus), SpoiledCount = spoiledCount }); }
// private void ClearOutOldComputerRecords() // { // // backward compatible... remove all records from database // // // const int maxMinutesOfNoContact = 30; // var computerCacher = new ComputerCacher(Db); // // var now = DateTime.Now; // var computers = computerCacher.AllForThisElection; // // computerCacher.RemoveItemsAndSaveCache( // computers.Where(c => !c.LastContact.HasValue // || (now - c.LastContact.Value).TotalMinutes > maxMinutesOfNoContact)); // } /// <Summary>Move this computer into this location (don't change the computer code)</Summary> public bool MoveCurrentComputerIntoLocation(int locationId) { var location = new LocationCacher(GetNewDbContext()).AllForThisElection.SingleOrDefault(l => l.Id == locationId); if (location == null) { // ignore the request return(false); } var computer = UserSession.CurrentComputer; AssertAtRuntime.That(computer != null, "computer missing"); AssertAtRuntime.That(computer.ElectionGuid == location.ElectionGuid, "can't switch elections"); computer.LocationGuid = location.LocationGuid; new ComputerCacher().UpdateComputer(computer); SessionKey.CurrentLocationGuid.SetInSession(location.LocationGuid); // reset ballot # SessionKey.CurrentBallotId.SetInSession(0); if (UserSession.CurrentElection.IsSingleNameElection) { // for single name elections, only have one ballot per computer per location. (But if altered from a normal election to a single name election, may have multiple.) //TODO //var ballotId = // new BallotCacher(Db).AllForThisElection.Where(b => b.LocationGuid == location.LocationGuid // && b.ComputerCode == computer.ComputerCode) // .OrderBy(b => b.BallotNumAtComputer) // .Select(b => b.Id).FirstOrDefault(); //if (ballotId != 0) //{ // SessionKey.CurrentBallotId.SetInSession(ballotId); //} } return(true); }
public VoteInfo(Vote vote, Election election, Ballot ballot, Location location, Person person) { VoteId = vote.C_RowId; SingleNameElectionCount = vote.SingleNameElectionCount; PositionOnBallot = vote.PositionOnBallot; PersonCombinedInfoInVote = vote.PersonCombinedInfo; VoteIneligibleReasonGuid = vote.InvalidReasonGuid; VoteStatusCode = vote.StatusCode; OnlineVoteRaw = vote.OnlineVoteRaw; //ballot BallotGuid = ballot.BallotGuid; BallotId = ballot.C_RowId; BallotStatusCode = ballot.StatusCode; C_BallotCode = ballot.C_BallotCode; //Location LocationId = location == null ? 0 : location.C_RowId; ElectionGuid = election.ElectionGuid; if (person != null) { AssertAtRuntime.That(person.PersonGuid == vote.PersonGuid); new PeopleModel().ApplyVoteReasonFlags(person); PersonId = person.C_RowId; PersonFullNameFL = person.FullNameAndArea; PersonFullName = person.C_FullName; PersonCombinedInfo = person.CombinedInfo; PersonIneligibleReasonGuid = person.IneligibleReasonGuid; PersonCanReceiveVotes = person.CanReceiveVotes.AsBoolean(); PersonGuid = person.PersonGuid; } else { PersonCanReceiveVotes = false; } }
public VoteInfo(Vote vote, Election election, Ballot ballot, Location location, Person person) { VoteId = vote.Id; SingleNameElectionCount = vote.SingleNameElectionCount; PositionOnBallot = vote.PositionOnBallot; PersonCombinedInfoInVote = vote.PersonCombinedInfo; VoteIneligibleReasonGuid = vote.InvalidReasonGuid; VoteStatusCode = vote.StatusCode; //ballot BallotGuid = ballot.BallotGuid; BallotId = ballot.Id; BallotStatusCode = ballot.StatusCode; C_BallotCode = ballot.C_BallotCode; //Location LocationId = location == null ? 0 : location.Id; ElectionGuid = election.ElectionGuid; if (person != null) { AssertAtRuntime.That(person.PersonGuid == vote.PersonGuid); var personCanReceiveVotes = person.CanReceiveVotes.AsBoolean(true); PersonId = person.Id; PersonFullNameFL = person.FullNameAndArea; PersonCombinedInfo = person.CombinedInfo; PersonIneligibleReasonGuid = personCanReceiveVotes ? null : person.IneligibleReasonGuid; PersonCanReceiveVotes = personCanReceiveVotes; PersonGuid = person.PersonGuid; } else { PersonCanReceiveVotes = true; } }
private void AnalyzeTieGroup(ResultTie resultTie, List <Result> results) { AssertAtRuntime.That(results.Count != 0); resultTie.NumInTie = results.Count; resultTie.NumToElect = 0; resultTie.TieBreakRequired = false; var groupInTop = false; var groupInExtra = false; var groupInOther = false; foreach (var result in results) { switch (result.Section) { case ResultHelper.Section.Top: groupInTop = true; break; case ResultHelper.Section.Extra: groupInExtra = true; break; case ResultHelper.Section.Other: groupInOther = true; break; } } var groupOnlyInTop = groupInTop && !(groupInExtra || groupInOther); var groupOnlyInOther = groupInOther && !(groupInTop || groupInExtra); var isResolved = true; results.ForEach(delegate(Result r) { r.TieBreakRequired = !(groupOnlyInOther || groupOnlyInTop); // expressed in the positive for developers! var stillTied = results.Any(other => other != r && other.TieBreakCount.AsInt() == r.TieBreakCount.AsInt() && (other.Section != r.Section || r.Section == ResultHelper.Section.Extra) ); if (stillTied) { isResolved = false; } }); // apply to each result results.ForEach(r => r.IsTieResolved = isResolved); resultTie.IsResolved = isResolved; // if others are involved, set them to show if (groupInOther && (groupInTop || groupInExtra)) { results.Where(r => r.Section == ResultHelper.Section.Other) .ToList() .ForEach(r => r.ForceShowInOther = true); } if (groupInTop) { if (groupOnlyInTop) { // default... tie-break not needed } else { resultTie.NumToElect += results.Count(r => r.Section == ResultHelper.Section.Top); resultTie.TieBreakRequired = true; } } var extrasToBeDistinct = 0; if (groupInExtra) { resultTie.TieBreakRequired = true; extrasToBeDistinct = results.Count(r => r.Section == ResultHelper.Section.Extra) - 1; if (!groupInTop) { resultTie.NumToElect += results.Count(r => r.Section == ResultHelper.Section.Extra); } } //var numResolved = 0; //if (resultTie.NumToElect > 0) //{ // //results are in descending order already, so starting at 0 is starting at the "top" // for (int i = 0, max = results.Count; i < max; i++) // { // var result = results[i]; // if (!result.IsTieResolved.AsBoolean()) break; // numResolved += 1; // } //} //if (numResolved < resultTie.NumToElect + extrasToBeDistinct) //{ // resultTie.IsResolved = false; //} //else //{ // resultTie.IsResolved = true; //} if (resultTie.NumInTie == resultTie.NumToElect) { // need to vote for one less than the number to be elected resultTie.NumToElect--; } if (resultTie.TieBreakRequired.Value) { // required? ensure each has a number results.ForEach(r => { if (r.TieBreakCount == null) { r.TieBreakCount = 0; } }); } else { // not required? remove any counts results.ForEach(r => r.TieBreakCount = null); } // conclusions //resultTie.Comments = resultTie.TieBreakRequired.AsBool() // ? "Tie-break required" // : "Tie-break not needed"; }