tags.go

v0.1.0
Doc Versions Source
1
package steward
2
3
import (
4
	"strconv"
5
)
6
7
type structTag string
8
9
func (tag structTag) Parse() map[string]string {
10
	out := make(map[string]string)
11
12
	for tag != "" {
13
		// Skip leading space.
14
		i := 0
15
		for i < len(tag) && tag[i] == ' ' {
16
			i++
17
		}
18
		tag = tag[i:]
19
		if tag == "" {
20
			break
21
		}
22
23
		// Scan to colon. A space, a quote or a control character is a syntax error.
24
		// Strictly speaking, control chars include the range [0x7f, 0x9f], not just
25
		// [0x00, 0x1f], but in practice, we ignore the multi-byte control characters
26
		// as it is simpler to inspect the tag's bytes than the tag's runes.
27
		i = 0
28
		for i < len(tag) && tag[i] > ' ' && tag[i] != ':' && tag[i] != '"' && tag[i] != 0x7f {
29
			i++
30
		}
31
		if i == 0 || i+1 >= len(tag) || tag[i] != ':' || tag[i+1] != '"' {
32
			break
33
		}
34
		name := string(tag[:i])
35
		tag = tag[i+1:]
36
37
		// Scan quoted string to find value.
38
		i = 1
39
		for i < len(tag) && tag[i] != '"' {
40
			if tag[i] == '\\' {
41
				i++
42
			}
43
			i++
44
		}
45
		if i >= len(tag) {
46
			break
47
		}
48
		qvalue := string(tag[:i+1])
49
		tag = tag[i+1:]
50
51
		value, err := strconv.Unquote(qvalue)
52
		if err != nil {
53
			break
54
		}
55
		out[name] = value
56
	}
57
58
	return out
59
}
60

Source Files