/
facade.go
130 lines (109 loc) · 2.76 KB
/
facade.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
122
123
124
125
126
127
128
129
130
package chunkenc
import (
"io"
"time"
"github.com/prometheus/common/model"
"github.com/grafana/loki/v3/pkg/storage/chunk"
"github.com/grafana/loki/v3/pkg/util/filter"
)
// GzipLogChunk is a cortex encoding type for our chunks.
// Deprecated: the chunk encoding/compression format is inside the chunk data.
const GzipLogChunk = chunk.Encoding(128)
// LogChunk is a cortex encoding type for our chunks.
const LogChunk = chunk.Encoding(129)
func init() {
chunk.MustRegisterEncoding(GzipLogChunk, "GzipLogChunk", func() chunk.Data {
return &Facade{}
})
chunk.MustRegisterEncoding(LogChunk, "LogChunk", func() chunk.Data {
return &Facade{}
})
}
// Facade for compatibility with cortex chunk type, so we can use its chunk store.
type Facade struct {
c Chunk
blockSize int
targetSize int
chunk.Data
}
// NewFacade makes a new Facade.
func NewFacade(c Chunk, blockSize, targetSize int) chunk.Data {
return &Facade{
c: c,
blockSize: blockSize,
targetSize: targetSize,
}
}
func (f Facade) Bounds() (time.Time, time.Time) {
return f.c.Bounds()
}
// Marshal implements chunk.Chunk.
func (f Facade) Marshal(w io.Writer) error {
if f.c == nil {
return nil
}
if _, err := f.c.WriteTo(w); err != nil {
return err
}
return nil
}
// UnmarshalFromBuf implements chunk.Chunk.
func (f *Facade) UnmarshalFromBuf(buf []byte) error {
var err error
f.c, err = NewByteChunk(buf, f.blockSize, f.targetSize)
return err
}
// Encoding implements chunk.Chunk.
func (Facade) Encoding() chunk.Encoding {
return LogChunk
}
// Utilization implements encoding.Chunk.
func (f Facade) Utilization() float64 {
if f.c == nil {
return 0
}
return f.c.Utilization()
}
// Size implements encoding.Chunk, which unfortunately uses
// the Size method to refer to the byte size and not the entry count
// like chunkenc.Chunk does.
func (f Facade) Size() int {
if f.c == nil {
return 0
}
// Note this is an estimation (which is OK)
return f.c.CompressedSize()
}
func (f Facade) UncompressedSize() int {
if f.c == nil {
return 0
}
return f.c.UncompressedSize()
}
func (f Facade) Entries() int {
if f.c == nil {
return 0
}
return f.c.Size()
}
// LokiChunk returns the chunkenc.Chunk.
func (f Facade) LokiChunk() Chunk {
return f.c
}
func (f Facade) Rebound(start, end model.Time, filter filter.Func) (chunk.Data, error) {
newChunk, err := f.c.Rebound(start.Time(), end.Time(), filter)
if err != nil {
return nil, err
}
return &Facade{
c: newChunk,
}, nil
}
// UncompressedSize is a helper function to hide the type assertion kludge when wanting the uncompressed size of the Cortex interface encoding.Chunk.
func UncompressedSize(c chunk.Data) (int, bool) {
f, ok := c.(*Facade)
if !ok || f.c == nil {
return 0, false
}
return f.c.UncompressedSize(), true
}