Skip to content

Commit 440c01c

Browse files
committed
refactor a little
1 parent 436e3b8 commit 440c01c

File tree

3 files changed

+498
-119
lines changed

3 files changed

+498
-119
lines changed

namer/key.go

Lines changed: 7 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -17,23 +17,22 @@ type Key interface {
1717
Name() string // Get object name.
1818
Type() KeyType // Get key type.
1919
Property() string // Get metadata (e.g., algorithm version).
20-
Raw() []byte // Get raw data.
2120
Build() string // Reconstruct raw key string.
2221
}
2322

2423
// DefaultKey implements default realization.
2524
type DefaultKey struct {
2625
name string // Object identifier.
27-
keytype KeyType // Type of object (hash/signature/value).
26+
keyType KeyType // Type of object (hash/signature/value).
2827
property string // Additional metadata (version/algorithm).
29-
raw []byte // Raw key string.
28+
raw string // Raw key string.
3029
}
3130

3231
// NewDefaultKey returns new Key object.
33-
func NewDefaultKey(name string, keytype KeyType, property string, raw []byte) DefaultKey {
32+
func NewDefaultKey(name string, keytype KeyType, property string, raw string) DefaultKey {
3433
return DefaultKey{
3534
name: name,
36-
keytype: keytype,
35+
keyType: keytype,
3736
property: property,
3837
raw: raw,
3938
}
@@ -46,25 +45,15 @@ func (k DefaultKey) Name() string {
4645

4746
// Type returns type of the key.
4847
func (k DefaultKey) Type() KeyType {
49-
return k.keytype
48+
return k.keyType
5049
}
5150

5251
// Property returns property of the key.
5352
func (k DefaultKey) Property() string {
5453
return k.property
5554
}
5655

57-
// Raw returns raw of the key.
58-
func (k DefaultKey) Raw() []byte {
59-
return k.raw
60-
}
61-
62-
// Build should reconstruct key from signature and digest or not?
56+
// Build reconstructs key string.
6357
func (k DefaultKey) Build() string {
64-
return string(k.raw)
65-
}
66-
67-
// String returns string representation of the `raw` field.
68-
func (k DefaultKey) String() string {
69-
return string(k.raw)
58+
return k.raw
7059
}

namer/namer.go

Lines changed: 145 additions & 77 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,6 @@
22
package namer
33

44
import (
5-
"errors"
65
"fmt"
76
"iter"
87
"strings"
@@ -11,29 +10,66 @@ import (
1110
const (
1211
hashName = "hash"
1312
signatureName = "sig"
14-
keysPerName = 3
1513
)
1614

17-
var (
18-
// ErrInvalidKey is returned when missing key, hash or signature.
19-
ErrInvalidKey = errors.New("missing key, hash or signature")
20-
// ErrInvalidInput is returned when input data is invalid.
21-
ErrInvalidInput = errors.New("failed to generate: invalid input data")
22-
// ErrInvalidPrefix is returned when prefix didn't match.
23-
ErrInvalidPrefix = errors.New("invalid prefix")
24-
)
15+
type InvalidKeyError struct {
16+
Key string
17+
Problem string
18+
}
19+
20+
func (e InvalidKeyError) Error() string {
21+
return fmt.Sprintf("invalid key '%s': %s", e.Key, e.Problem)
22+
}
23+
24+
func errInvalidKey(key string, problem string) error {
25+
return InvalidKeyError{
26+
Key: key,
27+
Problem: problem,
28+
}
29+
}
30+
31+
type InvalidNameError struct {
32+
Name string
33+
Problem string
34+
}
35+
36+
func (e InvalidNameError) Error() string {
37+
return fmt.Sprintf("invalid name '%s': %s", e.Name, e.Problem)
38+
}
39+
40+
func errInvalidName(name string, problem string) error {
41+
return InvalidNameError{
42+
Name: name,
43+
Problem: problem,
44+
}
45+
}
2546

2647
// Results represents Namer working result.
2748
type Results struct {
28-
IsSingle bool // True if result contains only one object name.
29-
IsSingleName string // Cached name when isSingle=true.
30-
Result map[string][]Key // Grouped keys: object name -> key list.
49+
isSingle bool // True if result contains only one object name.
50+
isSingleName string // Cached name when isSingle=true.
51+
result map[string][]Key // Grouped keys: object name -> key list.
52+
}
53+
54+
func getFirstFromMap(m map[string][]Key) string {
55+
for name := range m {
56+
return name
57+
}
58+
return ""
59+
}
60+
61+
func NewResults(initial map[string][]Key) Results {
62+
return Results{
63+
isSingle: len(initial) == 1,
64+
isSingleName: getFirstFromMap(initial),
65+
result: initial,
66+
}
3167
}
3268

3369
// SelectSingle gets keys for single-name case (if applicable).
3470
func (r *Results) SelectSingle() ([]Key, bool) {
35-
if r.IsSingle {
36-
return r.Result[r.IsSingleName], true
71+
if r.isSingle {
72+
return r.result[r.isSingleName], true
3773
}
3874

3975
return nil, false
@@ -42,17 +78,21 @@ func (r *Results) SelectSingle() ([]Key, bool) {
4278
// Items return iterator over all name->keys groups.
4379
func (r *Results) Items() iter.Seq2[string, []Key] {
4480
return func(yield func(str string, res []Key) bool) {
45-
for i, v := range r.Result {
81+
for i, v := range r.result {
4682
if !yield(i, v) {
4783
return
4884
}
4985
}
5086
}
5187
}
5288

89+
func (r *Results) Result() map[string][]Key {
90+
return r.result
91+
}
92+
5393
// Select gets keys for a specific object name.
5494
func (r *Results) Select(name string) ([]Key, bool) {
55-
if i, ok := r.Result[name]; ok {
95+
if i, ok := r.result[name]; ok {
5696
return i, true
5797
}
5898

@@ -61,7 +101,7 @@ func (r *Results) Select(name string) ([]Key, bool) {
61101

62102
// Len returns the number of unique object names.
63103
func (r *Results) Len() int {
64-
return len(r.Result)
104+
return len(r.result)
65105
}
66106

67107
// DefaultNamer represents default namer.
@@ -73,110 +113,138 @@ type DefaultNamer struct {
73113

74114
// NewDefaultNamer returns new DefaultNamer object with hash/signature names configuration.
75115
func NewDefaultNamer(prefix string, hashNames []string, sigNames []string) *DefaultNamer {
76-
prefix = strings.TrimPrefix(prefix, "/")
77-
prefix = strings.TrimSuffix(prefix, "/")
78-
79116
return &DefaultNamer{
80-
prefix: prefix, // "storage/".
81-
hashNames: hashNames, // "sha256".
82-
sigNames: sigNames, // "RSAPSS".
117+
prefix: strings.Trim(prefix, "/"),
118+
hashNames: hashNames,
119+
sigNames: sigNames,
83120
}
84121
}
85122

86123
// GenerateNames all keys for an object name.
87-
func (n *DefaultNamer) GenerateNames(name string) []Key {
124+
func (n *DefaultNamer) GenerateNames(name string) ([]Key, error) {
125+
switch {
126+
case name == "":
127+
return nil, errInvalidName(name, "should not be empty")
128+
case strings.HasSuffix(name, "/"):
129+
return nil, errInvalidName(name, "should not be prefix")
130+
}
131+
88132
name = strings.TrimPrefix(name, "/")
89133

90134
out := make([]Key, 0, len(n.hashNames)+len(n.sigNames)+1)
91135

92136
out = append(out,
93137
NewDefaultKey(
94-
fmt.Sprintf("/%s/%s", n.prefix, name),
138+
name,
95139
KeyTypeValue,
96140
"",
97-
[]byte{},
141+
fmt.Sprintf("/%s/%s", n.prefix, name),
98142
))
99143

100144
for _, hash := range n.hashNames {
101145
out = append(out,
102146
NewDefaultKey(
103-
fmt.Sprintf("/%s/%s/%s/%s", n.prefix, hashName, hash, name),
147+
name,
104148
KeyTypeHash,
105149
hash,
106-
[]byte{},
150+
fmt.Sprintf("/%s/%s/%s/%s", n.prefix, hashName, hash, name),
107151
),
108152
)
109153
}
110154

111155
for _, sig := range n.sigNames {
112156
out = append(out,
113157
NewDefaultKey(
114-
fmt.Sprintf("/%s/%s/%s/%s", n.prefix, signatureName, sig, name),
158+
name,
115159
KeyTypeSignature,
116160
sig,
117-
[]byte{},
161+
fmt.Sprintf("/%s/%s/%s/%s", n.prefix, signatureName, sig, name),
118162
),
119163
)
120164
}
121165

122-
return out
166+
return out, nil
123167
}
124168

125-
// ParseKeys combine multiple raw keys into grouped results.
126-
func (n *DefaultNamer) ParseKeys(names []string) (Results, error) {
127-
var out Results
169+
func (n *DefaultNamer) ParseKey(name string) (DefaultKey, error) {
170+
originalName := name
128171

129-
out.Result = map[string][]Key{}
130-
131-
if len(names) == 0 {
132-
return out, ErrInvalidInput
133-
}
134-
135-
if len(names) == 1 {
136-
out.IsSingle = true
137-
out.IsSingleName = names[0]
172+
name, found := strings.CutPrefix(strings.TrimPrefix(name, "/"), n.prefix)
173+
if !found {
174+
return DefaultKey{}, errInvalidKey(originalName, "prefix not found")
138175
}
139176

140-
for _, name := range names {
141-
originName := name
142-
143-
name = strings.TrimPrefix(name, "/")
144-
145-
name, found := strings.CutPrefix(name, n.prefix)
146-
if !found {
147-
return out, ErrInvalidInput
177+
name = strings.TrimPrefix(name, "/")
178+
nameParts := strings.SplitN(name, "/", 3)
179+
180+
switch {
181+
case len(nameParts) <= 0 || len(nameParts) > 3:
182+
panic("illegal state") // Unreachable.
183+
184+
case nameParts[0] == signatureName:
185+
switch {
186+
case len(nameParts) != 3:
187+
return DefaultKey{}, errInvalidKey(originalName, "found sig prefix, but key name is incomplete")
188+
case len(nameParts[1]) == 0:
189+
return DefaultKey{}, errInvalidKey(originalName, "found sig prefix, but hash name is invalid")
190+
case len(nameParts[2]) == 0:
191+
return DefaultKey{}, errInvalidKey(originalName, "found sig prefix, but key name is invalid")
192+
case strings.HasSuffix(nameParts[2], "/"):
193+
return DefaultKey{}, errInvalidKey(originalName, "found hash prefix, but key name is prefix")
148194
}
149195

150-
name = strings.TrimSuffix(name, "/")
196+
return NewDefaultKey(
197+
nameParts[2],
198+
KeyTypeSignature,
199+
nameParts[1],
200+
originalName,
201+
), nil
202+
case nameParts[0] == hashName:
203+
switch {
204+
case len(nameParts) != 3:
205+
return DefaultKey{}, errInvalidKey(originalName, "found hash prefix, but key name is incomplete")
206+
case len(nameParts[1]) == 0:
207+
return DefaultKey{}, errInvalidKey(originalName, "found hash prefix, but hash name is invalid")
208+
case len(nameParts[2]) == 0:
209+
return DefaultKey{}, errInvalidKey(originalName, "found hash prefix, but key name is invalid")
210+
case strings.HasSuffix(nameParts[2], "/"):
211+
return DefaultKey{}, errInvalidKey(originalName, "found hash prefix, but key name is prefix")
212+
}
151213

152-
parts := strings.Split(name, "/")
153-
partslen := len(parts)
214+
return NewDefaultKey(
215+
nameParts[2],
216+
KeyTypeHash,
217+
nameParts[1],
218+
originalName,
219+
), nil
220+
default:
221+
if strings.HasSuffix(name, "/") {
222+
return DefaultKey{}, errInvalidKey(originalName, "key name should not be prefix")
223+
}
154224

155-
var keyType KeyType
225+
return NewDefaultKey(
226+
name,
227+
KeyTypeValue,
228+
"",
229+
originalName,
230+
), nil
231+
}
232+
}
156233

157-
var keyProp string
234+
// ParseKeys combine multiple raw keys into grouped results.
235+
func (n *DefaultNamer) ParseKeys(names []string, ignoreError bool) (Results, error) {
236+
out := map[string][]Key{}
158237

159-
switch parts[0] {
160-
case hashName:
161-
keyType = KeyTypeHash
162-
keyProp = parts[1]
163-
case signatureName:
164-
keyType = KeyTypeSignature
165-
keyProp = parts[1]
166-
default:
167-
keyType = KeyTypeValue
168-
keyProp = ""
238+
for _, name := range names {
239+
key, err := n.ParseKey(name)
240+
switch {
241+
case err != nil && ignoreError:
242+
continue
243+
case err != nil:
244+
return Results{}, err
169245
}
170-
171-
key := NewDefaultKey(
172-
originName,
173-
keyType,
174-
keyProp,
175-
[]byte{},
176-
)
177-
178-
out.Result[parts[partslen-1]] = append(out.Result[parts[partslen-1]], key)
246+
out[key.name] = append(out[key.name], key)
179247
}
180248

181-
return out, nil
249+
return NewResults(out), nil
182250
}

0 commit comments

Comments
 (0)