Add structured validation diagnostics, JSON and Yams comparison gates, and lazy token/event parsing so production behavior is measured without retaining full intermediate parser arrays.
164 lines
7.1 KiB
Swift
164 lines
7.1 KiB
Swift
public extension PureYAML.Parsing {
|
|
/// Parser error with source line information when available.
|
|
enum ParseError: Swift.Error, Equatable, Sendable, CustomStringConvertible {
|
|
case emptyDocument
|
|
case tabIndentation(line: Int)
|
|
case unexpectedIndentation(line: Int)
|
|
case mixedCollectionStyles(line: Int)
|
|
case expectedMappingKey(line: Int)
|
|
case expectedAnchorName(line: Int)
|
|
case expectedAliasName(line: Int)
|
|
case expectedNode(line: Int, column: Int)
|
|
case expectedScalarKey(line: Int, column: Int)
|
|
case incompatibleYAMLDirective(line: Int)
|
|
case invalidTaggedScalar(tag: String, value: String, line: Int, column: Int)
|
|
case invalidMergeValue(line: Int, column: Int)
|
|
case unterminatedTag(line: Int)
|
|
case unterminatedQuotedString(line: Int)
|
|
case unsupportedDirective(name: String, line: Int)
|
|
case unsupportedMultiDocumentStream(line: Int)
|
|
case undefinedAlias(anchor: String, line: Int, column: Int)
|
|
case unexpectedEvent(expected: String, actual: String, line: Int, column: Int)
|
|
case unexpectedToken(expected: String, actual: String, line: Int, column: Int)
|
|
|
|
public var description: String {
|
|
switch self {
|
|
case .emptyDocument:
|
|
"document is empty"
|
|
case let .tabIndentation(line):
|
|
"tabs are not allowed for indentation at line \(line)"
|
|
case let .unexpectedIndentation(line):
|
|
"unexpected indentation at line \(line)"
|
|
case let .mixedCollectionStyles(line):
|
|
"mapping and sequence entries are mixed at line \(line)"
|
|
case let .expectedMappingKey(line):
|
|
"expected a mapping key at line \(line)"
|
|
case let .expectedAnchorName(line):
|
|
"expected an anchor name at line \(line)"
|
|
case let .expectedAliasName(line):
|
|
"expected an alias name at line \(line)"
|
|
case let .expectedNode(line, column):
|
|
"expected a YAML node at line \(line), column \(column)"
|
|
case let .expectedScalarKey(line, column):
|
|
"expected a scalar mapping key at line \(line), column \(column)"
|
|
case let .incompatibleYAMLDirective(line):
|
|
"incompatible YAML directive at line \(line)"
|
|
case let .invalidTaggedScalar(tag, value, line, column):
|
|
"invalid scalar '\(value)' for tag '\(tag)' at line \(line), column \(column)"
|
|
case let .invalidMergeValue(line, column):
|
|
"expected merge value to be a mapping or sequence of mappings at line \(line), column \(column)"
|
|
case let .unterminatedTag(line):
|
|
"unterminated tag at line \(line)"
|
|
case let .unterminatedQuotedString(line):
|
|
"unterminated quoted string at line \(line)"
|
|
case let .unsupportedDirective(name, line):
|
|
"unsupported directive '\(name)' at line \(line)"
|
|
case let .unsupportedMultiDocumentStream(line):
|
|
"multi-document streams are not supported at line \(line)"
|
|
case let .undefinedAlias(anchor, line, column):
|
|
"undefined alias '\(anchor)' at line \(line), column \(column)"
|
|
case let .unexpectedEvent(expected, actual, line, column):
|
|
"expected \(expected) at line \(line), column \(column), found \(actual)"
|
|
case let .unexpectedToken(expected, actual, line, column):
|
|
"expected \(expected) at line \(line), column \(column), found \(actual)"
|
|
}
|
|
}
|
|
|
|
public var diagnosticCode: String {
|
|
switch self {
|
|
case .emptyDocument:
|
|
"emptyDocument"
|
|
case .tabIndentation:
|
|
"tabIndentation"
|
|
case .unexpectedIndentation:
|
|
"unexpectedIndentation"
|
|
case .mixedCollectionStyles:
|
|
"mixedCollectionStyles"
|
|
case .expectedMappingKey:
|
|
"expectedMappingKey"
|
|
case .expectedAnchorName:
|
|
"expectedAnchorName"
|
|
case .expectedAliasName:
|
|
"expectedAliasName"
|
|
case .expectedNode:
|
|
"expectedNode"
|
|
case .expectedScalarKey:
|
|
"expectedScalarKey"
|
|
case .incompatibleYAMLDirective:
|
|
"incompatibleYAMLDirective"
|
|
case .invalidTaggedScalar:
|
|
"invalidTaggedScalar"
|
|
case .invalidMergeValue:
|
|
"invalidMergeValue"
|
|
case .unterminatedTag:
|
|
"unterminatedTag"
|
|
case .unterminatedQuotedString:
|
|
"unterminatedQuotedString"
|
|
case .unsupportedDirective:
|
|
"unsupportedDirective"
|
|
case .unsupportedMultiDocumentStream:
|
|
"unsupportedMultiDocumentStream"
|
|
case .undefinedAlias:
|
|
"undefinedAlias"
|
|
case .unexpectedEvent:
|
|
"unexpectedEvent"
|
|
case .unexpectedToken:
|
|
"unexpectedToken"
|
|
}
|
|
}
|
|
|
|
public var sourceLine: Int? {
|
|
switch self {
|
|
case .emptyDocument:
|
|
nil
|
|
case let .tabIndentation(line),
|
|
let .unexpectedIndentation(line),
|
|
let .mixedCollectionStyles(line),
|
|
let .expectedMappingKey(line),
|
|
let .expectedAnchorName(line),
|
|
let .expectedAliasName(line),
|
|
let .incompatibleYAMLDirective(line),
|
|
let .unterminatedTag(line),
|
|
let .unterminatedQuotedString(line),
|
|
let .unsupportedDirective(_, line),
|
|
let .unsupportedMultiDocumentStream(line):
|
|
line
|
|
case let .expectedNode(line, _),
|
|
let .expectedScalarKey(line, _),
|
|
let .invalidTaggedScalar(_, _, line, _),
|
|
let .invalidMergeValue(line, _),
|
|
let .undefinedAlias(_, line, _),
|
|
let .unexpectedEvent(_, _, line, _),
|
|
let .unexpectedToken(_, _, line, _):
|
|
line
|
|
}
|
|
}
|
|
|
|
public var sourceColumn: Int? {
|
|
switch self {
|
|
case .emptyDocument,
|
|
.tabIndentation,
|
|
.unexpectedIndentation,
|
|
.mixedCollectionStyles,
|
|
.expectedMappingKey,
|
|
.expectedAnchorName,
|
|
.expectedAliasName,
|
|
.incompatibleYAMLDirective,
|
|
.unterminatedTag,
|
|
.unterminatedQuotedString,
|
|
.unsupportedDirective,
|
|
.unsupportedMultiDocumentStream:
|
|
nil
|
|
case let .expectedNode(_, column),
|
|
let .expectedScalarKey(_, column),
|
|
let .invalidTaggedScalar(_, _, _, column),
|
|
let .invalidMergeValue(_, column),
|
|
let .undefinedAlias(_, _, column),
|
|
let .unexpectedEvent(_, _, _, column),
|
|
let .unexpectedToken(_, _, _, column):
|
|
column
|
|
}
|
|
}
|
|
}
|
|
}
|