import Testing @testable import PureXML @Suite("Schema structural derivation validity") struct SchemaStructureDerivationTests { private func compile(_ body: String) throws { _ = try PureXML.Schema.Document(""" \(body) """) } private func rejects(_ body: String) -> Bool { do { try compile(body) return false } catch { return true } } @Test("a complexContent derivation's content must be ordered: model group, attributes, anyAttribute") func test_complexContentDerivationOrder() { func derive(_ kind: String, _ body: String) -> String { #""" \#(body) """# } // Two model groups (ctG/ctH "X then Y"). #expect(rejects(derive("restriction", #""#))) #expect(rejects(derive("extension", #""#))) // A model group after an attribute. #expect(rejects(derive("restriction", #""#))) // An attribute after anyAttribute, and two anyAttributes. #expect(rejects(derive("extension", #""#))) #expect(rejects(derive("restriction", #""#))) } @Test("a well-ordered complexContent derivation compiles") func test_complexContentDerivationValid() throws { try compile(#""" """#) // No model group is fine (an extension that only adds attributes). try compile(#""" """#) } @Test("a complexType's shorthand content must be ordered: model group, attributes, anyAttribute") func test_complexTypeShorthandOrder() { // A model group after an attribute, two anyAttributes, an attribute after anyAttribute (ctB). #expect(rejects(#""#)) #expect(rejects(#""#)) #expect(rejects(#""#)) // A well-ordered shorthand complexType compiles. #expect(!rejects(#""" """#)) } @Test("a simpleType must contain exactly one of restriction, list, or union") func test_simpleTypeContent() { // Two derivations, or a mix, is invalid (stB). #expect(rejects(#""#)) #expect(rejects(#""#)) #expect(rejects(#""#)) // Exactly one compiles. #expect(!rejects(#""#)) #expect(!rejects(#""#)) } @Test("documentation xml:lang and xml:space validation") func test_documentationXmlAttributes() throws { // Valid xml:lang and xml:space try compile(#""" Valid documentation """#) // Invalid xml:lang (empty) #expect(rejects(#""" Invalid documentation """#)) // Invalid xml:lang (whitespace only) #expect(rejects(#""" Invalid documentation """#)) // Invalid xml:space #expect(rejects(#""" Invalid documentation """#)) } }