1package random_bugs
2
3import (
4 "math/rand"
5 "strings"
6 "time"
7
8 "github.com/MichaelMure/git-bug/bug"
9 "github.com/MichaelMure/git-bug/operations"
10 "github.com/MichaelMure/git-bug/repository"
11 "github.com/icrowley/fake"
12)
13
14type opsGenerator func(bug.Interface, bug.Person)
15
16type Options struct {
17 BugNumber int
18 PersonNumber int
19 MinOp int
20 MaxOp int
21}
22
23func DefaultOptions() Options {
24 return Options{
25 BugNumber: 15,
26 PersonNumber: 5,
27 MinOp: 3,
28 MaxOp: 20,
29 }
30}
31
32func CommitRandomBugs(repo repository.Repo, opts Options) {
33 CommitRandomBugsWithSeed(repo, opts, time.Now().UnixNano())
34}
35
36func CommitRandomBugsWithSeed(repo repository.Repo, opts Options, seed int64) {
37 bugs := GenerateRandomBugsWithSeed(opts, seed)
38
39 for _, b := range bugs {
40 err := b.Commit(repo)
41 if err != nil {
42 panic(err)
43 }
44 }
45}
46
47func GenerateRandomBugs(opts Options) []*bug.Bug {
48 return GenerateRandomBugsWithSeed(opts, time.Now().UnixNano())
49}
50
51func GenerateRandomBugsWithSeed(opts Options, seed int64) []*bug.Bug {
52 rand.Seed(seed)
53 fake.Seed(seed)
54
55 opsGenerators := []opsGenerator{
56 comment,
57 comment,
58 title,
59 labels,
60 operations.Open,
61 operations.Close,
62 }
63
64 result := make([]*bug.Bug, opts.BugNumber)
65
66 for i := 0; i < opts.BugNumber; i++ {
67 addedLabels = []string{}
68
69 b, err := operations.Create(randomPerson(opts.PersonNumber), fake.Sentence(), paragraphs())
70
71 if err != nil {
72 panic(err)
73 }
74
75 nOps := opts.MinOp
76
77 if opts.MaxOp > opts.MinOp {
78 nOps += rand.Intn(opts.MaxOp - opts.MinOp)
79 }
80
81 for j := 0; j < nOps; j++ {
82 index := rand.Intn(len(opsGenerators))
83 opsGenerators[index](b, randomPerson(opts.PersonNumber))
84 }
85
86 result[i] = b
87 }
88
89 return result
90}
91
92func GenerateRandomOperationPacks(packNumber int, opNumber int) []*bug.OperationPack {
93 return GenerateRandomOperationPacksWithSeed(packNumber, opNumber, time.Now().UnixNano())
94}
95
96func GenerateRandomOperationPacksWithSeed(packNumber int, opNumber int, seed int64) []*bug.OperationPack {
97 // Note: this is a bit crude, only generate a Create + Comments
98
99 rand.Seed(seed)
100 fake.Seed(seed)
101
102 result := make([]*bug.OperationPack, packNumber)
103
104 for i := 0; i < packNumber; i++ {
105 opp := &bug.OperationPack{}
106
107 var op bug.Operation
108
109 op = operations.NewCreateOp(randomPerson(5), fake.Sentence(), paragraphs(), nil)
110
111 opp.Append(op)
112
113 for j := 0; j < opNumber-1; j++ {
114 op = operations.NewAddCommentOp(randomPerson(5), paragraphs(), nil)
115 opp.Append(op)
116 }
117
118 result[i] = opp
119 }
120
121 return result
122}
123
124func person() bug.Person {
125 return bug.Person{
126 Name: fake.FullName(),
127 Email: fake.EmailAddress(),
128 }
129}
130
131var persons []bug.Person
132
133func randomPerson(personNumber int) bug.Person {
134 if len(persons) == 0 {
135 persons = make([]bug.Person, personNumber)
136 for i := range persons {
137 persons[i] = person()
138 }
139 }
140
141 index := rand.Intn(personNumber)
142 return persons[index]
143}
144
145func paragraphs() string {
146 p := fake.Paragraphs()
147 return strings.Replace(p, "\t", "\n\n", -1)
148}
149
150func comment(b bug.Interface, p bug.Person) {
151 operations.Comment(b, p, paragraphs())
152}
153
154func title(b bug.Interface, p bug.Person) {
155 operations.SetTitle(b, p, fake.Sentence())
156}
157
158var addedLabels []string
159
160func labels(b bug.Interface, p bug.Person) {
161 var removed []string
162 nbRemoved := rand.Intn(3)
163 for nbRemoved > 0 && len(addedLabels) > 0 {
164 index := rand.Intn(len(addedLabels))
165 removed = append(removed, addedLabels[index])
166 addedLabels[index] = addedLabels[len(addedLabels)-1]
167 addedLabels = addedLabels[:len(addedLabels)-1]
168 }
169
170 var added []string
171 nbAdded := rand.Intn(3)
172 for i := 0; i < nbAdded; i++ {
173 label := fake.Word()
174 added = append(added, label)
175 addedLabels = append(addedLabels, label)
176 }
177
178 operations.ChangeLabels(nil, b, p, added, removed)
179}