Skip to content

Commit d3a3db7

Browse files
authored
Merge pull request #42 from vapor/ubuntu_render_issue
Ubuntu render issue
2 parents 483e364 + 799609e commit d3a3db7

File tree

4 files changed

+70
-5
lines changed

4 files changed

+70
-5
lines changed

Sources/Leaf/HTMLEscape.swift

Lines changed: 37 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,43 @@
11
import Foundation
22

3+
extension Byte {
4+
// <
5+
static let lessThan: Byte = 0x3C
6+
7+
// >
8+
static let greaterThan: Byte = 0x3E
9+
}
10+
311
extension String {
412
func htmlEscaped() -> String {
5-
return replacingOccurrences(of: "&", with: "&amp;")
6-
.replacingOccurrences(of: "\"", with: "&quot;")
7-
.replacingOccurrences(of: "'", with: "&#39;")
8-
.replacingOccurrences(of: "<", with: "&lt;")
9-
.replacingOccurrences(of: ">", with: "&gt;")
13+
/**
14+
***** WARNING ******
15+
16+
Temporary resolution to the following issue in swift on linux:
17+
https://github.com/vapor/leaf/issues/41
18+
19+
See:
20+
https://bugs.swift.org/browse/SR-3448
21+
22+
Replace when appropriate with:
23+
24+
return replacingOccurrences(of: "&", with: "&amp;")
25+
.replacingOccurrences(of: "\"", with: "&quot;")
26+
.replacingOccurrences(of: "'", with: "&#39;")
27+
.replacingOccurrences(of: "<", with: "&lt;")
28+
.replacingOccurrences(of: ">", with: "&gt;")
29+
*/
30+
return bytes
31+
.split(separator: .ampersand, omittingEmptySubsequences: false)
32+
.joined(separator: "&amp;".bytes)
33+
.split(separator: .quotationMark, omittingEmptySubsequences: false)
34+
.joined(separator: "&quot;".bytes)
35+
.split(separator: .apostrophe, omittingEmptySubsequences: false)
36+
.joined(separator: "&#39;".bytes)
37+
.split(separator: .lessThan, omittingEmptySubsequences: false)
38+
.joined(separator: "&lt;".bytes)
39+
.split(separator: .greaterThan, omittingEmptySubsequences: false)
40+
.joined(separator: "&gt;".bytes)
41+
.string
1042
}
1143
}
Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
import Foundation
2+
import XCTest
3+
@testable import Leaf
4+
5+
class HTMLEscapeTests: XCTestCase {
6+
static let allTests = [
7+
("testHTMLEscape", testHTMLEscape),
8+
("testHTMLEscapeCRLFQuotes", testHTMLEscapeCRLFQuotes),
9+
]
10+
11+
func testHTMLEscape() throws {
12+
let input = "&\"'<>"
13+
let expected = "&amp;&quot;&#39;&lt;&gt;"
14+
15+
XCTAssertEqual(input.htmlEscaped(), expected)
16+
}
17+
18+
func testHTMLEscapeCRLFQuotes() throws {
19+
let input = "\r\n\""
20+
let expected = "\r\n&quot;"
21+
22+
XCTAssertEqual(input.htmlEscaped(), expected)
23+
}
24+
}

Tests/LeafTests/VariableTests.swift

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ class VariableTests: XCTestCase {
88
("testVariableThrows", testVariableThrows),
99
("testVariableEscape", testVariableEscape),
1010
("testConstant", testConstant),
11+
("testCarriageReturn", testCarriageReturn),
1112
]
1213

1314
func testVariable() throws {
@@ -40,4 +41,11 @@ class VariableTests: XCTestCase {
4041
let rendered = try stem.render(leaf, with: context).string
4142
XCTAssert(rendered == "Hello, World!")
4243
}
44+
45+
func testCarriageReturn() throws {
46+
let leaf = try stem.spawnLeaf(raw: "This thing: #(content)")
47+
let context = Context(["content": "\r\n\"/\""])
48+
let rendered = try stem.render(leaf, with: context).string
49+
XCTAssertEqual(rendered, "This thing: \r\n&quot;/&quot;")
50+
}
4351
}

Tests/LinuxMain.swift

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@ XCTMain([
99
testCase(FileLoadTests.allTests),
1010
testCase(IfTests.allTests),
1111
testCase(IndexTests.allTests),
12+
testCase(HTMLEscapeTests.allTests),
1213
testCase(LinkTests.allTests),
1314
testCase(LoopTests.allTests),
1415
testCase(NodeRenderTests.allTests),

0 commit comments

Comments
 (0)