1
1
<?php declare (strict_types=1 );
2
2
/*
3
- * This file is part of Document \Engine.
3
+ * This file is part of Templado \Engine.
4
4
*
5
5
* Copyright (c) Arne Blankerts <[email protected] > and contributors
6
6
*
9
9
*/
10
10
namespace Templado \Engine ;
11
11
12
+ use function libxml_get_errors ;
13
+ use ArrayIterator ;
12
14
use DOMDocument ;
13
15
use PHPUnit \Framework \Attributes \CoversClass ;
14
16
use PHPUnit \Framework \Attributes \UsesClass ;
@@ -39,6 +41,18 @@ public function testCanBeConstructedFromString(): void {
39
41
);
40
42
}
41
43
44
+ public function testExistingLibxmlErrorStateGetsClearedOnConstruct (): void {
45
+ libxml_use_internal_errors (true );
46
+ $ dummy = new DOMDocument ();
47
+ $ dummy ->loadXML ('parsing-this-will-cause-libxml-errors ' );
48
+ libxml_use_internal_errors (false );
49
+
50
+ $ this ->assertInstanceOf (
51
+ Document::class,
52
+ Document::fromString ('<?xml version="1.0" ?><root /> ' )
53
+ );
54
+ }
55
+
42
56
public function testCanBeConstructedFromStringWithId (): void {
43
57
$ id = new Id ('abc ' );
44
58
$ instance = Document::fromString ('<?xml version="1.0" ?><root /> ' , $ id );
@@ -51,25 +65,44 @@ public function testCanBeConstructedFromStringWithId(): void {
51
65
}
52
66
53
67
public function testCanBeSerializedBackToStringWithoutSerializer (): void {
54
- $ xml = "<?xml version= \"1.0 \"?> \n<root/> \n" ;
68
+ $ xml = "<?xml version= \"1.0 \"?> \n<root/> \n" ;
55
69
$ instance = Document::fromString ($ xml );
56
70
$ this ->assertEquals ($ xml , $ instance ->asString ());
57
71
}
58
72
59
73
public function testTryingToParseInvalidMarkupStringThrowsException (): void {
60
- $ this ->expectException (ParsingException::class);
61
- Document::fromString ('<?xml version="1.0" ?><root> ' );
74
+ $ caught = null ;
75
+ try {
76
+ Document::fromString ('<?xml version="1.0" ?><root> ' );
77
+ } catch (\Throwable $ t ) {
78
+ $ caught = $ t ;
79
+ }
80
+
81
+ $ this ->assertInstanceOf (ParsingException::class, $ caught );
82
+ $ this ->assertEmpty (libxml_get_errors ());
62
83
}
63
84
64
85
public function testSelectionOfSingleNodeCanBeExtracted (): void {
65
86
$ id = new Id ('test ' );
66
- $ result = (Document::fromString ('<?xml version="1.0" ?><root><child / ></root> ' ))->extract (
87
+ $ result = (Document::fromString ('<?xml version="1.0" ?><root><child><p>text</p></child ></root> ' ))->extract (
67
88
new XPathSelector ('//child ' ),
68
89
$ id
69
90
);
70
91
71
92
$ this ->assertInstanceOf (Document::class, $ result );
72
93
$ this ->assertEquals ($ id , $ result ->id ());
94
+
95
+ $ result ->asString (new class ($ this ) implements Serializer {
96
+ public function __construct (
97
+ private TestCase $ testCase
98
+ ) {
99
+ }
100
+ public function serialize (DOMDocument $ document ): string {
101
+ $ this ->testCase ->assertEquals ('child ' , $ document ->documentElement ->nodeName );
102
+ $ this ->testCase ->assertTrue ($ document ->documentElement ->hasChildNodes ());
103
+ return '' ;
104
+ }
105
+ });
73
106
}
74
107
75
108
public function testExtractingEmptySelectionThrowsException (): void {
@@ -80,21 +113,20 @@ public function testExtractingEmptySelectionThrowsException(): void {
80
113
}
81
114
82
115
public function testSelectionOfMultiNodesCanBeExtracted (): void {
83
- $ result = (Document::fromString ('<?xml version="1.0" ?><root><child / ><child /></root> ' ))->extract (
116
+ $ result = (Document::fromString ('<?xml version="1.0" ?><root><child><p>text</p></child ><child /></root> ' ))->extract (
84
117
new XPathSelector ('//child ' )
85
118
);
86
119
87
120
$ this ->assertInstanceOf (Document::class, $ result );
88
121
89
122
$ result ->asString (new class ($ this ) implements Serializer {
90
-
91
123
public function __construct (
92
124
private TestCase $ testCase
93
- ){
94
-
125
+ ) {
95
126
}
96
127
public function serialize (DOMDocument $ document ): string {
97
128
$ this ->testCase ->assertCount (2 , $ document ->getElementsByTagName ('child ' ));
129
+ $ this ->testCase ->assertTrue ($ document ->documentElement ->firstElementChild ->hasChildNodes ());
98
130
99
131
return '' ;
100
132
}
@@ -126,7 +158,7 @@ public function testTransformationCanBeApplied(): void {
126
158
$ dom ->loadXML ('<?xml version="1.0" ?><root><child /></root> ' );
127
159
128
160
$ selection = $ this ->createMock (Selection::class);
129
- $ selection ->method ('getIterator ' )->willReturn (new \ ArrayIterator ([$ dom ->documentElement ->firstChild ]));
161
+ $ selection ->method ('getIterator ' )->willReturn (new ArrayIterator ([$ dom ->documentElement ->firstChild ]));
130
162
131
163
$ selector = $ this ->createMock (Selector::class);
132
164
$ selector ->method ('select ' )->willReturn ($ selection );
@@ -228,4 +260,33 @@ public function testTryingToMergeDocumentCollectionWithDocumentWithoutIdThrowsEx
228
260
$ target ->merge ($ list );
229
261
}
230
262
263
+ public function testBlankWhitespaceGetsRemoved (): void {
264
+ $ document = Document::fromString (
265
+ implode ("\n" ,[
266
+ '<?xml version="1.0" ?> ' ,
267
+ '<root> ' ,
268
+ ' <p>text</p> ' ,
269
+ '</root> '
270
+ ])
271
+ );
272
+
273
+ $ document ->asString (new class ($ this ) implements Serializer {
274
+ public function __construct (
275
+ private TestCase $ testCase
276
+ ) {
277
+ }
278
+ public function serialize (DOMDocument $ document ): string {
279
+ $ this ->testCase ->assertCount (1 , $ document ->documentElement ->childNodes );
280
+ return '' ;
281
+ }
282
+ });
283
+ }
284
+
285
+ public function testNonFatalWarningsFromParsingAreCaught (): void {
286
+ $ this ->expectException (ParsingException::class);
287
+ $ xml = '<?xml version="1.0" encoding="UTF-8"?> '
288
+ .'<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd"> '
289
+ .'<body> </body> ' ;
290
+ (Document::fromString ($ xml ));
291
+ }
231
292
}
0 commit comments