Skip to content

Commit

Permalink
Encode element with empty key, empty element, and attributes (CoreOff…
Browse files Browse the repository at this point in the history
…ice#223)

Fixes an edge case with intrinsic value key encoding.
  • Loading branch information
wooj2 authored and spotlightishere committed Aug 6, 2021
1 parent 93132b4 commit 84257a7
Show file tree
Hide file tree
Showing 2 changed files with 79 additions and 5 deletions.
18 changes: 13 additions & 5 deletions Sources/XMLCoder/Auxiliaries/XMLCoderElement.swift
Expand Up @@ -217,9 +217,16 @@ struct XMLCoderElement: Equatable {
_ string: inout String,
_ charactersEscapedInAttributes: [(String, String)]
) {
let attributesBelongingToContainer = self.elements.filter {
$0.key.isEmpty && !$0.attributes.isEmpty
}.flatMap {
$0.attributes
}
let allAttributes = self.attributes + attributesBelongingToContainer

let attributes = formatting.contains(.sortedKeys) ?
self.attributes.sorted(by: { $0.key < $1.key }) :
self.attributes
allAttributes.sorted(by: { $0.key < $1.key }) :
allAttributes
formatXMLAttributes(
from: attributes,
into: &string,
Expand Down Expand Up @@ -266,10 +273,9 @@ struct XMLCoderElement: Equatable {

if !key.isEmpty {
string += "<\(key)"
formatXMLAttributes(formatting, &string, escapedCharacters.attributes)
}

formatXMLAttributes(formatting, &string, escapedCharacters.attributes)

if !elements.isEmpty {
let prettyPrintElements = prettyPrinted && !containsTextNodes
if !key.isEmpty {
Expand All @@ -282,7 +288,9 @@ struct XMLCoderElement: Equatable {
string += "</\(key)>"
}
} else {
string += " />"
if !key.isEmpty {
string += " />"
}
}

return string
Expand Down
66 changes: 66 additions & 0 deletions Tests/XMLCoderTests/Auxiliary/XMLElementTests.swift
Expand Up @@ -64,4 +64,70 @@ class XMLElementTests: XCTestCase {
XCTAssert(whitespaceElement2.isWhitespaceWithNoElements())
XCTAssert(whitespaceElement3.isWhitespaceWithNoElements())
}

func testNestedElementWith_Namespace_Attribute() {
typealias Attribute = XMLCoderElement.Attribute
typealias Element = XMLCoderElement
let nested = Element(key: "Nested",
elements: [
Element(key: "",
elements: [],
attributes: [
Attribute(key: "xsi:someName", value: "nestedAttrValue")
]
)],
attributes: [
Attribute(key: "xmlns:xsi", value: "https://example.com")
])
let inputNamespace = Attribute(key: "xmlns", value: "https://example.com")
let input = Element(key: "Input",
elements: [nested],
attributes: [inputNamespace])

let result = input.toXMLString(
escapedCharacters: (elements: XMLEncoder().charactersEscapedInElements,
attributes: XMLEncoder().charactersEscapedInAttributes),
formatting: [],
indentation: .spaces(4)
)

XCTAssertEqual(result, """
<Input xmlns="https://example.com"><Nested xmlns:xsi="https://example.com" xsi:someName="nestedAttrValue"></Nested></Input>
""")
}

func testNestedElementWith_Namespace_Attribute_Element() {
typealias Attribute = XMLCoderElement.Attribute
typealias Element = XMLCoderElement
let nested = Element(key: "Nested",
elements: [
Element(key: "",
elements: [
Element(key: "nonAttrField",
elements: [Element(key: "", stringValue: "hello")],
attributes: [])
],
attributes: [
Attribute(key: "xsi:someName", value: "nestedAttrValue")
]
)],
attributes: [
Attribute(key: "xmlns:xsi", value: "https://example.com")
])
let inputNamespace = Attribute(key: "xmlns", value: "https://example.com")
let input = Element(key: "Input",
elements: [nested],
attributes: [inputNamespace])

let result = input.toXMLString(
escapedCharacters: (elements: XMLEncoder().charactersEscapedInElements,
attributes: XMLEncoder().charactersEscapedInAttributes),
formatting: [],
indentation: .spaces(4)
)

XCTAssertEqual(result, """
<Input xmlns="https://example.com"><Nested xmlns:xsi="https://example.com" xsi:someName="nestedAttrValue"><nonAttrField>hello</nonAttrField></Nested></Input>
""")
}
}

0 comments on commit 84257a7

Please sign in to comment.