/
configuration.go
121 lines (103 loc) · 2.38 KB
/
configuration.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
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
package config
import (
"bytes"
"compress/gzip"
"context"
"fmt"
"io"
"github.com/kong/koko/internal/json"
)
type Map map[string]interface{}
type Content struct {
CompressedPayload []byte
Hash string
GranularHashes map[string]string
}
type MutatorOpts struct {
ClusterID string
}
type Mutator interface {
Name() string
Mutate(context.Context, MutatorOpts, DataPlaneConfig) error
}
type Loader interface {
Load(ctx context.Context, clusterID string) (Content, error)
}
type DataPlaneConfig Map
type KongConfigurationLoader struct {
mutators []Mutator
}
func (l *KongConfigurationLoader) Register(mutator Mutator) error {
for _, m := range l.mutators {
if m.Name() == mutator.Name() {
return fmt.Errorf("mutator '%v' already registered", m.Name())
}
}
l.mutators = append(l.mutators, mutator)
return nil
}
func (l *KongConfigurationLoader) Load(ctx context.Context, clusterID string) (Content, error) {
var configTable DataPlaneConfig = map[string]interface{}{}
for _, m := range l.mutators {
err := m.Mutate(ctx, MutatorOpts{ClusterID: clusterID},
configTable)
if err != nil {
return Content{}, err
}
}
return ReconfigurePayload(configTable)
}
func ReconfigurePayload(c DataPlaneConfig) (Content, error) {
configHash, hashes := getGranularHashes(c)
payload := Map{
"type": "reconfigure",
"config_table": c,
"config_hash": configHash,
"hashes": hashes,
}
var buf bytes.Buffer
writer := gzip.NewWriter(&buf)
defer writer.Close()
err := json.Marshaller.NewEncoder(writer).Encode(payload)
if err != nil {
return Content{}, fmt.Errorf("json marshal: %v", err)
}
err = writer.Close()
if err != nil {
return Content{}, fmt.Errorf("gzip failure: %v", err)
}
return Content{
CompressedPayload: buf.Bytes(),
Hash: configHash,
GranularHashes: hashes,
}, nil
}
func CompressPayload(payload []byte) ([]byte, error) {
var buf bytes.Buffer
w := gzip.NewWriter(&buf)
_, err := w.Write(payload)
if err != nil {
return nil, err
}
err = w.Close()
if err != nil {
return nil, err
}
return buf.Bytes(), nil
}
func UncompressPayload(payload []byte) ([]byte, error) {
r, err := gzip.NewReader(bytes.NewBuffer(payload))
if err != nil {
return nil, err
}
buf, err := io.ReadAll(r)
if err != nil {
_ = r.Close()
return nil, err
}
err = r.Close()
if err != nil {
return nil, err
}
return buf, nil
}