go-toml/parser/syn_key.go

66 lines
1.9 KiB
Go

package parser
import "github.com/mmakaay/toml/parsekit"
// The primary building block of a TOML document is the key/value pair.
func startKeyValuePair(p *parsekit.P) {
switch {
case p.On(whitespace + carriageReturn + newline).Skip():
p.Repeat()
case p.On(hash).Stay():
p.RouteTo(startComment).ThenReturnHere()
case p.On(startOfKey).RouteTo(startKey):
default:
p.RouteTo(endOfFile)
}
}
// A key may be either bare, quoted or dotted.
func startKey(p *parsekit.P) {
switch {
case p.On(bareKeyChars).RouteTo(startBareKey):
default:
p.UnexpectedInput("a valid key name")
}
}
// Bare keys may only contain ASCII letters, ASCII digits,
// underscores, and dashes (A-Za-z0-9_-). Note that bare
// keys are allowed to be composed of only ASCII digits,
// e.g. 1234, but are always interpreted as strings.
func startBareKey(p *parsekit.P) {
p.AcceptConsecutive(bareKeyChars) // TODO make a plan for adding this to After()
p.EmitLiteral(ItemKey)
p.RouteTo(endOfKeyOrDot)
}
// Dotted keys are a sequence of bare or quoted keys joined with a dot.
// This allows for grouping similar properties together:
func endOfKeyOrDot(p *parsekit.P) {
// Whitespace around dot-separated parts is ignored, however,
// best practice is to not use any extraneous whitespace.
p.SkipConsecutive(whitespace)
if p.On(dot).Accept() {
p.SkipConsecutive(whitespace)
p.EmitLiteral(ItemKeyDot)
p.RouteTo(startKey)
} else {
p.RouteTo(startKeyAssignment)
}
}
// Keys are on the left of the equals sign and values are on the right.
// Whitespace is ignored around key names and values. The key, equals
// sign, and value must be on the same line (though some values can
// be broken over multiple lines).
func startKeyAssignment(p *parsekit.P) {
p.SkipConsecutive(whitespace)
if p.On(equal).Accept() {
p.EmitLiteral(ItemAssignment)
p.SkipConsecutive(whitespace)
p.RouteTo(startValue)
} else {
p.UnexpectedInput("a value assignment")
}
}