summaryrefslogtreecommitdiffstats
path: root/vendor/github.com/wiggin77/cfg/ini/section.go
blob: 18c4c254039d4750c8b96b623aad31f14d77a1ae (plain) (blame)
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
package ini

import (
	"fmt"
	"strings"
	"sync"
)

// Section represents a section in an INI file. The section has a name, which is
// enclosed in square brackets in the file. The section also has an array of
// key/value pairs.
type Section struct {
	name  string
	props map[string]string
	mtx   sync.RWMutex
}

func newSection(name string) *Section {
	sec := &Section{}
	sec.name = name
	sec.props = make(map[string]string)
	return sec
}

// addLines addes an array of strings containing name/value pairs
// of the format `key=value`.
//func addLines(lines []string) {
// TODO
//}

// GetName returns the name of the section.
func (sec *Section) GetName() (name string) {
	sec.mtx.RLock()
	name = sec.name
	sec.mtx.RUnlock()
	return
}

// GetProp returns the value associated with the given key, or
// `ok=false` if key does not exist.
func (sec *Section) GetProp(key string) (val string, ok bool) {
	sec.mtx.RLock()
	val, ok = sec.props[key]
	sec.mtx.RUnlock()
	return
}

// SetProp sets the value associated with the given key.
func (sec *Section) setProp(key string, val string) {
	sec.mtx.Lock()
	sec.props[key] = val
	sec.mtx.Unlock()
}

// hasKeys returns true if there are one or more properties in
// this section.
func (sec *Section) hasKeys() (b bool) {
	sec.mtx.RLock()
	b = len(sec.props) > 0
	sec.mtx.RUnlock()
	return
}

// getKeys returns an array containing all keys in this section.
func (sec *Section) getKeys() []string {
	sec.mtx.RLock()
	defer sec.mtx.RUnlock()

	arr := make([]string, len(sec.props))
	idx := 0
	for k := range sec.props {
		arr[idx] = k
		idx++
	}
	return arr
}

// combine the given section with this one.
func (sec *Section) combine(sec2 *Section) {
	sec.mtx.Lock()
	sec2.mtx.RLock()
	defer sec.mtx.Unlock()
	defer sec2.mtx.RUnlock()

	for k, v := range sec2.props {
		sec.props[k] = v
	}
}

// String returns a string representation of this section.
func (sec *Section) String() string {
	return fmt.Sprintf("[%s]\n%s", sec.GetName(), sec.StringPropsOnly())
}

// StringPropsOnly returns a string representation of this section
// without the section header.
func (sec *Section) StringPropsOnly() string {
	sec.mtx.RLock()
	defer sec.mtx.RUnlock()
	sb := &strings.Builder{}

	for k, v := range sec.props {
		sb.WriteString(k)
		sb.WriteString("=")
		sb.WriteString(v)
		sb.WriteString("\n")
	}
	return sb.String()
}