An alias may stand where a mapping key is expected (`*a : value`). The scanner emits the implicit-key indicator before a scalar key that a `:` follows, but not before an alias, so the parser, which already accepts an alias node in key position, never entered the pair and rejected the alias as an unexpected token. The scanner now emits the same indicator before an alias that a `:` (after optional spaces) follows, in block context. A `:` written directly against the alias stays part of its name, since `:` is a valid anchor-name character, so only a space-separated `:` marks the alias as a key. Fixes yaml-test-suite E76Z and 26DV; raises parse-level conformance to 310/333 (93.1%) and value-level to 203/203 (100.0%), with the should-error rate unchanged.
35 lines
1.8 KiB
Swift
35 lines
1.8 KiB
Swift
@testable import PureYAML
|
|
import Testing
|
|
|
|
@Suite("An alias node can serve as an implicit mapping key")
|
|
struct AliasAsMappingKeyTests {
|
|
/// yaml-test-suite E76Z: an alias may stand where a mapping key is expected (`*b : value`). The
|
|
/// scanner now emits the implicit-key indicator before an alias followed by a `:`, exactly as it
|
|
/// does for a scalar key, and the alias resolves to the anchored node's value.
|
|
@Test("An alias followed by a value indicator is a mapping key")
|
|
func test_aliasIsImplicitKey() throws {
|
|
let mapping = try requireMapping(PureYAML.parse("&a a: &b b\n*b : *a\n"))
|
|
#expect(mapping?["a"] == .string("b"))
|
|
#expect(mapping?["b"] == .string("a"))
|
|
}
|
|
|
|
/// yaml-test-suite 26DV exercises an alias key nested inside a block-mapping value, where the
|
|
/// alias resolves to an earlier anchored scalar and becomes that nested mapping's key.
|
|
@Test("An alias key resolves inside a nested block mapping value")
|
|
func test_aliasKeyInNestedMapping() throws {
|
|
let root = try requireMapping(PureYAML.parse("top1: &x scalar1\ntop3:\n *x : scalar3\n"))
|
|
#expect(root?["top1"] == .string("scalar1"))
|
|
let nested = try requireMapping(#require(root?["top3"]))
|
|
#expect(nested?["scalar1"] == .string("scalar3"))
|
|
}
|
|
|
|
/// A `:` written directly against an alias with no separating space is part of the alias name,
|
|
/// not a value indicator (`:` is a valid anchor-name character), so the alias is not a key here.
|
|
@Test("An alias with an adjacent colon keeps the colon in its name")
|
|
func test_adjacentColonStaysInName() throws {
|
|
let mapping = try requireMapping(PureYAML.parse("key: &a: scalar\nref: *a:\n"))
|
|
#expect(mapping?["key"] == .string("scalar"))
|
|
#expect(mapping?["ref"] == .string("scalar"))
|
|
}
|
|
}
|