Files: ebad2e906b7c5bfaaf2ef70e09eb2ed8b39f698d / results / sync / buildResults.js
1909 bytesRaw
1 | const getMsgContent = require('../../lib/getMsgContent') |
2 | const PositionChoiceError = require('../../errors/sync/positionChoiceError') |
3 | const PositionLateError = require('../../errors/sync/positionLateError') |
4 | const { isChooseOnePoll } = require('ssb-poll-schema') |
5 | |
6 | // Expects `poll` and `position` objects passed in to be of shape: |
7 | // { |
8 | // key, |
9 | // value: { |
10 | // content: {...}, |
11 | // timestamp: ... |
12 | // author: ... |
13 | // } |
14 | // } |
15 | // |
16 | // postions must be of the correct type ie: type checked by the caller. |
17 | module.exports = function ({positions, poll}) { |
18 | if (isChooseOnePoll(poll)) { |
19 | return chooseOneResults({positions, poll}) |
20 | } |
21 | } |
22 | |
23 | function chooseOneResults ({positions, poll}) { |
24 | var results = getMsgContent(poll) |
25 | .details |
26 | .choices |
27 | .map(choice => { |
28 | return { |
29 | choice, |
30 | voters: {} |
31 | } |
32 | }) |
33 | |
34 | return positions.reduce(function (acc, position) { |
35 | const { author, content } = position.value |
36 | const { choice } = content.details |
37 | |
38 | if (isInvalidChoice({position, poll})) { |
39 | acc.errors.push(PositionChoiceError({position})) |
40 | return acc |
41 | } |
42 | |
43 | if (isPositionLate({position, poll})) { |
44 | acc.errors.push(PositionLateError({position})) |
45 | return acc |
46 | } |
47 | |
48 | deleteExistingVotesByAuthor({results: acc.results, author}) |
49 | acc.results[choice].voters[author] = position |
50 | |
51 | return acc |
52 | }, {errors: [], results}) |
53 | } |
54 | |
55 | // !!! assumes these are already sorted by time. |
56 | // modifies results passed in |
57 | function deleteExistingVotesByAuthor ({author, results}) { |
58 | results.forEach(result => { |
59 | if (result.voters[author]) { |
60 | delete result.voters[author] |
61 | } |
62 | }) |
63 | } |
64 | |
65 | function isInvalidChoice ({position, poll}) { |
66 | const { choice } = position.value.content.details |
67 | return choice >= poll.value.content.details.choices.length |
68 | } |
69 | |
70 | function isPositionLate ({position, poll}) { |
71 | return position.value.timestamp > poll.value.content.closesAt |
72 | } |
73 |
Built with git-ssb-web