Skip to content

Commit a735d23

Browse files
refactor vote calculation logic into module
1 parent 68252f5 commit a735d23

File tree

2 files changed

+31
-29
lines changed

2 files changed

+31
-29
lines changed

lib/pointing_party/vote_calculator.ex

Lines changed: 29 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,29 @@
1+
defmodule PointingParty.VoteCalculator do
2+
defp winning_vote(users) do
3+
votes = Enum.map(users, fn {_username, %{metas: [%{points: points}]}} -> points end)
4+
calculated_votes = Enum.reduce(votes, %{}, fn vote, acc ->
5+
acc
6+
|> Map.get_and_update(vote, &({&1, (&1 || 0) + 1}))
7+
|> elem(1)
8+
end)
9+
10+
total_votes = length(votes)
11+
12+
majority = Enum.reduce_while(calculated_votes, nil, fn {point, vote_count}, _acc ->
13+
if vote_count == total_votes or rem(vote_count, total_votes) > 5 do
14+
{:halt, point}
15+
else
16+
{:cont, nil}
17+
end
18+
end)
19+
20+
if is_nil(majority) do
21+
calculated_votes
22+
|> Enum.sort_by(&elem(&1, 1))
23+
|> Enum.take(2)
24+
|> Enum.map(&elem(&1, 0))
25+
else
26+
majority
27+
end
28+
end
29+
end

lib/pointing_party_web/channels/room_channel.ex

Lines changed: 2 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@ defmodule PointingPartyWeb.RoomChannel do
33

44
alias PointingParty.Card
55
alias PointingPartyWeb.Presence
6+
alias PointingParty.VoteCalculator
67

78
def join("room:lobby", _payload, socket) do
89
send(self(), :after_join)
@@ -57,7 +58,7 @@ defmodule PointingPartyWeb.RoomChannel do
5758
current_users = Presence.list(socket)
5859

5960
{event, points} =
60-
case winning_vote(current_users) do
61+
case VoteCalculator.winning_vote(current_users) do
6162
top_two when is_list(top_two) -> {"tie", top_two}
6263
winner -> {"winner", winner}
6364
end
@@ -91,32 +92,4 @@ defmodule PointingPartyWeb.RoomChannel do
9192
|> assign(:current, next)
9293
|> assign(:voted, [latest_card | socket.assigns[:voted]])
9394
end
94-
95-
defp winning_vote(users) do
96-
votes = Enum.map(users, fn {_username, %{metas: [%{points: points}]}} -> points end)
97-
calculated_votes = Enum.reduce(votes, %{}, fn vote, acc ->
98-
acc
99-
|> Map.get_and_update(vote, &({&1, (&1 || 0) + 1}))
100-
|> elem(1)
101-
end)
102-
103-
total_votes = length(votes)
104-
105-
majority = Enum.reduce_while(calculated_votes, nil, fn {point, vote_count}, _acc ->
106-
if vote_count == total_votes or rem(vote_count, total_votes) > 5 do
107-
{:halt, point}
108-
else
109-
{:cont, nil}
110-
end
111-
end)
112-
113-
if is_nil(majority) do
114-
calculated_votes
115-
|> Enum.sort_by(&elem(&1, 1))
116-
|> Enum.take(2)
117-
|> Enum.map(&elem(&1, 0))
118-
else
119-
majority
120-
end
121-
end
12295
end

0 commit comments

Comments
 (0)