rexml 3.2.4 → 3.2.5
Sign up to get free protection for your applications and to get access to all the features.
Potentially problematic release.
This version of rexml might be problematic. Click here for more details.
- checksums.yaml +4 -4
- data/NEWS.md +37 -0
- data/README.md +2 -14
- data/doc/rexml/context.rdoc +143 -0
- data/doc/rexml/tasks/rdoc/child.rdoc +87 -0
- data/doc/rexml/tasks/rdoc/document.rdoc +276 -0
- data/doc/rexml/tasks/rdoc/element.rdoc +602 -0
- data/doc/rexml/tasks/rdoc/node.rdoc +97 -0
- data/doc/rexml/tasks/rdoc/parent.rdoc +267 -0
- data/doc/rexml/tasks/tocs/child_toc.rdoc +12 -0
- data/doc/rexml/tasks/tocs/document_toc.rdoc +30 -0
- data/doc/rexml/tasks/tocs/element_toc.rdoc +55 -0
- data/doc/rexml/tasks/tocs/master_toc.rdoc +135 -0
- data/doc/rexml/tasks/tocs/node_toc.rdoc +16 -0
- data/doc/rexml/tasks/tocs/parent_toc.rdoc +25 -0
- data/lib/rexml.rb +3 -0
- data/lib/rexml/doctype.rb +55 -31
- data/lib/rexml/document.rb +194 -34
- data/lib/rexml/element.rb +1786 -456
- data/lib/rexml/light/node.rb +0 -8
- data/lib/rexml/parsers/baseparser.rb +139 -39
- data/lib/rexml/parsers/xpathparser.rb +25 -11
- data/lib/rexml/rexml.rb +27 -22
- data/lib/rexml/xpath_parser.rb +36 -30
- metadata +49 -11
- data/.gitignore +0 -9
- data/.travis.yml +0 -24
- data/Gemfile +0 -6
- data/Rakefile +0 -8
- data/rexml.gemspec +0 -84
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: fc3edd128c37b7817a6db92dfa9d45add8328d9c5f6983652d24562cd6968672
|
4
|
+
data.tar.gz: 1c604fe6aa4908d8c13134c8f0966bd1483a01ad2ccca0ad1a85057e39f36e54
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 4b3f5f714c38e22ed05b53389e7d3950896f1da2675527c28ed6c7f91ef18bb49fec90e0120c2f2c911da85db34a3a99e9b6209ba4d5dc4876379c6302a01ace
|
7
|
+
data.tar.gz: 9b11b1cfcdb9404574f35ad237b141c6d6fd97b34ead68401064228eb7562c2d13576e1b66a75fa1e3ddc70d937ff638c31de03eb9bc47274c01711eb8abcf3f
|
data/NEWS.md
CHANGED
@@ -1,5 +1,42 @@
|
|
1
1
|
# News
|
2
2
|
|
3
|
+
## 3.2.5 - 2021-04-05 {#version-3-2-5}
|
4
|
+
|
5
|
+
### Improvements
|
6
|
+
|
7
|
+
* Add more validations to XPath parser.
|
8
|
+
|
9
|
+
* `require "rexml/docuemnt"` by default.
|
10
|
+
[GitHub#36][Patch by Koichi ITO]
|
11
|
+
|
12
|
+
* Don't add `#dcloe` method to core classes globally.
|
13
|
+
[GitHub#37][Patch by Akira Matsuda]
|
14
|
+
|
15
|
+
* Add more documentations.
|
16
|
+
[Patch by Burdette Lamar]
|
17
|
+
|
18
|
+
* Added `REXML::Elements#parent`.
|
19
|
+
[GitHub#52][Patch by Burdette Lamar]
|
20
|
+
|
21
|
+
### Fixes
|
22
|
+
|
23
|
+
* Fixed a bug that `REXML::DocType#clone` doesn't copy external ID
|
24
|
+
information.
|
25
|
+
|
26
|
+
* Fixed round-trip vulnerability bugs.
|
27
|
+
See also: https://www.ruby-lang.org/en/news/2021/04/05/xml-round-trip-vulnerability-in-rexml-cve-2021-28965/
|
28
|
+
[HackerOne#1104077][CVE-2021-28965][Reported by Juho Nurminen]
|
29
|
+
|
30
|
+
### Thanks
|
31
|
+
|
32
|
+
* Koichi ITO
|
33
|
+
|
34
|
+
* Akira Matsuda
|
35
|
+
|
36
|
+
* Burdette Lamar
|
37
|
+
|
38
|
+
* Juho Nurminen
|
39
|
+
|
3
40
|
## 3.2.4 - 2020-01-31 {#version-3-2-4}
|
4
41
|
|
5
42
|
### Improvements
|
data/README.md
CHANGED
@@ -4,21 +4,9 @@ REXML was inspired by the Electric XML library for Java, which features an easy-
|
|
4
4
|
|
5
5
|
REXML supports both tree and stream document parsing. Stream parsing is faster (about 1.5 times as fast). However, with stream parsing, you don't get access to features such as XPath.
|
6
6
|
|
7
|
-
##
|
7
|
+
## API
|
8
8
|
|
9
|
-
|
10
|
-
|
11
|
-
```ruby
|
12
|
-
gem 'rexml'
|
13
|
-
```
|
14
|
-
|
15
|
-
And then execute:
|
16
|
-
|
17
|
-
$ bundle
|
18
|
-
|
19
|
-
Or install it yourself as:
|
20
|
-
|
21
|
-
$ gem install rexml
|
9
|
+
See the {API documentation}[https://ruby.github.io/rexml/]
|
22
10
|
|
23
11
|
## Usage
|
24
12
|
|
@@ -0,0 +1,143 @@
|
|
1
|
+
== Element Context
|
2
|
+
|
3
|
+
Notes:
|
4
|
+
- All code on this page presupposes that the following has been executed:
|
5
|
+
|
6
|
+
require 'rexml/document'
|
7
|
+
|
8
|
+
- For convenience, examples on this page use +REXML::Document.new+, not +REXML::Element.new+.
|
9
|
+
This is completely valid, because REXML::Document is a subclass of REXML::Element.
|
10
|
+
|
11
|
+
The context for an element is a hash of processing directives
|
12
|
+
that influence the way \XML is read, stored, and written.
|
13
|
+
The context entries are:
|
14
|
+
|
15
|
+
- +:respect_whitespace+: controls treatment of whitespace.
|
16
|
+
- +:compress_whitespace+: determines whether whitespace is compressed.
|
17
|
+
- +:ignore_whitespace_nodes+: determines whether whitespace-only nodes are to be ignored.
|
18
|
+
- +:raw+: controls treatment of special characters and entities.
|
19
|
+
|
20
|
+
The default context for a new element is <tt>{}</tt>.
|
21
|
+
You can set the context at element-creation time:
|
22
|
+
|
23
|
+
d = REXML::Document.new('', {compress_whitespace: :all, raw: :all})
|
24
|
+
d.context # => {:compress_whitespace=>:all, :raw=>:all}
|
25
|
+
|
26
|
+
You can reset the entire context by assigning a new hash:
|
27
|
+
|
28
|
+
d.context = {ignore_whitespace_nodes: :all}
|
29
|
+
d.context # => {:ignore_whitespace_nodes=>:all}
|
30
|
+
|
31
|
+
Or you can create or modify an individual entry:
|
32
|
+
|
33
|
+
d.context[:raw] = :all
|
34
|
+
d.context # => {:ignore_whitespace_nodes=>:all, :raw=>:all}
|
35
|
+
|
36
|
+
=== +:respect_whitespace+
|
37
|
+
|
38
|
+
Affects: +REXML::Element.new+, +REXML::Element.text=+.
|
39
|
+
|
40
|
+
By default, all parsed whitespace is respected (that is, stored whitespace not compressed):
|
41
|
+
|
42
|
+
xml_string = '<root><foo>a b</foo> <bar>c d</bar> <baz>e f</baz></root>'
|
43
|
+
d = REXML::Document.new(xml_string)
|
44
|
+
d.to_s # => "<root><foo>a b</foo> <bar>c d</bar> <baz>e f</baz></root>"
|
45
|
+
|
46
|
+
Use +:respect_whitespace+ with an array of element names
|
47
|
+
to specify the elements that _are_ to have their whitespace respected;
|
48
|
+
other elements' whitespace, and whitespace between elements, will be compressed.
|
49
|
+
|
50
|
+
In this example: +foo+ and +baz+ will have their whitespace respected;
|
51
|
+
+bar+ and the space between elements will have their whitespace compressed:
|
52
|
+
|
53
|
+
d = REXML::Document.new(xml_string, {respect_whitespace: ['foo', 'baz']})
|
54
|
+
d.to_s # => "<root><foo>a b</foo> <bar>c d</bar> <baz>e f</baz></root>"
|
55
|
+
bar = d.root[2] # => <bar> ... </>
|
56
|
+
bar.text = 'X Y'
|
57
|
+
d.to_s # => "<root><foo>a b</foo> <bar>X Y</bar> <baz>e f</baz></root>"
|
58
|
+
|
59
|
+
=== +:compress_whitespace+
|
60
|
+
|
61
|
+
Affects: +REXML::Element.new+, +REXML::Element.text=+.
|
62
|
+
|
63
|
+
Use <tt>compress_whitespace: :all</tt>
|
64
|
+
to compress whitespace both within and between elements:
|
65
|
+
|
66
|
+
xml_string = '<root><foo>a b</foo> <bar>c d</bar> <baz>e f</baz></root>'
|
67
|
+
d = REXML::Document.new(xml_string, {compress_whitespace: :all})
|
68
|
+
d.to_s # => "<root><foo>a b</foo> <bar>c d</bar> <baz>e f</baz></root>"
|
69
|
+
|
70
|
+
Use +:compress_whitespace+ with an array of element names
|
71
|
+
to compress whitespace in those elements,
|
72
|
+
but not in other elements nor between elements.
|
73
|
+
|
74
|
+
In this example, +foo+ and +baz+ will have their whitespace compressed;
|
75
|
+
+bar+ and the space between elements will not:
|
76
|
+
|
77
|
+
d = REXML::Document.new(xml_string, {compress_whitespace: ['foo', 'baz']})
|
78
|
+
d.to_s # => "<root><foo>a b</foo> <bar>c d</bar> <baz>e f</baz></root>"
|
79
|
+
foo = d.root[0] # => <foo> ... </>
|
80
|
+
foo.text= 'X Y'
|
81
|
+
d.to_s # => "<root><foo>X Y</foo> <bar>c d</bar> <baz>e f</baz></root>"
|
82
|
+
|
83
|
+
=== +:ignore_whitespace_nodes+
|
84
|
+
|
85
|
+
Affects: +REXML::Element.new+.
|
86
|
+
|
87
|
+
Use <tt>ignore_whitespace_nodes: :all</tt> to omit all whitespace-only elements.
|
88
|
+
|
89
|
+
In this example, +bar+ has a text node, while nodes +foo+ and +baz+ do not:
|
90
|
+
|
91
|
+
xml_string = '<root><foo> </foo><bar> BAR </bar><baz> </baz></root>'
|
92
|
+
d = REXML::Document.new(xml_string, {ignore_whitespace_nodes: :all})
|
93
|
+
d.to_s # => "<root><foo> FOO </foo><bar/><baz> BAZ </baz></root>"
|
94
|
+
root = d.root # => <root> ... </>
|
95
|
+
foo = root[0] # => <foo/>
|
96
|
+
bar = root[1] # => <bar> ... </>
|
97
|
+
baz = root[2] # => <baz/>
|
98
|
+
foo.first.class # => NilClass
|
99
|
+
bar.first.class # => REXML::Text
|
100
|
+
baz.first.class # => NilClass
|
101
|
+
|
102
|
+
Use +:ignore_whitespace_nodes+ with an array of element names
|
103
|
+
to specify the elements that are to have whitespace nodes ignored.
|
104
|
+
|
105
|
+
In this example, +bar+ and +baz+ have text nodes, while node +foo+ does not.
|
106
|
+
|
107
|
+
xml_string = '<root><foo> </foo><bar> BAR </bar><baz> </baz></root>'
|
108
|
+
d = REXML::Document.new(xml_string, {ignore_whitespace_nodes: ['foo']})
|
109
|
+
d.to_s # => "<root><foo/><bar> BAR </bar><baz> </baz></root>"
|
110
|
+
root = d.root # => <root> ... </>
|
111
|
+
foo = root[0] # => <foo/>
|
112
|
+
bar = root[1] # => <bar> ... </>
|
113
|
+
baz = root[2] # => <baz> ... </>
|
114
|
+
foo.first.class # => NilClass
|
115
|
+
bar.first.class # => REXML::Text
|
116
|
+
baz.first.class # => REXML::Text
|
117
|
+
|
118
|
+
=== +:raw+
|
119
|
+
|
120
|
+
Affects: +Element.text=+, +Element.add_text+, +Text.to_s+.
|
121
|
+
|
122
|
+
Parsing of +a+ elements is not affected by +raw+:
|
123
|
+
|
124
|
+
xml_string = '<root><a>0 < 1</a><b>1 > 0</b></root>'
|
125
|
+
d = REXML::Document.new(xml_string, {:raw => ['a']})
|
126
|
+
d.root.to_s # => "<root><a>0 < 1</a><b>1 > 0</b></root>"
|
127
|
+
a, b = *d.root.elements
|
128
|
+
a.to_s # => "<a>0 < 1</a>"
|
129
|
+
b.to_s # => "<b>1 > 0</b>"
|
130
|
+
|
131
|
+
But Element#text= is affected:
|
132
|
+
|
133
|
+
a.text = '0 < 1'
|
134
|
+
b.text = '1 > 0'
|
135
|
+
a.to_s # => "<a>0 < 1</a>"
|
136
|
+
b.to_s # => "<b>1 &gt; 0</b>"
|
137
|
+
|
138
|
+
As is Element.add_text:
|
139
|
+
|
140
|
+
a.add_text(' so 1 > 0')
|
141
|
+
b.add_text(' so 0 < 1')
|
142
|
+
a.to_s # => "<a>0 < 1 so 1 > 0</a>"
|
143
|
+
b.to_s # => "<b>1 &gt; 0 so 0 &lt; 1</b>"
|
@@ -0,0 +1,87 @@
|
|
1
|
+
== Class Child
|
2
|
+
|
3
|
+
Class Child includes module Node;
|
4
|
+
see {Tasks for Node}[node_rdoc.html].
|
5
|
+
|
6
|
+
:include: ../tocs/child_toc.rdoc
|
7
|
+
|
8
|
+
=== Relationships
|
9
|
+
|
10
|
+
==== Task: Set the Parent
|
11
|
+
|
12
|
+
Use method {Child#parent=}[../../../../REXML/Parent.html#method-i-parent-3D]
|
13
|
+
to set the parent:
|
14
|
+
|
15
|
+
e0 = REXML::Element.new('foo')
|
16
|
+
e1 = REXML::Element.new('bar')
|
17
|
+
e1.parent # => nil
|
18
|
+
e1.parent = e0
|
19
|
+
e1.parent # => <foo/>
|
20
|
+
|
21
|
+
==== Task: Insert Previous Sibling
|
22
|
+
|
23
|
+
Use method {Child#previous_sibling=}[../../../../REXML/Parent.html#method-i-previous_sibling-3D]
|
24
|
+
to insert a previous sibling:
|
25
|
+
|
26
|
+
xml_string = '<root><a/><c/></root>'
|
27
|
+
d = REXML::Document.new(xml_string)
|
28
|
+
d.root.to_a # => [<a/>, <c/>]
|
29
|
+
c = d.root[1] # => <c/>
|
30
|
+
b = REXML::Element.new('b')
|
31
|
+
c.previous_sibling = b
|
32
|
+
d.root.to_a # => [<a/>, <b/>, <c/>]
|
33
|
+
|
34
|
+
==== Task: Insert Next Sibling
|
35
|
+
|
36
|
+
Use method {Child#next_sibling=}[../../../../REXML/Parent.html#method-i-next-sibling-3D]
|
37
|
+
to insert a previous sibling:
|
38
|
+
|
39
|
+
xml_string = '<root><a/><c/></root>'
|
40
|
+
d = REXML::Document.new(xml_string)
|
41
|
+
d.root.to_a # => [<a/>, <c/>]
|
42
|
+
a = d.root[0] # => <a/>
|
43
|
+
b = REXML::Element.new('b')
|
44
|
+
a.next_sibling = b
|
45
|
+
d.root.to_a # => [<a/>, <b/>, <c/>]
|
46
|
+
|
47
|
+
=== Removal or Replacement
|
48
|
+
|
49
|
+
==== Task: Remove Child from Parent
|
50
|
+
|
51
|
+
Use method {Child#remove}[../../../../REXML/Parent.html#method-i-remove]
|
52
|
+
to remove a child from its parent; returns the removed child:
|
53
|
+
|
54
|
+
xml_string = '<root><a/><b/><c/></root>'
|
55
|
+
d = REXML::Document.new(xml_string)
|
56
|
+
d.root.to_a # => [<a/>, <b/>, <c/>]
|
57
|
+
b = d.root[1] # => <b/>
|
58
|
+
b.remove # => <b/>
|
59
|
+
d.root.to_a # => [<a/>, <c/>]
|
60
|
+
|
61
|
+
==== Task: Replace Child
|
62
|
+
|
63
|
+
Use method {Child#replace_with}[../../../../REXML/Parent.html#method-i-replace]
|
64
|
+
to replace a child;
|
65
|
+
returns the replaced child:
|
66
|
+
|
67
|
+
xml_string = '<root><a/><b/><c/></root>'
|
68
|
+
d = REXML::Document.new(xml_string)
|
69
|
+
d.root.to_a # => [<a/>, <b/>, <c/>]
|
70
|
+
b = d.root[1] # => <b/>
|
71
|
+
d = REXML::Element.new('d')
|
72
|
+
b.replace_with(d) # => <b/>
|
73
|
+
d.root.to_a # => [<a/>, <d/>, <c/>]
|
74
|
+
|
75
|
+
=== Document
|
76
|
+
|
77
|
+
==== Task: Get the Document
|
78
|
+
|
79
|
+
Use method {Child#document}[../../../../REXML/Parent.html#method-i-document]
|
80
|
+
to get the document for the child:
|
81
|
+
|
82
|
+
xml_string = '<root><a/><b/><c/></root>'
|
83
|
+
d = REXML::Document.new(xml_string)
|
84
|
+
d.root.to_a # => [<a/>, <b/>, <c/>]
|
85
|
+
b = d.root[1] # => <b/>
|
86
|
+
b.document == d # => true
|
87
|
+
REXML::Child.new.document # => nil
|
@@ -0,0 +1,276 @@
|
|
1
|
+
== Class Document
|
2
|
+
|
3
|
+
Class Document has methods from its superclasses and included modules;
|
4
|
+
see:
|
5
|
+
|
6
|
+
- {Tasks for Element}[element_rdoc.html].
|
7
|
+
- {Tasks for Parent}[parent_rdoc.html].
|
8
|
+
- {Tasks for Child}[child_rdoc.html].
|
9
|
+
- {Tasks for Node}[node_rdoc.html].
|
10
|
+
- {Module Enumerable}[https://docs.ruby-lang.org/en/master/Enumerable.html].
|
11
|
+
|
12
|
+
:include: ../tocs/document_toc.rdoc
|
13
|
+
|
14
|
+
=== New Document
|
15
|
+
|
16
|
+
==== Task: Create an Empty Document
|
17
|
+
|
18
|
+
Use method {Document::new}[../../../../REXML/Document.html#method-c-new]
|
19
|
+
to create an empty document.
|
20
|
+
|
21
|
+
d = REXML::Document.new
|
22
|
+
|
23
|
+
==== Task: Parse a \String into a New Document
|
24
|
+
|
25
|
+
Use method {Document::new}[../../../../REXML/Document.html#method-c-new]
|
26
|
+
to parse an XML string into a new document:
|
27
|
+
|
28
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
29
|
+
d = REXML::Document.new(xml_string)
|
30
|
+
d.root # => <root> ... </>
|
31
|
+
|
32
|
+
==== Task: Parse an \IO Stream into a New Document
|
33
|
+
|
34
|
+
Use method {Document::new}[../../../../REXML/Document.html#method-c-new]
|
35
|
+
to parse an XML \IO stream into a new document:
|
36
|
+
|
37
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
38
|
+
File.write('t.xml', xml_string)
|
39
|
+
d = File.open('t.xml', 'r') do |file|
|
40
|
+
REXML::Document.new(file)
|
41
|
+
end
|
42
|
+
d.root # => <root> ... </>
|
43
|
+
|
44
|
+
==== Task: Create a Document from an Existing Document
|
45
|
+
|
46
|
+
Use method {Document::new}[../../../../REXML/Document.html#method-c-new]
|
47
|
+
to create a document from an existing document.
|
48
|
+
The context and attributes are copied to the new document,
|
49
|
+
but not the children:
|
50
|
+
|
51
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
52
|
+
d = REXML::Document.new(xml_string)
|
53
|
+
d.children # => [<root> ... </>]
|
54
|
+
d.context = {raw: :all, compress_whitespace: :all}
|
55
|
+
d.add_attributes({'bar' => 0, 'baz' => 1})
|
56
|
+
d1 = REXML::Document.new(d)
|
57
|
+
d1.context # => {:raw=>:all, :compress_whitespace=>:all}
|
58
|
+
d1.attributes # => {"bar"=>bar='0', "baz"=>baz='1'}
|
59
|
+
d1.children # => []
|
60
|
+
|
61
|
+
==== Task: Clone a Document
|
62
|
+
|
63
|
+
Use method {Document#clone}[../../../../REXML/Document.html#method-i-clone]
|
64
|
+
to clone a document.
|
65
|
+
The context and attributes are copied to the new document,
|
66
|
+
but not the children:
|
67
|
+
|
68
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
69
|
+
d = REXML::Document.new(xml_string)
|
70
|
+
d.children # => [<root> ... </>]
|
71
|
+
d.context = {raw: :all, compress_whitespace: :all}
|
72
|
+
d.add_attributes({'bar' => 0, 'baz' => 1})
|
73
|
+
d1 = d.clone # => < bar='0' baz='1'/>
|
74
|
+
d1.context # => {:raw=>:all, :compress_whitespace=>:all}
|
75
|
+
d1.attributes # => {"bar"=>bar='0', "baz"=>baz='1'}
|
76
|
+
d1.children # => []
|
77
|
+
|
78
|
+
=== Document Type
|
79
|
+
|
80
|
+
==== Task: Get the Document Type
|
81
|
+
|
82
|
+
Use method {Document#doctype}[../../../../REXML/Document.html#method-i-doctype]
|
83
|
+
to get the document type:
|
84
|
+
|
85
|
+
d = REXML::Document.new('<!DOCTYPE document SYSTEM "subjects.dtd">')
|
86
|
+
d.doctype.class # => REXML::DocType
|
87
|
+
d = REXML::Document.new('')
|
88
|
+
d.doctype.class # => nil
|
89
|
+
|
90
|
+
==== Task: Set the Document Type
|
91
|
+
|
92
|
+
Use method {document#add}[../../../../REXML/Document.html#method-i-add]
|
93
|
+
to add or replace the document type:
|
94
|
+
|
95
|
+
d = REXML::Document.new('')
|
96
|
+
d.doctype.class # => nil
|
97
|
+
d.add(REXML::DocType.new('foo'))
|
98
|
+
d.doctype.class # => REXML::DocType
|
99
|
+
|
100
|
+
=== XML Declaration
|
101
|
+
|
102
|
+
==== Task: Get the XML Declaration
|
103
|
+
|
104
|
+
Use method {document#xml_decl}[../../../../REXML/Document.html#method-i-xml_decl]
|
105
|
+
to get the XML declaration:
|
106
|
+
|
107
|
+
d = REXML::Document.new('<!DOCTYPE document SYSTEM "subjects.dtd">')
|
108
|
+
d.xml_decl.class # => REXML::XMLDecl
|
109
|
+
d.xml_decl # => <?xml ... ?>
|
110
|
+
d = REXML::Document.new('')
|
111
|
+
d.xml_decl.class # => REXML::XMLDecl
|
112
|
+
d.xml_decl # => <?xml ... ?>
|
113
|
+
|
114
|
+
==== Task: Set the XML Declaration
|
115
|
+
|
116
|
+
Use method {document#add}[../../../../REXML/Document.html#method-i-add]
|
117
|
+
to replace the XML declaration:
|
118
|
+
|
119
|
+
d = REXML::Document.new('<!DOCTYPE document SYSTEM "subjects.dtd">')
|
120
|
+
d.add(REXML::XMLDecl.new)
|
121
|
+
|
122
|
+
=== Children
|
123
|
+
|
124
|
+
==== Task: Add an Element Child
|
125
|
+
|
126
|
+
Use method
|
127
|
+
{document#add_element}[../../../../REXML/Document.html#method-i-add_element]
|
128
|
+
to add an element to the document:
|
129
|
+
|
130
|
+
d = REXML::Document.new('')
|
131
|
+
d.add_element(REXML::Element.new('root'))
|
132
|
+
d.children # => [<root/>]
|
133
|
+
|
134
|
+
==== Task: Add a Non-Element Child
|
135
|
+
|
136
|
+
Use method
|
137
|
+
{document#add}[../../../../REXML/Document.html#method-i-add]
|
138
|
+
to add a non-element to the document:
|
139
|
+
|
140
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
141
|
+
d = REXML::Document.new(xml_string)
|
142
|
+
d.add(REXML::Text.new('foo'))
|
143
|
+
d.children # => [<root> ... </>, "foo"]
|
144
|
+
|
145
|
+
=== Writing
|
146
|
+
|
147
|
+
==== Task: Write to $stdout
|
148
|
+
|
149
|
+
Use method
|
150
|
+
{document#write}[../../../../REXML/Document.html#method-i-write]
|
151
|
+
to write the document to <tt>$stdout</tt>:
|
152
|
+
|
153
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
154
|
+
d = REXML::Document.new(xml_string)
|
155
|
+
d.write
|
156
|
+
|
157
|
+
Output:
|
158
|
+
|
159
|
+
<root><a/>text<b/>more<c/></root>
|
160
|
+
|
161
|
+
==== Task: Write to IO Stream
|
162
|
+
|
163
|
+
Use method
|
164
|
+
{document#write}[../../../../REXML/Document.html#method-i-write]
|
165
|
+
to write the document to <tt>$stdout</tt>:
|
166
|
+
|
167
|
+
xml_string = '<root><a/>text<b/>more<c/></root>'
|
168
|
+
d = REXML::Document.new(xml_string)
|
169
|
+
File.open('t.xml', 'w') do |file|
|
170
|
+
d.write(file)
|
171
|
+
end
|
172
|
+
p File.read('t.xml')
|
173
|
+
|
174
|
+
Output:
|
175
|
+
|
176
|
+
"<root><a/>text<b/>more<c/></root>"
|
177
|
+
|
178
|
+
==== Task: Write with No Indentation
|
179
|
+
|
180
|
+
Use method
|
181
|
+
{document#write}[../../../../REXML/Document.html#method-i-write]
|
182
|
+
to write the document with no indentation:
|
183
|
+
|
184
|
+
xml_string = '<root><a><b><c></c></b></a></root>'
|
185
|
+
d = REXML::Document.new(xml_string)
|
186
|
+
d.write({indent: 0})
|
187
|
+
|
188
|
+
Output:
|
189
|
+
|
190
|
+
<root>
|
191
|
+
<a>
|
192
|
+
<b>
|
193
|
+
<c/>
|
194
|
+
</b>
|
195
|
+
</a>
|
196
|
+
</root>
|
197
|
+
|
198
|
+
==== Task: Write with Specified Indentation
|
199
|
+
|
200
|
+
Use method
|
201
|
+
{document#write}[../../../../REXML/Document.html#method-i-write]
|
202
|
+
to write the document with a specified indentation:
|
203
|
+
|
204
|
+
xml_string = '<root><a><b><c></c></b></a></root>'
|
205
|
+
d = REXML::Document.new(xml_string)
|
206
|
+
d.write({indent: 2})
|
207
|
+
|
208
|
+
Output:
|
209
|
+
|
210
|
+
<root>
|
211
|
+
<a>
|
212
|
+
<b>
|
213
|
+
<c/>
|
214
|
+
</b>
|
215
|
+
</a>
|
216
|
+
</root>
|
217
|
+
|
218
|
+
=== Querying
|
219
|
+
|
220
|
+
==== Task: Get the Document
|
221
|
+
|
222
|
+
Use method
|
223
|
+
{document#document}[../../../../REXML/Document.html#method-i-document]
|
224
|
+
to get the document (+self+); overrides <tt>Element#document</tt>:
|
225
|
+
|
226
|
+
xml_string = '<root><a><b><c></c></b></a></root>'
|
227
|
+
d = REXML::Document.new(xml_string)
|
228
|
+
d.document == d # => true
|
229
|
+
|
230
|
+
==== Task: Get the Encoding
|
231
|
+
|
232
|
+
Use method
|
233
|
+
{document#document}[../../../../REXML/Document.html#method-i-document]
|
234
|
+
to get the document (+self+); overrides <tt>Element#document</tt>:
|
235
|
+
|
236
|
+
xml_string = '<root><a><b><c></c></b></a></root>'
|
237
|
+
d = REXML::Document.new(xml_string)
|
238
|
+
d.encoding # => "UTF-8"
|
239
|
+
|
240
|
+
==== Task: Get the Node Type
|
241
|
+
|
242
|
+
Use method
|
243
|
+
{document#node_type}[../../../../REXML/Document.html#method-i-node_type]
|
244
|
+
to get the node type (+:document+); overrides <tt>Element#node_type</tt>:
|
245
|
+
|
246
|
+
xml_string = '<root><a><b><c></c></b></a></root>'
|
247
|
+
d = REXML::Document.new(xml_string)
|
248
|
+
d.node_type # => :document
|
249
|
+
|
250
|
+
==== Task: Get the Root Element
|
251
|
+
|
252
|
+
Use method
|
253
|
+
{document#root}[../../../../REXML/Document.html#method-i-root]
|
254
|
+
to get the root element:
|
255
|
+
|
256
|
+
xml_string = '<root><a><b><c></c></b></a></root>'
|
257
|
+
d = REXML::Document.new(xml_string)
|
258
|
+
d.root # => <root> ... </>
|
259
|
+
|
260
|
+
==== Task: Determine Whether Stand-Alone
|
261
|
+
|
262
|
+
Use method
|
263
|
+
{document#stand_alone?}[../../../../REXML/Document.html#method-i-stand_alone-3F]
|
264
|
+
to get the stand-alone value:
|
265
|
+
|
266
|
+
d = REXML::Document.new('<?xml standalone="yes"?>')
|
267
|
+
d.stand_alone? # => "yes"
|
268
|
+
|
269
|
+
==== Task: Get the Version
|
270
|
+
|
271
|
+
Use method
|
272
|
+
{document#version}[../../../../REXML/Document.html#method-i-version]
|
273
|
+
to get the version:
|
274
|
+
|
275
|
+
d = REXML::Document.new('<?xml version="2.0" encoding="UTF-8"?>')
|
276
|
+
d.version # => "2.0"
|