-
Notifications
You must be signed in to change notification settings - Fork 2
/
questions.go
95 lines (83 loc) · 2.12 KB
/
questions.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
package domain
import (
"encoding/json"
"strconv"
"github.com/pkg/errors"
)
var ErrQuestionsIndexOutOfRange = errors.New("Index out of range")
var ErrQuestionsNoNext = errors.New("No next question")
var ErrQuestionsIdExists = errors.New("Duplicate question id")
var ErrQuestionsEmpty = errors.New("Cannot do this operation on an empty Questions struct")
// stores a list of Question objects
// not a map because we need to keep the order of the questions
// maps in Go do not keep order
type Questions struct {
text []string
ids []string
weights []int
channel []string
}
func NewQuestions() *Questions {
return &Questions{}
}
func (qs *Questions) MarshalJSON() ([]byte, error) {
q := make(map[string]map[string]string)
for index, id := range qs.ids {
q[id] = map[string]string{
"text": qs.text[index],
"weight": strconv.Itoa(qs.weights[index]),
"channel": qs.channel[index],
}
}
return json.Marshal(q)
}
func (qs *Questions) Add(id, question string, weight int, channel string) error {
for _, existingId := range qs.ids {
if existingId == id {
return ErrQuestionsIdExists
}
}
qs.text = append(qs.text, question)
qs.ids = append(qs.ids, id)
qs.weights = append(qs.weights, weight)
qs.channel = append(qs.channel, channel)
return nil
}
func (qs *Questions) Len() int {
return len(qs.ids)
}
func (qs *Questions) At(index int) (q *Question, err error) {
if index >= len(qs.ids) {
return q, ErrQuestionsIndexOutOfRange
}
return &Question{
Id: qs.ids[index],
Text: qs.text[index],
Weight: qs.weights[index],
Channel: qs.channel[index],
}, nil
}
func (qs *Questions) Next(qid string) (q *Question, err error) {
returnNext := false
for index, id := range qs.ids {
if returnNext {
return qs.At(index)
}
if id == qid {
returnNext = true
continue
}
}
return q, ErrQuestionsNoNext
}
func (qs *Questions) Last() (q *Question, err error) {
if len(qs.ids) == 0 {
return q, ErrQuestionsEmpty
}
return &Question{
Id: qs.ids[len(qs.ids)-1],
Text: qs.text[len(qs.text)-1],
Weight: qs.weights[len(qs.weights)-1],
Channel: qs.channel[len(qs.channel)-1],
}, nil
}