libxml-ruby 0.6.0-x86-mswin32-60

Sign up to get free protection for your applications and to get access to all the features.
Files changed (127) hide show
  1. data/CHANGES +122 -0
  2. data/LICENSE +23 -0
  3. data/README +144 -0
  4. data/ext/libxml/cbg.c +76 -0
  5. data/ext/libxml/extconf.rb +308 -0
  6. data/ext/libxml/libxml.c +62 -0
  7. data/ext/libxml/ruby_libxml.h +93 -0
  8. data/ext/libxml/ruby_xml_attr.c +405 -0
  9. data/ext/libxml/ruby_xml_attr.h +19 -0
  10. data/ext/libxml/ruby_xml_document.c +1111 -0
  11. data/ext/libxml/ruby_xml_document.h +27 -0
  12. data/ext/libxml/ruby_xml_dtd.c +168 -0
  13. data/ext/libxml/ruby_xml_dtd.h +17 -0
  14. data/ext/libxml/ruby_xml_html_parser.c +449 -0
  15. data/ext/libxml/ruby_xml_html_parser.h +29 -0
  16. data/ext/libxml/ruby_xml_input_cbg.c +158 -0
  17. data/ext/libxml/ruby_xml_input_cbg.h +20 -0
  18. data/ext/libxml/ruby_xml_node.c +2410 -0
  19. data/ext/libxml/ruby_xml_node.h +27 -0
  20. data/ext/libxml/ruby_xml_node_set.c +170 -0
  21. data/ext/libxml/ruby_xml_node_set.h +20 -0
  22. data/ext/libxml/ruby_xml_ns.c +153 -0
  23. data/ext/libxml/ruby_xml_ns.h +21 -0
  24. data/ext/libxml/ruby_xml_parser.c +1425 -0
  25. data/ext/libxml/ruby_xml_parser.h +31 -0
  26. data/ext/libxml/ruby_xml_parser_context.c +750 -0
  27. data/ext/libxml/ruby_xml_parser_context.h +22 -0
  28. data/ext/libxml/ruby_xml_reader.c +900 -0
  29. data/ext/libxml/ruby_xml_reader.h +14 -0
  30. data/ext/libxml/ruby_xml_sax_parser.c +485 -0
  31. data/ext/libxml/ruby_xml_sax_parser.h +56 -0
  32. data/ext/libxml/ruby_xml_schema.c +146 -0
  33. data/ext/libxml/ruby_xml_schema.h +16 -0
  34. data/ext/libxml/ruby_xml_state.c +113 -0
  35. data/ext/libxml/ruby_xml_state.h +12 -0
  36. data/ext/libxml/ruby_xml_tree.c +43 -0
  37. data/ext/libxml/ruby_xml_tree.h +12 -0
  38. data/ext/libxml/ruby_xml_xinclude.c +20 -0
  39. data/ext/libxml/ruby_xml_xinclude.h +13 -0
  40. data/ext/libxml/ruby_xml_xpath.c +243 -0
  41. data/ext/libxml/ruby_xml_xpath.h +23 -0
  42. data/ext/libxml/ruby_xml_xpath_context.c +118 -0
  43. data/ext/libxml/ruby_xml_xpath_context.h +20 -0
  44. data/ext/libxml/ruby_xml_xpath_object.c +293 -0
  45. data/ext/libxml/ruby_xml_xpath_object.h +28 -0
  46. data/ext/libxml/ruby_xml_xpointer.c +100 -0
  47. data/ext/libxml/ruby_xml_xpointer.h +27 -0
  48. data/ext/libxml/ruby_xml_xpointer_context.c +21 -0
  49. data/ext/libxml/ruby_xml_xpointer_context.h +18 -0
  50. data/ext/libxml/sax_parser_callbacks.inc +213 -0
  51. data/ext/libxml/version.h +9 -0
  52. data/lib/libxml.rb +125 -0
  53. data/lib/libxml_ruby.so +0 -0
  54. data/lib/xml/libxml.rb +5 -0
  55. data/mingw/libiconv-2.dll +0 -0
  56. data/mingw/libxml2-2.dll +0 -0
  57. data/mingw/libxml_ruby.so +0 -0
  58. data/mingw/mingw.rake +36 -0
  59. data/test/dtd-test.rb +24 -0
  60. data/test/etc_doc_to_s.rb +19 -0
  61. data/test/ets_copy_bug.rb +21 -0
  62. data/test/ets_copy_bug2.rb +32 -0
  63. data/test/ets_copy_bug3.rb +38 -0
  64. data/test/ets_doc_file.rb +15 -0
  65. data/test/ets_doc_to_s.rb +21 -0
  66. data/test/ets_gpx.rb +26 -0
  67. data/test/ets_node_gc.rb +21 -0
  68. data/test/ets_test.xml +2 -0
  69. data/test/ets_tsr.rb +9 -0
  70. data/test/gc.log +0 -0
  71. data/test/merge_bug.rb +55 -0
  72. data/test/schema-test.rb +74 -0
  73. data/test/tc_well_formed.rb +11 -0
  74. data/test/tc_xml_document.rb +52 -0
  75. data/test/tc_xml_document_write.rb +24 -0
  76. data/test/tc_xml_document_write2.rb +54 -0
  77. data/test/tc_xml_document_write3.rb +96 -0
  78. data/test/tc_xml_html_parser.rb +63 -0
  79. data/test/tc_xml_node.rb +59 -0
  80. data/test/tc_xml_node2.rb +25 -0
  81. data/test/tc_xml_node3.rb +27 -0
  82. data/test/tc_xml_node4.rb +86 -0
  83. data/test/tc_xml_node5.rb +52 -0
  84. data/test/tc_xml_node6.rb +27 -0
  85. data/test/tc_xml_node7.rb +35 -0
  86. data/test/tc_xml_node8.rb +32 -0
  87. data/test/tc_xml_node9.rb +32 -0
  88. data/test/tc_xml_node_copy.rb +40 -0
  89. data/test/tc_xml_node_set.rb +24 -0
  90. data/test/tc_xml_node_set2.rb +37 -0
  91. data/test/tc_xml_node_text.rb +17 -0
  92. data/test/tc_xml_node_xlink.rb +28 -0
  93. data/test/tc_xml_parser.rb +190 -0
  94. data/test/tc_xml_parser2.rb +16 -0
  95. data/test/tc_xml_parser3.rb +23 -0
  96. data/test/tc_xml_parser4.rb +33 -0
  97. data/test/tc_xml_parser5.rb +27 -0
  98. data/test/tc_xml_parser6.rb +23 -0
  99. data/test/tc_xml_parser7.rb +28 -0
  100. data/test/tc_xml_parser8.rb +32 -0
  101. data/test/tc_xml_parser9.rb +11 -0
  102. data/test/tc_xml_parser_context.rb +88 -0
  103. data/test/tc_xml_reader.rb +112 -0
  104. data/test/tc_xml_sax_parser.rb +104 -0
  105. data/test/tc_xml_sax_parser2.rb +51 -0
  106. data/test/tc_xml_xinclude.rb +30 -0
  107. data/test/tc_xml_xpath.rb +38 -0
  108. data/test/tc_xml_xpath2.rb +14 -0
  109. data/test/tc_xml_xpointer.rb +78 -0
  110. data/vc/libxml.sln +20 -0
  111. data/vc/libxml.vcproj +389 -0
  112. data/work/Rakefile +247 -0
  113. data/work/task/make +26 -0
  114. data/work/task/memory +37 -0
  115. data/work/task/rdoc +39 -0
  116. data/work/task/setup +1616 -0
  117. data/work/task/test +29 -0
  118. data/work/test/ets_runner.rb +33 -0
  119. data/work/test/libxml_test.rb +3 -0
  120. data/work/test/runner.rb +0 -0
  121. data/work/test/runner_ets.rb +33 -0
  122. data/work/vc/debug/libxml.exp +0 -0
  123. data/work/vc/debug/libxml.ilk +0 -0
  124. data/work/vc/debug/libxml.lib +0 -0
  125. data/work/vc/debug/libxml.pdb +0 -0
  126. data/work/vc/debug/libxml.so +0 -0
  127. metadata +224 -0
@@ -0,0 +1,29 @@
1
+ /* $Id: ruby_xml_html_parser.h 111 2006-11-20 01:39:14Z roscopeco $ */
2
+
3
+ /* Please see the LICENSE file for copyright and distribution information */
4
+
5
+ #ifndef __RUBY_XML_HTML_PARSER__
6
+ #define __RUBY_XML_HTML_PARSER__
7
+
8
+ extern int ruby_xml_html_parser_count;
9
+ extern VALUE cXMLHTMLParser;
10
+
11
+ typedef struct ruby_xml_html_parser {
12
+ VALUE ctxt;
13
+ int parsed;
14
+ void *data;
15
+ int data_type;
16
+ } ruby_xml_html_parser;
17
+
18
+ /*
19
+ * VALUE ruby_xml_html_parser_filename_get(VALUE self);
20
+ VALUE ruby_xml_html_parser_filename_set(VALUE self, VALUE filename);
21
+ VALUE ruby_xml_html_parser_new(VALUE class);
22
+ */
23
+ VALUE ruby_xml_html_parser_parse(VALUE self);
24
+ VALUE ruby_xml_html_parser_str_get(VALUE self);
25
+ VALUE ruby_xml_html_parser_str_set(VALUE self, VALUE str);
26
+
27
+ void ruby_init_html_parser(void);
28
+
29
+ #endif
@@ -0,0 +1,158 @@
1
+
2
+ /* ruby support for custom scheme handlers */
3
+ /* Author: Martin Povolny (xpovolny@fi.muni.cz) */
4
+
5
+ #include "ruby_libxml.h"
6
+ #include "ruby_xml_input_cbg.h"
7
+
8
+ static ic_scheme *first_scheme = 0;
9
+
10
+ int ic_match (char const *filename) {
11
+ ic_scheme *scheme;
12
+
13
+ //fprintf( stderr, "ic_match: %s\n", filename );
14
+
15
+ scheme = first_scheme;
16
+ while (0 != scheme) {
17
+ if (!xmlStrncasecmp(BAD_CAST filename, BAD_CAST scheme->scheme_name, scheme->name_len)) {
18
+ return 1;
19
+ }
20
+ scheme = scheme->next_scheme;
21
+ }
22
+ return 0;
23
+ }
24
+
25
+ void* ic_open (char const *filename) {
26
+ ic_doc_context *ic_doc;
27
+ ic_scheme *scheme;
28
+ VALUE res;
29
+
30
+ scheme = first_scheme;
31
+ while (0 != scheme) {
32
+ if (!xmlStrncasecmp(BAD_CAST filename, BAD_CAST scheme->scheme_name, scheme->name_len)) {
33
+ ic_doc = (ic_doc_context*)malloc( sizeof(ic_doc_context) );
34
+
35
+ res = rb_funcall( scheme->class,
36
+ rb_intern("document_query"),
37
+ 1,
38
+ rb_str_new2(filename) );
39
+
40
+ ic_doc->buffer = strdup( StringValuePtr(res) );
41
+
42
+ ic_doc->bpos = ic_doc->buffer;
43
+ ic_doc->remaining = strlen(ic_doc->buffer);
44
+ return ic_doc;
45
+ }
46
+ scheme = scheme->next_scheme;
47
+ }
48
+ return 0;
49
+ }
50
+
51
+ int ic_read (void *context, char *buffer, int len) {
52
+ ic_doc_context *ic_doc;
53
+ int ret_len;
54
+ ic_doc = (ic_doc_context*)context;
55
+
56
+ if (len >= ic_doc->remaining) {
57
+ ret_len = ic_doc->remaining;
58
+ } else {
59
+ ret_len = len;
60
+ }
61
+ ic_doc->remaining -= ret_len;
62
+ strncpy( buffer, ic_doc->bpos, ret_len );
63
+ ic_doc->bpos += ret_len;
64
+
65
+ return ret_len;
66
+ }
67
+
68
+ int ic_close (void *context) {
69
+ ruby_xfree( ((ic_doc_context*)context)->buffer );
70
+ ruby_xfree( context );
71
+ return 1;
72
+ }
73
+
74
+ VALUE input_callbacks_register_input_callbacks() {
75
+ xmlRegisterInputCallbacks( ic_match, ic_open, ic_read, ic_close );
76
+ return(Qtrue);
77
+ }
78
+
79
+ VALUE
80
+ input_callbacks_add_scheme (VALUE self, VALUE scheme_name, VALUE class) {
81
+ ic_scheme *scheme;
82
+
83
+ Check_Type(scheme_name, T_STRING);
84
+
85
+ scheme = (ic_scheme*)malloc(sizeof(ic_scheme));
86
+ scheme->next_scheme = 0;
87
+ scheme->scheme_name = strdup(StringValuePtr(scheme_name)); /* TODO alloc, dealloc */
88
+ scheme->name_len = strlen(scheme->scheme_name);
89
+ scheme->class = class; /* TODO alloc, dealloc */
90
+
91
+ //fprintf( stderr, "registered: %s, %d, %s\n", scheme->scheme_name, scheme->name_len, scheme->class );
92
+
93
+ if (0 == first_scheme)
94
+ first_scheme = scheme;
95
+ else {
96
+ ic_scheme *pos;
97
+ pos = first_scheme;
98
+ while (0 != pos->next_scheme)
99
+ pos = pos->next_scheme;
100
+ pos->next_scheme = scheme;
101
+ }
102
+
103
+ return(Qtrue);
104
+ }
105
+
106
+ VALUE
107
+ input_callbacks_remove_scheme (VALUE self, VALUE scheme_name) {
108
+ char *name;
109
+ ic_scheme *save_scheme, *scheme;
110
+
111
+ Check_Type(scheme_name, T_STRING);
112
+ name = StringValuePtr(scheme_name);
113
+
114
+ if (0 == first_scheme)
115
+ return Qfalse;
116
+
117
+ /* check the first one */
118
+ if (!strncmp(name, first_scheme->scheme_name, first_scheme->name_len)) {
119
+ save_scheme = first_scheme->next_scheme;
120
+
121
+ ruby_xfree(first_scheme->scheme_name);
122
+ ruby_xfree(first_scheme);
123
+
124
+ first_scheme = save_scheme;
125
+ return Qtrue;
126
+ }
127
+
128
+ scheme = first_scheme;
129
+ while (0 != scheme->next_scheme) {
130
+ if ( !strncmp( name, scheme->next_scheme->scheme_name, scheme->next_scheme->name_len ) ) {
131
+ save_scheme = scheme->next_scheme->next_scheme;
132
+
133
+ ruby_xfree(scheme->next_scheme->scheme_name);
134
+ ruby_xfree(scheme->next_scheme);
135
+
136
+ scheme->next_scheme = save_scheme;
137
+ return Qtrue;
138
+ }
139
+ scheme = scheme->next_scheme;
140
+ }
141
+ return Qfalse;
142
+ }
143
+
144
+ // Rdoc needs to know
145
+ #ifdef RDOC_NEVER_DEFINED
146
+ mXML = rb_define_module("XML");
147
+ #endif
148
+
149
+ void
150
+ ruby_init_input_callbacks(void) {
151
+ VALUE cInputCallbacks;
152
+ cInputCallbacks = rb_define_class_under(mXML, "InputCallbacks", rb_cObject);
153
+
154
+ /* Class Methods */
155
+ rb_define_singleton_method(cInputCallbacks, "register", input_callbacks_register_input_callbacks, 0);
156
+ rb_define_singleton_method(cInputCallbacks, "add_scheme", input_callbacks_add_scheme, 2);
157
+ rb_define_singleton_method(cInputCallbacks, "remove_scheme", input_callbacks_remove_scheme, 1);
158
+ }
@@ -0,0 +1,20 @@
1
+ #ifndef _INPUT_CBG_
2
+ #define _INPUT_CBG_
3
+
4
+ void ruby_init_input_callbacks(void);
5
+
6
+ typedef struct ic_doc_context {
7
+ char *buffer;
8
+ char *bpos;
9
+ int remaining;
10
+ } ic_doc_context;
11
+
12
+ typedef struct ic_scheme {
13
+ char *scheme_name;
14
+ VALUE class;
15
+ int name_len;
16
+
17
+ struct ic_scheme *next_scheme;
18
+ } ic_scheme;
19
+
20
+ #endif
@@ -0,0 +1,2410 @@
1
+ /* $Id: ruby_xml_node.c 300 2008-07-01 19:14:15Z cfis $ */
2
+
3
+ /* Please see the LICENSE file for copyright and distribution information */
4
+
5
+ #include "ruby_libxml.h"
6
+ #include "ruby_xml_node.h"
7
+
8
+ VALUE cXMLNode;
9
+ VALUE eXMLNodeSetNamespace;
10
+ VALUE eXMLNodeFailedModify;
11
+ VALUE eXMLNodeUnknownType;
12
+
13
+ static VALUE
14
+ check_string_or_symbol( VALUE val ) {
15
+ if( TYPE(val) != T_STRING && TYPE(val) != T_SYMBOL ) {
16
+ rb_raise(rb_eTypeError, "wrong argument type %s (expected String or Symbol)",
17
+ rb_obj_classname(val) );
18
+ }
19
+ return rb_obj_as_string( val );
20
+ }
21
+
22
+ /*
23
+ * call-seq:
24
+ * node.attribute? => (true|false)
25
+ *
26
+ * Determine whether this is an attribute node,
27
+ */
28
+ VALUE
29
+ ruby_xml_node_attribute_q(VALUE self) {
30
+ ruby_xml_node *rxn;
31
+ Data_Get_Struct(self, ruby_xml_node, rxn);
32
+ if (rxn->node->type == XML_ATTRIBUTE_NODE)
33
+ return(Qtrue);
34
+ else
35
+ return(Qfalse);
36
+ }
37
+
38
+
39
+ /*
40
+ * call-seq:
41
+ * node.attribute_decl? => (true|false)
42
+ *
43
+ * Determine whether this is an attribute declaration node,
44
+ */
45
+ VALUE
46
+ ruby_xml_node_attribute_decl_q(VALUE self) {
47
+ ruby_xml_node *rxn;
48
+ Data_Get_Struct(self, ruby_xml_node, rxn);
49
+ if (rxn->node->type == XML_ATTRIBUTE_DECL)
50
+ return(Qtrue);
51
+ else
52
+ return(Qfalse);
53
+ }
54
+
55
+
56
+ /*
57
+ * call-seq:
58
+ * node.base => "uri"
59
+ *
60
+ * Obtain this node's base URI.
61
+ */
62
+ VALUE
63
+ ruby_xml_node_base_get(VALUE self) {
64
+ ruby_xml_node *rxn;
65
+ xmlChar* base_uri;
66
+ VALUE result = Qnil;
67
+
68
+ Data_Get_Struct(self, ruby_xml_node, rxn);
69
+
70
+ if (rxn->node->doc == NULL)
71
+ return(result);
72
+
73
+ base_uri = xmlNodeGetBase(rxn->node->doc, rxn->node);
74
+ if (base_uri) {
75
+ result = rb_str_new2((const char*)base_uri);
76
+ xmlFree(base_uri);
77
+ }
78
+
79
+ return(result);
80
+ }
81
+
82
+
83
+ // TODO node_base_set should support setting back to nil
84
+
85
+ /*
86
+ * call-seq:
87
+ * node.base = "uri"
88
+ *
89
+ * Set this node's base URI.
90
+ */
91
+ VALUE
92
+ ruby_xml_node_base_set(VALUE self, VALUE uri) {
93
+ ruby_xml_node *node;
94
+
95
+ Check_Type(uri, T_STRING);
96
+ Data_Get_Struct(self, ruby_xml_node, node);
97
+ if (node->node->doc == NULL)
98
+ return(Qnil);
99
+
100
+ xmlNodeSetBase(node->node, (xmlChar*)StringValuePtr(uri));
101
+ return(Qtrue);
102
+ }
103
+
104
+
105
+ /*
106
+ * call-seq:
107
+ * node.cdata? => (true|false)
108
+ *
109
+ * Determine whether this is a #CDATA node
110
+ */
111
+ VALUE
112
+ ruby_xml_node_cdata_q(VALUE self) {
113
+ ruby_xml_node *rxn;
114
+ Data_Get_Struct(self, ruby_xml_node, rxn);
115
+ if (rxn->node->type == XML_CDATA_SECTION_NODE)
116
+ return(Qtrue);
117
+ else
118
+ return(Qfalse);
119
+ }
120
+
121
+
122
+ /*
123
+ * call-seq:
124
+ * node.comment? => (true|false)
125
+ *
126
+ * Determine whether this is a comment node
127
+ */
128
+ VALUE
129
+ ruby_xml_node_comment_q(VALUE self) {
130
+ ruby_xml_node *rxn;
131
+ Data_Get_Struct(self, ruby_xml_node, rxn);
132
+ if (rxn->node->type == XML_COMMENT_NODE)
133
+ return(Qtrue);
134
+ else
135
+ return(Qfalse);
136
+ }
137
+
138
+
139
+ /*
140
+ * call-seq:
141
+ * node << ("string" | node) => node
142
+ *
143
+ * Add the specified string or XML::Node to this node's
144
+ * content.
145
+ */
146
+ VALUE
147
+ ruby_xml_node_content_add(VALUE self, VALUE obj) {
148
+ ruby_xml_node *node;
149
+ VALUE str;
150
+
151
+ Data_Get_Struct(self, ruby_xml_node, node);
152
+ /* XXX This should only be legal for a CDATA type node, I think,
153
+ * resulting in a merge of content, as if a string were passed
154
+ * danj 070827
155
+ */
156
+ if (rb_obj_is_kind_of(obj, cXMLNode)) {
157
+ ruby_xml_node_child_set(self, obj);
158
+ return(self);
159
+ } else if (TYPE(obj) == T_STRING) {
160
+ xmlNodeAddContent(node->node, (xmlChar*)StringValuePtr(obj));
161
+ return(self);
162
+ } else {
163
+ str = rb_obj_as_string(obj);
164
+ if (NIL_P(str) || TYPE(str) != T_STRING)
165
+ rb_raise(rb_eTypeError, "invalid argument: must be string or XML::Node");
166
+
167
+ xmlNodeAddContent(node->node, (xmlChar*)StringValuePtr(str));
168
+ return(self);
169
+ }
170
+ }
171
+
172
+
173
+ /*
174
+ * call-seq:
175
+ * node.content => "string"
176
+ *
177
+ * Obtain this node's content as a string.
178
+ */
179
+ VALUE
180
+ ruby_xml_node_content_get(VALUE self) {
181
+ ruby_xml_node *rxn;
182
+ xmlChar *content;
183
+ VALUE result;
184
+
185
+ Data_Get_Struct(self, ruby_xml_node, rxn);
186
+ content = xmlNodeGetContent(rxn->node);
187
+ if (content) {
188
+ result = rb_str_new2((const char *) content);
189
+ xmlFree(content);
190
+ }
191
+
192
+ return result;
193
+ }
194
+
195
+ /*
196
+ * call-seq:
197
+ * node.content = "string"
198
+ *
199
+ * Set this node's content to the specified string.
200
+ */
201
+ VALUE
202
+ ruby_xml_node_content_set(VALUE self, VALUE content) {
203
+ ruby_xml_node *node;
204
+
205
+ Check_Type(content, T_STRING);
206
+ Data_Get_Struct(self, ruby_xml_node, node);
207
+ // XXX docs indicate need for escaping entites, need to be done? danj
208
+ xmlNodeSetContent(node->node, (xmlChar*)StringValuePtr(content));
209
+ return(Qtrue);
210
+ }
211
+
212
+
213
+ /*
214
+ * call-seq:
215
+ * node.content_stripped => "string"
216
+ *
217
+ * Obtain this node's stripped content.
218
+ *
219
+ * *Deprecated*: Stripped content can be obtained via the
220
+ * +content+ method.
221
+ */
222
+ VALUE
223
+ ruby_xml_node_content_stripped_get(VALUE self) {
224
+ ruby_xml_node *rxn;
225
+ xmlChar* content;
226
+ VALUE result = Qnil;
227
+
228
+ Data_Get_Struct(self, ruby_xml_node, rxn);
229
+
230
+ if (!rxn->node->content)
231
+ return result;
232
+
233
+ content = xmlNodeGetContent(rxn->node);
234
+ if (content) {
235
+ result = rb_str_new2((const char*)content);
236
+ xmlFree(content);
237
+ }
238
+ return(result);
239
+ }
240
+
241
+ /*
242
+ * call-seq:
243
+ * node.child => node
244
+ *
245
+ * Obtain this node's first child node, if any.
246
+ */
247
+ VALUE
248
+ ruby_xml_node_child_get(VALUE self) {
249
+ ruby_xml_node *node;
250
+ xmlNodePtr tmp;
251
+
252
+ Data_Get_Struct(self, ruby_xml_node, node);
253
+
254
+ switch (node->node->type) {
255
+ case XML_ELEMENT_NODE:
256
+ case XML_ENTITY_REF_NODE:
257
+ case XML_ENTITY_NODE:
258
+ case XML_PI_NODE:
259
+ case XML_COMMENT_NODE:
260
+ case XML_DOCUMENT_NODE:
261
+ #ifdef LIBXML_DOCB_ENABLED
262
+ case XML_DOCB_DOCUMENT_NODE:
263
+ #endif
264
+ case XML_HTML_DOCUMENT_NODE:
265
+ case XML_DTD_NODE:
266
+ tmp = node->node->children;
267
+ break;
268
+ case XML_ATTRIBUTE_NODE:
269
+ {
270
+ xmlAttrPtr attr = (xmlAttrPtr) node->node;
271
+ tmp = attr->children;
272
+ break;
273
+ }
274
+ default:
275
+ tmp = NULL;
276
+ break;
277
+ }
278
+
279
+ if (tmp == NULL)
280
+ return(Qnil);
281
+ else
282
+ return(ruby_xml_node2_wrap(cXMLNode, tmp));
283
+ }
284
+
285
+
286
+ /*
287
+ * call-seq:
288
+ * node.child? => (true|false)
289
+ *
290
+ * Determine whether this node has at least one child.
291
+ */
292
+ VALUE
293
+ ruby_xml_node_child_q(VALUE self) {
294
+ ruby_xml_node *rxn;
295
+ xmlNodePtr node;
296
+ Data_Get_Struct(self, ruby_xml_node, rxn);
297
+
298
+ node = NULL;
299
+ switch (rxn->node->type) {
300
+ case XML_ELEMENT_NODE:
301
+ case XML_ENTITY_REF_NODE:
302
+ case XML_ENTITY_NODE:
303
+ case XML_PI_NODE:
304
+ case XML_COMMENT_NODE:
305
+ case XML_DOCUMENT_NODE:
306
+ #ifdef LIBXML_DOCB_ENABLED
307
+ case XML_DOCB_DOCUMENT_NODE:
308
+ #endif
309
+ case XML_HTML_DOCUMENT_NODE:
310
+ case XML_DTD_NODE:
311
+ node = rxn->node->children;
312
+ break;
313
+ case XML_ATTRIBUTE_NODE:
314
+ {
315
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
316
+ node = attr->children;
317
+ break;
318
+ }
319
+ default:
320
+ node = NULL;
321
+ }
322
+
323
+ if (node == NULL)
324
+ return(Qfalse);
325
+ else
326
+ return(Qtrue);
327
+ }
328
+
329
+ /*
330
+ * underlying for child_set and child_add, difference being
331
+ * former raises on implicit copy, latter does not.
332
+ */
333
+ VALUE
334
+ ruby_xml_node_child_set_aux(VALUE self, VALUE rnode, int do_raise) {
335
+ ruby_xml_node *cnode, *pnode;
336
+ xmlNodePtr chld, ret;
337
+ int copied=0;
338
+
339
+ if (rb_obj_is_kind_of(rnode, cXMLNode) == Qfalse)
340
+ rb_raise(rb_eTypeError, "Must pass an XML::Node object");
341
+
342
+ Data_Get_Struct(self, ruby_xml_node, pnode);
343
+ Data_Get_Struct(rnode, ruby_xml_node, cnode);
344
+
345
+ chld = cnode->node;
346
+ /* Since an add operation may destroy a textnode by merging, we need to work
347
+ * with a copy, so that the ruby instance is not left with a dangling reference
348
+ */
349
+ if ( chld->type == XML_TEXT_NODE ) {
350
+ chld = xmlCopyNode(chld,1);
351
+ copied=1;
352
+ }
353
+
354
+ if ( chld->parent != NULL || chld->doc != NULL ) {
355
+ /* raise before copying if applicable */
356
+ if ( do_raise == 1 )
357
+ rb_raise(rb_eRuntimeError, "implicit copy not legal for child= or <<");
358
+ chld=xmlCopyNode(chld,1);
359
+ copied=1;
360
+ }
361
+
362
+ ret = xmlAddChild(pnode->node, chld);
363
+ if (ret == NULL) {
364
+ if ( copied == 1 )
365
+ xmlFreeNode(chld);
366
+ rb_raise(eXMLNodeFailedModify, "unable to add a child to the document");
367
+ } else if ( ret==chld ) {
368
+ /* child was added whole to parent and we need to return it as a new object */
369
+ return ruby_xml_node2_wrap(cXMLNode,chld);
370
+ }
371
+ /* else */
372
+ /* If it was a text node, then ret should be parent->last, so we will just return ret. */
373
+ return ruby_xml_node2_wrap(cXMLNode,ret);
374
+ }
375
+
376
+ /*
377
+ * call-seq:
378
+ * node.child = node
379
+ *
380
+ * Set a child node for this node. Also called for <<
381
+ */
382
+ VALUE
383
+ ruby_xml_node_child_set(VALUE self, VALUE rnode) {
384
+ return ruby_xml_node_child_set_aux(self,rnode,1);
385
+ }
386
+
387
+ /*
388
+ * call-seq:
389
+ * node.child_add(node)
390
+ *
391
+ * Set a child node for this node.
392
+ */
393
+ VALUE
394
+ ruby_xml_node_child_add(VALUE self, VALUE rnode) {
395
+ return ruby_xml_node_child_set_aux(self,rnode,0);
396
+ }
397
+
398
+ /*
399
+ * call-seq:
400
+ * node.doc => document
401
+ *
402
+ * Obtain the XML::Document this node belongs to.
403
+ */
404
+ VALUE
405
+ ruby_xml_node_doc(VALUE self) {
406
+ ruby_xml_node *rxn;
407
+ xmlDocPtr doc=NULL;
408
+
409
+ Data_Get_Struct(self, ruby_xml_node, rxn);
410
+
411
+ switch (rxn->node->type) {
412
+ case XML_DOCUMENT_NODE:
413
+ #ifdef LIBXML_DOCB_ENABLED
414
+ case XML_DOCB_DOCUMENT_NODE:
415
+ #endif
416
+ case XML_HTML_DOCUMENT_NODE:
417
+ doc = NULL;
418
+ break;
419
+ case XML_ATTRIBUTE_NODE:
420
+ {
421
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
422
+ doc = attr->doc;
423
+ break;
424
+ }
425
+ case XML_NAMESPACE_DECL:
426
+ doc = NULL;
427
+ break;
428
+ default:
429
+ doc = rxn->node->doc;
430
+ break;
431
+ }
432
+
433
+ if (doc == NULL)
434
+ return(Qnil);
435
+
436
+ if ( doc->_private == NULL )
437
+ rb_raise(rb_eRuntimeError,"existing document object has no ruby-instance");
438
+
439
+ return (VALUE)doc->_private;
440
+ }
441
+
442
+
443
+ /*
444
+ * call-seq:
445
+ * node.docbook? => (true|false)
446
+ *
447
+ * Determine whether this is a docbook node.
448
+ */
449
+ VALUE
450
+ ruby_xml_node_docbook_doc_q(VALUE self) {
451
+ #ifdef LIBXML_DOCB_ENABLED
452
+ ruby_xml_node *rxn;
453
+ Data_Get_Struct(self, ruby_xml_node, rxn);
454
+ if (rxn->node->type == XML_DOCB_DOCUMENT_NODE)
455
+ return(Qtrue);
456
+ else
457
+ return(Qfalse);
458
+ #else
459
+ rb_warn("libxml compiled without docbook support");
460
+ return(Qfalse);
461
+ #endif
462
+ }
463
+
464
+
465
+ /*
466
+ * call-seq:
467
+ * node.doctype? => (true|false)
468
+ *
469
+ * Determine whether this is a DOCTYPE node.
470
+ */
471
+ VALUE
472
+ ruby_xml_node_doctype_q(VALUE self) {
473
+ ruby_xml_node *rxn;
474
+ Data_Get_Struct(self, ruby_xml_node, rxn);
475
+ if (rxn->node->type == XML_DOCUMENT_TYPE_NODE)
476
+ return(Qtrue);
477
+ else
478
+ return(Qfalse);
479
+ }
480
+
481
+
482
+ /*
483
+ * call-seq:
484
+ * node.document? => (true|false)
485
+ *
486
+ * Determine whether this is a document node.
487
+ */
488
+ VALUE
489
+ ruby_xml_node_document_q(VALUE self) {
490
+ ruby_xml_node *rxn;
491
+ Data_Get_Struct(self, ruby_xml_node, rxn);
492
+ if (rxn->node->type == XML_DOCUMENT_NODE)
493
+ return(Qtrue);
494
+ else
495
+ return(Qfalse);
496
+ }
497
+
498
+
499
+ /*
500
+ * call-seq:
501
+ * node.dtd? => (true|false)
502
+ *
503
+ * Determine whether this is a DTD node.
504
+ */
505
+ VALUE
506
+ ruby_xml_node_dtd_q(VALUE self) {
507
+ ruby_xml_node *rxn;
508
+ Data_Get_Struct(self, ruby_xml_node, rxn);
509
+ if (rxn->node->type == XML_DTD_NODE)
510
+ return(Qtrue);
511
+ else
512
+ return(Qfalse);
513
+ }
514
+
515
+
516
+ /*
517
+ * call-seq:
518
+ * node.dump => (true|nil)
519
+ *
520
+ * Dump this node to stdout.
521
+ */
522
+ VALUE
523
+ ruby_xml_node_dump(VALUE self) {
524
+ ruby_xml_node *rxn;
525
+ xmlBufferPtr buf;
526
+
527
+ Data_Get_Struct(self, ruby_xml_node, rxn);
528
+
529
+ if (rxn->node->doc == NULL)
530
+ return(Qnil);
531
+
532
+ buf = xmlBufferCreate();
533
+ xmlNodeDump(buf, rxn->node->doc, rxn->node, 0, 1);
534
+ xmlBufferDump(stdout, buf);
535
+ xmlBufferFree(buf);
536
+ return(Qtrue);
537
+ }
538
+
539
+
540
+ /*
541
+ * call-seq:
542
+ * node.debug_dump => (true|nil)
543
+ *
544
+ * Dump this node to stdout, including any debugging
545
+ * information.
546
+ */
547
+ VALUE
548
+ ruby_xml_node_debug_dump(VALUE self) {
549
+ ruby_xml_node *rxn;
550
+ Data_Get_Struct(self, ruby_xml_node, rxn);
551
+
552
+ if (rxn->node->doc == NULL)
553
+ return(Qnil);
554
+
555
+ xmlElemDump(stdout, rxn->node->doc, rxn->node);
556
+ return(Qtrue);
557
+ }
558
+
559
+
560
+ /*
561
+ * call-seq:
562
+ * node.element? => (true|false)
563
+ *
564
+ * Determine whether this is an element node.
565
+ */
566
+ VALUE
567
+ ruby_xml_node_element_q(VALUE self) {
568
+ ruby_xml_node *rxn;
569
+ Data_Get_Struct(self, ruby_xml_node, rxn);
570
+ if (rxn->node->type == XML_ELEMENT_NODE)
571
+ return(Qtrue);
572
+ else
573
+ return(Qfalse);
574
+ }
575
+
576
+
577
+ /*
578
+ * call-seq:
579
+ * node.element_decl? => (true|false)
580
+ *
581
+ * Determine whether this is an element declaration node.
582
+ */
583
+ VALUE
584
+ ruby_xml_node_element_decl_q(VALUE self) {
585
+ ruby_xml_node *rxn;
586
+ Data_Get_Struct(self, ruby_xml_node, rxn);
587
+ if (rxn->node->type == XML_ELEMENT_DECL)
588
+ return(Qtrue);
589
+ else
590
+ return(Qfalse);
591
+ }
592
+
593
+
594
+ /*
595
+ * call-seq:
596
+ * node.empty? => (true|false)
597
+ *
598
+ * Determine whether this node is empty.
599
+ */
600
+ VALUE
601
+ ruby_xml_node_empty_q(VALUE self) {
602
+ ruby_xml_node *rxn;
603
+ Data_Get_Struct(self, ruby_xml_node, rxn);
604
+ if (rxn->node == NULL)
605
+ return(Qnil);
606
+
607
+ return((xmlIsBlankNode(rxn->node) == 1) ? Qtrue : Qfalse);
608
+ }
609
+
610
+
611
+ /*
612
+ * call-seq:
613
+ * node.entity? => (true|false)
614
+ *
615
+ * Determine whether this is an entity node.
616
+ */
617
+ VALUE
618
+ ruby_xml_node_entity_q(VALUE self) {
619
+ ruby_xml_node *rxn;
620
+ Data_Get_Struct(self, ruby_xml_node, rxn);
621
+ if (rxn->node->type == XML_ENTITY_NODE)
622
+ return(Qtrue);
623
+ else
624
+ return(Qfalse);
625
+ }
626
+
627
+
628
+ /*
629
+ * call-seq:
630
+ * node.entity_ref? => (true|false)
631
+ *
632
+ * Determine whether this is an entity reference node.
633
+ */
634
+ VALUE
635
+ ruby_xml_node_entity_ref_q(VALUE self) {
636
+ ruby_xml_node *rxn;
637
+ Data_Get_Struct(self, ruby_xml_node, rxn);
638
+ if (rxn->node->type == XML_ENTITY_REF_NODE)
639
+ return(Qtrue);
640
+ else
641
+ return(Qfalse);
642
+ }
643
+
644
+ VALUE ruby_xml_node_to_s(VALUE self);
645
+
646
+ /*
647
+ * call-seq:
648
+ * node.eql?(other_node) => (true|false)
649
+ *
650
+ * Test equality between the two nodes. Equality is determined based
651
+ * on the XML representation of the nodes.
652
+ */
653
+ VALUE
654
+ ruby_xml_node_eql_q(VALUE self, VALUE other) {
655
+ // TODO this isn't the best way to handle this
656
+ ruby_xml_node *rxn, *orxn;
657
+ VALUE thisxml, otherxml;
658
+ Data_Get_Struct(self, ruby_xml_node, rxn);
659
+ Data_Get_Struct(other, ruby_xml_node, orxn);
660
+ thisxml = ruby_xml_node_to_s(self);
661
+ otherxml = ruby_xml_node_to_s(other);
662
+
663
+ return(rb_funcall(thisxml, rb_intern("=="), 1, otherxml));
664
+ }
665
+
666
+
667
+ /*
668
+ * call-seq:
669
+ * node.find(xpath_expr, namespace = [any]) => nodeset
670
+ *
671
+ * Find nodes matching the specified xpath expression, optionally
672
+ * using the specified namespaces. Returns an XML::Node::Set.
673
+ */
674
+ VALUE
675
+ ruby_xml_node_find(int argc, VALUE *argv, VALUE self) {
676
+ if (argc > 2 || argc < 1)
677
+ rb_raise(rb_eArgError, "wrong number of arguments (need 1 or 2)");
678
+
679
+ return(ruby_xml_xpath_find2(self,argv[0],(argc==2)?argv[1]:Qnil));
680
+ }
681
+
682
+ /*
683
+ * call-seq:
684
+ * node.find_first(xpath_expr, namespace = [any]) => nodeset
685
+ *
686
+ * Find the first node matching the specified xpath expression, optionally
687
+ * using the specified namespaces. Returns an XML::Node.
688
+ */
689
+ VALUE
690
+ ruby_xml_node_find_first(int argc, VALUE *argv, VALUE self) {
691
+ return ruby_xml_xpath_object_first(ruby_xml_node_find(argc, argv, self));
692
+ }
693
+
694
+
695
+ /*
696
+ * call-seq:
697
+ * node.fragment? => (true|false)
698
+ *
699
+ * Determine whether this node is a fragment.
700
+ */
701
+ VALUE
702
+ ruby_xml_node_fragment_q(VALUE self) {
703
+ ruby_xml_node *rxn;
704
+ Data_Get_Struct(self, ruby_xml_node, rxn);
705
+ if (rxn->node->type == XML_DOCUMENT_FRAG_NODE)
706
+ return(Qtrue);
707
+ else
708
+ return(Qfalse);
709
+ }
710
+
711
+ /*
712
+ * call-seq:
713
+ * node.hash => fixnum
714
+ *
715
+ * Returns the hash-code for this node. This is the hash of the XML
716
+ * representation in order to be consistent with eql.
717
+ */
718
+ VALUE
719
+ ruby_xml_node_hash(VALUE self) {
720
+ ruby_xml_node *rxn;
721
+ VALUE thisxml;
722
+ Data_Get_Struct(self, ruby_xml_node, rxn);
723
+ thisxml = ruby_xml_node_to_s(self);
724
+
725
+ return(rb_funcall(thisxml, rb_intern("hash"), 0));
726
+ }
727
+
728
+
729
+ /*
730
+ * call-seq:
731
+ * node.html_doc? => (true|false)
732
+ *
733
+ * Determine whether this node is an html document node.
734
+ */
735
+ VALUE
736
+ ruby_xml_node_html_doc_q(VALUE self) {
737
+ ruby_xml_node *rxn;
738
+ Data_Get_Struct(self, ruby_xml_node, rxn);
739
+ if (rxn->node->type == XML_HTML_DOCUMENT_NODE)
740
+ return(Qtrue);
741
+ else
742
+ return(Qfalse);
743
+ }
744
+
745
+ /*
746
+ * call-seq:
747
+ * XML::Node.new_cdata(content = nil) => node
748
+ *
749
+ * Create a new #CDATA node, optionally setting
750
+ * the node's content.
751
+ */
752
+ VALUE
753
+ ruby_xml_node_new_cdata(int argc, VALUE *argv, VALUE class) {
754
+ xmlNodePtr xnode;
755
+ VALUE str=Qnil;
756
+
757
+ switch(argc) {
758
+ case 1:
759
+ str = argv[0];
760
+ Check_Type(str, T_STRING);
761
+ if (!NIL_P(str)) {
762
+ xnode = xmlNewCDataBlock(NULL, (xmlChar*)StringValuePtr(str), xmlStrlen((xmlChar*)StringValuePtr(str)));
763
+ } else {
764
+ xnode = xmlNewCDataBlock(NULL, NULL , 0);
765
+ }
766
+
767
+ if (xnode == NULL)
768
+ return(Qnil);
769
+
770
+ return ruby_xml_node2_wrap(class,xnode);
771
+
772
+ default:
773
+ rb_raise(rb_eArgError, "wrong number of arguments (1)");
774
+ }
775
+
776
+ // not reached
777
+ return(Qnil);
778
+ }
779
+
780
+
781
+ /*
782
+ * call-seq:
783
+ * XML::Node.new_comment(content = nil) => node
784
+ *
785
+ * Create a new comment node, optionally setting
786
+ * the node's content.
787
+ *
788
+ */
789
+ VALUE
790
+ ruby_xml_node_new_comment(int argc, VALUE *argv, VALUE class) {
791
+ xmlNodePtr xnode;
792
+ VALUE str=Qnil;
793
+
794
+ switch(argc) {
795
+ case 1:
796
+ str = argv[0];
797
+ Check_Type(str, T_STRING);
798
+ // TODO xmlNewComment wrongly? adds \n before and after the comment
799
+ if (!NIL_P(str)) {
800
+ xnode = xmlNewComment((xmlChar*)StringValuePtr(str));
801
+ } else {
802
+ xnode = xmlNewComment(NULL);
803
+ }
804
+
805
+ if (xnode == NULL)
806
+ return(Qnil);
807
+
808
+ return ruby_xml_node2_wrap(class,xnode);
809
+
810
+ default:
811
+ rb_raise(rb_eArgError, "wrong number of arguments (1)");
812
+ }
813
+
814
+ // not reached
815
+ return(Qnil);
816
+ }
817
+
818
+
819
+ /*
820
+ * call-seq:
821
+ * node.lang => "string"
822
+ *
823
+ * Obtain the language set for this node, if any.
824
+ * This is set in XML via the xml:lang attribute.
825
+ */
826
+ VALUE
827
+ ruby_xml_node_lang_get(VALUE self) {
828
+ ruby_xml_node *rxn;
829
+ xmlChar *lang;
830
+ VALUE result = Qnil;
831
+
832
+ Data_Get_Struct(self, ruby_xml_node, rxn);
833
+ lang = xmlNodeGetLang(rxn->node);
834
+
835
+ if (lang) {
836
+ result = rb_str_new2((const char*)lang);
837
+ xmlFree(lang);
838
+ }
839
+
840
+ return(result);
841
+ }
842
+
843
+
844
+ // TODO node_lang_set should support setting back to nil
845
+
846
+ /*
847
+ * call-seq:
848
+ * node.lang = "string"
849
+ *
850
+ * Set the language for this node. This affects the value
851
+ * of the xml:lang attribute.
852
+ */
853
+ VALUE
854
+ ruby_xml_node_lang_set(VALUE self, VALUE lang) {
855
+ ruby_xml_node *node;
856
+
857
+ Check_Type(lang, T_STRING);
858
+ Data_Get_Struct(self, ruby_xml_node, node);
859
+ xmlNodeSetLang(node->node, (xmlChar*)StringValuePtr(lang));
860
+
861
+ return(Qtrue);
862
+ }
863
+
864
+
865
+ /*
866
+ * call-seq:
867
+ * node.last => node
868
+ *
869
+ * Obtain the last child node of this node, if any.
870
+ */
871
+ VALUE
872
+ ruby_xml_node_last_get(VALUE self) {
873
+ ruby_xml_node *rxn;
874
+ xmlNodePtr node;
875
+
876
+ Data_Get_Struct(self, ruby_xml_node, rxn);
877
+
878
+ switch (rxn->node->type) {
879
+ case XML_ELEMENT_NODE:
880
+ case XML_ENTITY_REF_NODE:
881
+ case XML_ENTITY_NODE:
882
+ case XML_PI_NODE:
883
+ case XML_COMMENT_NODE:
884
+ case XML_DOCUMENT_NODE:
885
+ #ifdef LIBXML_DOCB_ENABLED
886
+ case XML_DOCB_DOCUMENT_NODE:
887
+ #endif
888
+ case XML_HTML_DOCUMENT_NODE:
889
+ case XML_DTD_NODE:
890
+ node = rxn->node->last;
891
+ break;
892
+ case XML_ATTRIBUTE_NODE:
893
+ {
894
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
895
+ node = attr->last;
896
+ }
897
+ default:
898
+ node = NULL;
899
+ break;
900
+ }
901
+
902
+ if (node == NULL)
903
+ return(Qnil);
904
+ else
905
+ return(ruby_xml_node2_wrap(cXMLNode, node));
906
+ }
907
+
908
+
909
+ /*
910
+ * call-seq:
911
+ * node.last? => (true|false)
912
+ *
913
+ * Determine whether this node has a last child node.
914
+ */
915
+ VALUE
916
+ ruby_xml_node_last_q(VALUE self) {
917
+ ruby_xml_node *rxn;
918
+ xmlNodePtr node;
919
+
920
+ Data_Get_Struct(self, ruby_xml_node, rxn);
921
+
922
+ switch (rxn->node->type) {
923
+ case XML_ELEMENT_NODE:
924
+ case XML_ENTITY_REF_NODE:
925
+ case XML_ENTITY_NODE:
926
+ case XML_PI_NODE:
927
+ case XML_COMMENT_NODE:
928
+ case XML_DOCUMENT_NODE:
929
+ #ifdef LIBXML_DOCB_ENABLED
930
+ case XML_DOCB_DOCUMENT_NODE:
931
+ #endif
932
+ case XML_HTML_DOCUMENT_NODE:
933
+ case XML_DTD_NODE:
934
+ node = rxn->node->last;
935
+ break;
936
+ case XML_ATTRIBUTE_NODE:
937
+ {
938
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
939
+ node = attr->last;
940
+ }
941
+ default:
942
+ node = NULL;
943
+ break;
944
+ }
945
+
946
+ if (node == NULL)
947
+ return(Qfalse);
948
+ else
949
+ return(Qtrue);
950
+ }
951
+
952
+
953
+ /*
954
+ * call-seq:
955
+ * node.line_num => num
956
+ *
957
+ * Obtain the line number (in the XML document) that this
958
+ * node was read from. If +default_line_numbers+ is set
959
+ * false (the default), this method returns zero.
960
+ */
961
+ VALUE
962
+ ruby_xml_node_line_num(VALUE self) {
963
+ ruby_xml_node *rxn;
964
+ long line_num;
965
+ Data_Get_Struct(self, ruby_xml_node, rxn);
966
+
967
+ if (!xmlLineNumbersDefaultValue)
968
+ rb_warn("Line numbers were not retained: use XML::Parser::default_line_numbers=true");
969
+
970
+ line_num = xmlGetLineNo(rxn->node);
971
+ if (line_num == -1)
972
+ return(Qnil);
973
+ else
974
+ return(INT2NUM((long)line_num));
975
+ }
976
+
977
+
978
+ /*
979
+ * call-seq:
980
+ * node.xlink? => (true|false)
981
+ *
982
+ * Determine whether this node is an xlink node.
983
+ */
984
+ VALUE
985
+ ruby_xml_node_xlink_q(VALUE self) {
986
+ ruby_xml_node *node;
987
+ xlinkType xlt;
988
+
989
+ Data_Get_Struct(self, ruby_xml_node, node);
990
+ xlt = xlinkIsLink(node->node->doc, node->node);
991
+
992
+ if (xlt == XLINK_TYPE_NONE)
993
+ return(Qfalse);
994
+ else
995
+ return(Qtrue);
996
+ }
997
+
998
+
999
+ /*
1000
+ * call-seq:
1001
+ * node.xlink_type => num
1002
+ *
1003
+ * Obtain the type identifier for this xlink, if applicable.
1004
+ * If this is not an xlink node (see +xlink?+), will return
1005
+ * nil.
1006
+ */
1007
+ VALUE
1008
+ ruby_xml_node_xlink_type(VALUE self) {
1009
+ ruby_xml_node *node;
1010
+ xlinkType xlt;
1011
+
1012
+ Data_Get_Struct(self, ruby_xml_node, node);
1013
+ xlt = xlinkIsLink(node->node->doc, node->node);
1014
+
1015
+ if (xlt == XLINK_TYPE_NONE)
1016
+ return(Qnil);
1017
+ else
1018
+ return(INT2NUM(xlt));
1019
+ }
1020
+
1021
+
1022
+ /*
1023
+ * call-seq:
1024
+ * node.xlink_type_name => "string"
1025
+ *
1026
+ * Obtain the type name for this xlink, if applicable.
1027
+ * If this is not an xlink node (see +xlink?+), will return
1028
+ * nil.
1029
+ */
1030
+ VALUE
1031
+ ruby_xml_node_xlink_type_name(VALUE self) {
1032
+ ruby_xml_node *node;
1033
+ xlinkType xlt;
1034
+
1035
+ Data_Get_Struct(self, ruby_xml_node, node);
1036
+ xlt = xlinkIsLink(node->node->doc, node->node);
1037
+
1038
+ switch(xlt) {
1039
+ case XLINK_TYPE_NONE:
1040
+ return(Qnil);
1041
+ case XLINK_TYPE_SIMPLE:
1042
+ return(rb_str_new2("simple"));
1043
+ case XLINK_TYPE_EXTENDED:
1044
+ return(rb_str_new2("extended"));
1045
+ case XLINK_TYPE_EXTENDED_SET:
1046
+ return(rb_str_new2("extended_set"));
1047
+ default:
1048
+ rb_fatal("Unknowng xlink type, %d", xlt);
1049
+ }
1050
+ }
1051
+
1052
+ /*
1053
+ * call-seq:
1054
+ * node.name => "string"
1055
+ *
1056
+ * Obtain this node's name.
1057
+ */
1058
+ VALUE
1059
+ ruby_xml_node_name_get(VALUE self) {
1060
+ ruby_xml_node *rxn;
1061
+ const xmlChar *name;
1062
+
1063
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1064
+
1065
+ switch (rxn->node->type) {
1066
+ case XML_DOCUMENT_NODE:
1067
+ #ifdef LIBXML_DOCB_ENABLED
1068
+ case XML_DOCB_DOCUMENT_NODE:
1069
+ #endif
1070
+ case XML_HTML_DOCUMENT_NODE:
1071
+ {
1072
+ xmlDocPtr doc = (xmlDocPtr) rxn->node;
1073
+ name = doc->URL;
1074
+ break;
1075
+ }
1076
+ case XML_ATTRIBUTE_NODE:
1077
+ {
1078
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1079
+ name = attr->name;
1080
+ break;
1081
+ }
1082
+ case XML_NAMESPACE_DECL:
1083
+ {
1084
+ xmlNsPtr ns = (xmlNsPtr) rxn->node;
1085
+ name = ns->prefix;
1086
+ break;
1087
+ }
1088
+ default:
1089
+ name = rxn->node->name;
1090
+ break;
1091
+ }
1092
+
1093
+ if (rxn->node->name == NULL)
1094
+ return(Qnil);
1095
+ else
1096
+ return(rb_str_new2((const char*)name));
1097
+ }
1098
+
1099
+
1100
+ /*
1101
+ * call-seq:
1102
+ * node.name = "string"
1103
+ *
1104
+ * Set this node's name.
1105
+ */
1106
+ VALUE
1107
+ ruby_xml_node_name_set(VALUE self, VALUE name) {
1108
+ ruby_xml_node *node;
1109
+
1110
+ Check_Type(name, T_STRING);
1111
+ Data_Get_Struct(self, ruby_xml_node, node);
1112
+ xmlNodeSetName(node->node, (xmlChar*)StringValuePtr(name));
1113
+ return(Qtrue);
1114
+ }
1115
+
1116
+
1117
+ /*
1118
+ * call-seq:
1119
+ * node.namespace => [namespace, ..., namespace]
1120
+ *
1121
+ * Obtain an array of +XML::NS+ objects representing
1122
+ * this node's xmlns attributes
1123
+ */
1124
+ VALUE
1125
+ ruby_xml_node_namespace_get(VALUE self) {
1126
+ ruby_xml_node *node;
1127
+ xmlNsPtr *nsList, *cur;
1128
+ VALUE arr, ns;
1129
+
1130
+ Data_Get_Struct(self, ruby_xml_node, node);
1131
+ if (node->node == NULL)
1132
+ return(Qnil);
1133
+
1134
+ nsList = xmlGetNsList(node->node->doc, node->node);
1135
+
1136
+ if (nsList == NULL)
1137
+ return(Qnil);
1138
+
1139
+ arr = rb_ary_new();
1140
+ for (cur = nsList; *cur != NULL; cur++) {
1141
+ ns = ruby_xml_ns_new2(cXMLNS, ruby_xml_document_wrap(node->node->doc), *cur);
1142
+ if (ns == Qnil)
1143
+ continue;
1144
+ else
1145
+ rb_ary_push(arr, ns);
1146
+ }
1147
+ xmlFree(nsList);
1148
+
1149
+ return(arr);
1150
+ }
1151
+
1152
+
1153
+ /*
1154
+ * call-seq:
1155
+ * node.namespace_node => namespace.
1156
+ *
1157
+ * Obtain this node's namespace node.
1158
+ */
1159
+ VALUE
1160
+ ruby_xml_node_namespace_get_node(VALUE self) {
1161
+ ruby_xml_node *node;
1162
+
1163
+ Data_Get_Struct(self, ruby_xml_node, node);
1164
+ if (node->node->ns == NULL)
1165
+ return(Qnil);
1166
+ else
1167
+ return ruby_xml_ns_new2(cXMLNS,
1168
+ ruby_xml_document_wrap(node->node->doc),
1169
+ node->node->ns);
1170
+ }
1171
+
1172
+ // TODO namespace_set can take varargs (in fact, must if used
1173
+ // with strings), but I cannot see how you can call
1174
+ // that version, apart from with 'send'
1175
+ //
1176
+ // Would sure be nice to support foo.namespace['foo'] = 'bar'
1177
+ // but maybe that's not practical...
1178
+
1179
+ /*
1180
+ * call-seq:
1181
+ * node.namespace = namespace
1182
+ *
1183
+ * Add the specified XML::NS object to this node's xmlns attributes.
1184
+ */
1185
+ VALUE
1186
+ ruby_xml_node_namespace_set(int argc, VALUE *argv, VALUE self) {
1187
+ VALUE rns, rprefix;
1188
+ ruby_xml_node *rxn;
1189
+ ruby_xml_ns *rxns;
1190
+ xmlNsPtr ns;
1191
+ char *cp, *href;
1192
+
1193
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1194
+ switch (argc) {
1195
+ case 1:
1196
+ rns = argv[0];
1197
+ if (TYPE(rns) == T_STRING) {
1198
+ cp = strchr(StringValuePtr(rns), (int)':');
1199
+ if (cp == NULL) {
1200
+ rprefix = rns;
1201
+ href = NULL;
1202
+ } else {
1203
+ rprefix = rb_str_new(StringValuePtr(rns), (int)((long)cp - (long)StringValuePtr(rns)));
1204
+ href = &cp[1]; /* skip the : */
1205
+ }
1206
+ } else if (rb_obj_is_kind_of(rns, cXMLNS) == Qtrue) {
1207
+ Data_Get_Struct(self, ruby_xml_ns, rxns);
1208
+ xmlSetNs(rxn->node, rxns->ns);
1209
+ return(rns);
1210
+ } else
1211
+ rb_raise(rb_eTypeError, "must pass a string or an XML::Ns object");
1212
+
1213
+ /* Fall through to next case because when argc == 1, we need to
1214
+ * manually setup the additional args unless the arg passed is of
1215
+ * cXMLNS type */
1216
+ case 2:
1217
+ /* Don't want this code run in the fall through case */
1218
+ if (argc == 2) {
1219
+ rprefix = argv[0];
1220
+ href = StringValuePtr(argv[1]);
1221
+ }
1222
+
1223
+ ns = xmlNewNs(rxn->node, (xmlChar*)href, (xmlChar*)StringValuePtr(rprefix));
1224
+ if (ns == NULL)
1225
+ rb_raise(eXMLNodeSetNamespace, "unable to set the namespace");
1226
+ else
1227
+ return ruby_xml_ns_new2(cXMLNS, ruby_xml_document_wrap(rxn->node->doc), ns);
1228
+ break;
1229
+
1230
+ default:
1231
+ rb_raise(rb_eArgError, "wrong number of arguments (1 or 2)");
1232
+ }
1233
+
1234
+ /* can't get here */
1235
+ return(Qnil);
1236
+ }
1237
+
1238
+
1239
+ /*
1240
+ * call-seq:
1241
+ * node.namespace? => (true|false)
1242
+ *
1243
+ * Determine whether this node *is* (not has) a namespace
1244
+ * node.
1245
+ */
1246
+ VALUE
1247
+ ruby_xml_node_namespace_q(VALUE self) {
1248
+ ruby_xml_node *rxn;
1249
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1250
+ if (rxn->node->type == XML_NAMESPACE_DECL)
1251
+ return(Qtrue);
1252
+ else
1253
+ return(Qfalse);
1254
+ }
1255
+
1256
+ /*
1257
+ * memory2 implementation: xmlNode->_private holds a reference
1258
+ * to the wrapping ruby object VALUE when there is one.
1259
+ * traversal for marking is upward, and top levels are marked
1260
+ * through and lower level mark entry.
1261
+ *
1262
+ * All ruby retrieval for an xml
1263
+ * node will result in the same ruby instance. When all handles to them
1264
+ * go out of scope, then ruby_xfree gets called and _private is set to NULL.
1265
+ * If the xmlNode has no parent or document, then call xmlFree.
1266
+ */
1267
+ void
1268
+ ruby_xml_node2_free(ruby_xml_node *rxn) {
1269
+
1270
+ if (rxn == NULL ) return;
1271
+
1272
+ if (rxn->node != NULL ) {
1273
+ rxn->node->_private=NULL;
1274
+
1275
+ if ( rxn->node->doc==NULL || rxn->node->parent==NULL ) {
1276
+ #ifdef NODE_DEBUG
1277
+ fprintf(stderr,"ruby_xml_node2_free ruby_xfree rxn=0x%x xn=0x%x o=0x%x\n",(long)rxn,(long)rxn->node,(long)rxn->node->_private);
1278
+ #endif
1279
+ xmlFreeNode(rxn->node);
1280
+ }
1281
+
1282
+ rxn->node=NULL;
1283
+ }
1284
+
1285
+ ruby_xfree(rxn);
1286
+ }
1287
+
1288
+ void
1289
+ ruby_xml_node_mark_common(xmlNodePtr node) {
1290
+ if (node->parent == NULL ) {
1291
+ #ifdef NODE_DEBUG
1292
+ fprintf(stderr,"mark no parent r=0x%x *n=0x%x\n",rxn,node);
1293
+ #endif
1294
+ } else if ( node->doc != NULL ) {
1295
+ if (node->doc->_private == NULL) {
1296
+ rb_bug("XmlNode Doc is not bound! (%s:%d)",
1297
+ __FILE__,__LINE__);
1298
+ }
1299
+ rb_gc_mark((VALUE)node->doc->_private);
1300
+ } else {
1301
+ while (node->parent != NULL )
1302
+ node=node->parent;
1303
+ if (node->_private == NULL )
1304
+ rb_warning("XmlNode Root Parent is not bound! (%s:%d)",
1305
+ __FILE__,__LINE__);
1306
+ else {
1307
+ #ifdef NODE_DEBUG
1308
+ fprintf(stderr,"mark rxn=0x%x xn=0x%x o=0x%x doc=0x%x\n",(long)rxn,(long)node,(long)node->_private,node->doc);
1309
+ #endif
1310
+ rb_gc_mark((VALUE)node->_private);
1311
+ }
1312
+ }
1313
+ }
1314
+
1315
+ void
1316
+ ruby_xml_node2_mark(ruby_xml_node *rxn) {
1317
+ if (rxn->node == NULL ) return;
1318
+
1319
+ if (rxn->node->_private == NULL ) {
1320
+ rb_warning("XmlNode is not bound! (%s:%d)",
1321
+ __FILE__,__LINE__);
1322
+ return;
1323
+ }
1324
+
1325
+ ruby_xml_node_mark_common(rxn->node);
1326
+ }
1327
+
1328
+ VALUE
1329
+ ruby_xml_node2_wrap(VALUE class, xmlNodePtr xnode)
1330
+ {
1331
+ VALUE obj;
1332
+ ruby_xml_node *rxn;
1333
+
1334
+ // This node is already wrapped
1335
+ if (xnode->_private != NULL) {
1336
+ #ifdef NODE_DEBUG
1337
+ Data_Get_Struct((VALUE)xnode->_private,ruby_xml_node,rxn);
1338
+ fprintf(stderr,"re-wrap rn=0x%x n*=0x%x\n",(long)rxn,(long)xnode);
1339
+ #endif
1340
+ return (VALUE)xnode->_private;
1341
+ }
1342
+
1343
+ obj=Data_Make_Struct(class,ruby_xml_node,ruby_xml_node2_mark,
1344
+ ruby_xml_node2_free,rxn);
1345
+
1346
+ rxn->node=xnode;
1347
+ xnode->_private=(void*)obj;
1348
+ #ifdef NODE_DEBUG
1349
+ fprintf(stderr,"wrap rn=0x%x n*=0x%x d*=0x%x\n",
1350
+ (long)rxn,(long)xnode,xnode->doc);
1351
+ #endif
1352
+ return obj;
1353
+ }
1354
+
1355
+ VALUE
1356
+ ruby_xml_node2_new_native(VALUE class, VALUE ns, VALUE name)
1357
+ {
1358
+ VALUE obj;
1359
+ xmlNodePtr xnode;
1360
+ xmlNsPtr xns=NULL;
1361
+
1362
+ if ( ! NIL_P(ns) ) {
1363
+ Data_Get_Struct(ns,xmlNs,xns);
1364
+ }
1365
+ xnode=xmlNewNode(xns,(xmlChar*)StringValuePtr(name));
1366
+ xnode->_private=NULL;
1367
+
1368
+ obj=
1369
+ ruby_xml_node2_wrap(class,xnode);
1370
+
1371
+ rb_obj_call_init(obj,0,NULL);
1372
+ return obj;
1373
+ }
1374
+
1375
+ VALUE
1376
+ ruby_xml_node2_new_string(VALUE class, VALUE ns, VALUE name, VALUE val)
1377
+ {
1378
+ VALUE obj;
1379
+ obj=ruby_xml_node2_new_native(class,ns,name);
1380
+ if ( ! NIL_P(val) ) {
1381
+ if ( TYPE(val) != T_STRING )
1382
+ val=rb_obj_as_string(val);
1383
+ ruby_xml_node_content_set(obj,val);
1384
+ }
1385
+ return obj;
1386
+ }
1387
+ /*
1388
+ * call-seq:
1389
+ * XML::Node.new(name, content = nil) => node
1390
+ * XML::Node.new_element(name, content = nil) => node
1391
+ *
1392
+ * Create a new element node with the specified name, optionally setting
1393
+ * the node's content.
1394
+ * backward compatibility for <.5 new
1395
+ */
1396
+ VALUE
1397
+ ruby_xml_node2_new_string_bc(int argc, VALUE *argv, VALUE class)
1398
+ {
1399
+ VALUE content=Qnil;
1400
+ VALUE name=Qnil;
1401
+ switch(argc) {
1402
+ case 2:
1403
+ content=argv[1];
1404
+ if ( TYPE(content) != T_STRING)
1405
+ content=rb_obj_as_string(content);
1406
+
1407
+ case 1:
1408
+ name=check_string_or_symbol( argv[0] );
1409
+ return ruby_xml_node2_new_string(class,Qnil,name,content);
1410
+
1411
+ default:
1412
+ rb_raise(rb_eArgError, "wrong number of arguments (1 or 2) given %d",argc);
1413
+ }
1414
+ }
1415
+
1416
+ /*
1417
+ * call-seq:
1418
+ * node.next => node
1419
+ *
1420
+ * Obtain the next sibling node, if any.
1421
+ */
1422
+ VALUE
1423
+ ruby_xml_node_next_get(VALUE self) {
1424
+ ruby_xml_node *rxn;
1425
+ xmlNodePtr node;
1426
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1427
+
1428
+ switch (rxn->node->type) {
1429
+ case XML_DOCUMENT_NODE:
1430
+ #ifdef LIBXML_DOCB_ENABLED
1431
+ case XML_DOCB_DOCUMENT_NODE:
1432
+ #endif
1433
+ case XML_HTML_DOCUMENT_NODE:
1434
+ node = NULL;
1435
+ break;
1436
+ case XML_ATTRIBUTE_NODE:
1437
+ {
1438
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1439
+ node = (xmlNodePtr) attr->next;
1440
+ break;
1441
+ }
1442
+ case XML_NAMESPACE_DECL:
1443
+ {
1444
+ xmlNsPtr ns = (xmlNsPtr) rxn->node;
1445
+ node = (xmlNodePtr) ns->next;
1446
+ break;
1447
+ }
1448
+ default:
1449
+ node = rxn->node->next;
1450
+ break;
1451
+ }
1452
+
1453
+ if (node == NULL) {
1454
+ return(Qnil);
1455
+ } else {
1456
+ return(ruby_xml_node2_wrap(cXMLNode, node));
1457
+ }
1458
+ }
1459
+
1460
+
1461
+ /*
1462
+ * call-seq:
1463
+ * node.next? => (true|false)
1464
+ *
1465
+ * Determine whether this node has a next sibling.
1466
+ */
1467
+ VALUE
1468
+ ruby_xml_node_next_q(VALUE self) {
1469
+ ruby_xml_node *rxn;
1470
+ xmlNodePtr node;
1471
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1472
+
1473
+ switch (rxn->node->type) {
1474
+ case XML_DOCUMENT_NODE:
1475
+ #ifdef LIBXML_DOCB_ENABLED
1476
+ case XML_DOCB_DOCUMENT_NODE:
1477
+ #endif
1478
+ case XML_HTML_DOCUMENT_NODE:
1479
+ node = NULL;
1480
+ break;
1481
+ case XML_ATTRIBUTE_NODE:
1482
+ {
1483
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1484
+ node = (xmlNodePtr) attr->next;
1485
+ break;
1486
+ }
1487
+ case XML_NAMESPACE_DECL:
1488
+ {
1489
+ xmlNsPtr ns = (xmlNsPtr) rxn->node;
1490
+ node = (xmlNodePtr) ns->next;
1491
+ break;
1492
+ }
1493
+ default:
1494
+ node = rxn->node->next;
1495
+ break;
1496
+ }
1497
+
1498
+ if (node == NULL)
1499
+ return(Qfalse);
1500
+ else
1501
+ return(Qtrue);
1502
+ }
1503
+
1504
+
1505
+ /*
1506
+ * call-seq:
1507
+ * node.next = node
1508
+ *
1509
+ * Insert the specified node as this node's next sibling.
1510
+ */
1511
+ VALUE
1512
+ ruby_xml_node_next_set(VALUE self, VALUE rnode) {
1513
+ ruby_xml_node *cnode, *pnode;
1514
+ xmlNodePtr ret;
1515
+
1516
+ if (rb_obj_is_kind_of(rnode, cXMLNode) == Qfalse)
1517
+ rb_raise(rb_eTypeError, "Must pass an XML::Node object");
1518
+
1519
+ Data_Get_Struct(self, ruby_xml_node, pnode);
1520
+ Data_Get_Struct(rnode, ruby_xml_node, cnode);
1521
+
1522
+ ret = xmlAddNextSibling(pnode->node, cnode->node);
1523
+ if (ret == NULL)
1524
+ rb_raise(eXMLNodeFailedModify, "unable to add a sibling to the document");
1525
+
1526
+ return(ruby_xml_node2_wrap(cXMLNode, ret));
1527
+ }
1528
+
1529
+
1530
+ /*
1531
+ * call-seq:
1532
+ * node.notation? => (true|false)
1533
+ *
1534
+ * Determine whether this is a notation node
1535
+ */
1536
+ VALUE
1537
+ ruby_xml_node_notation_q(VALUE self) {
1538
+ ruby_xml_node *rxn;
1539
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1540
+ if (rxn->node->type == XML_NOTATION_NODE)
1541
+ return(Qtrue);
1542
+ else
1543
+ return(Qfalse);
1544
+ }
1545
+
1546
+
1547
+ /*
1548
+ * call-seq:
1549
+ * node.ns? => (true|false)
1550
+ *
1551
+ * Determine whether this node is a namespace node.
1552
+ */
1553
+ VALUE
1554
+ ruby_xml_node_ns_q(VALUE self) {
1555
+ ruby_xml_node *rxn;
1556
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1557
+ if (rxn->node->ns == NULL)
1558
+ return(Qfalse);
1559
+ else
1560
+ return(Qtrue);
1561
+ }
1562
+
1563
+
1564
+ /*
1565
+ * call-seq:
1566
+ * node.ns_def => namespace
1567
+ *
1568
+ * Obtain this node's default namespace.
1569
+ */
1570
+ VALUE
1571
+ ruby_xml_node_ns_def_get(VALUE self) {
1572
+ ruby_xml_node *rxn;
1573
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1574
+ if (rxn->node->nsDef == NULL)
1575
+ return(Qnil);
1576
+ else
1577
+ return(ruby_xml_ns_new2(cXMLNS, ruby_xml_document_wrap(rxn->node->doc), rxn->node->nsDef));
1578
+ }
1579
+
1580
+
1581
+ /*
1582
+ * call-seq:
1583
+ * node.ns_def? => (true|false)
1584
+ *
1585
+ * Obtain an array of +XML::NS+ objects representing
1586
+ * this node's xmlns attributes
1587
+ */
1588
+ VALUE
1589
+ ruby_xml_node_ns_def_q(VALUE self) {
1590
+ ruby_xml_node *rxn;
1591
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1592
+ if (rxn->node->nsDef == NULL)
1593
+ return(Qfalse);
1594
+ else
1595
+ return(Qtrue);
1596
+ }
1597
+
1598
+
1599
+ /*
1600
+ * call-seq:
1601
+ * node.parent => node
1602
+ *
1603
+ * Obtain this node's parent node, if any.
1604
+ */
1605
+ VALUE
1606
+ ruby_xml_node_parent_get(VALUE self) {
1607
+ ruby_xml_node *rxn;
1608
+ xmlNodePtr node;
1609
+
1610
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1611
+
1612
+ switch (rxn->node->type) {
1613
+ case XML_DOCUMENT_NODE:
1614
+ case XML_HTML_DOCUMENT_NODE:
1615
+ #ifdef LIBXML_DOCB_ENABLED
1616
+ case XML_DOCB_DOCUMENT_NODE:
1617
+ #endif
1618
+ node = NULL;
1619
+ break;
1620
+ case XML_ATTRIBUTE_NODE:
1621
+ {
1622
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1623
+ node = attr->parent;
1624
+ }
1625
+ case XML_ENTITY_DECL:
1626
+ case XML_NAMESPACE_DECL:
1627
+ case XML_XINCLUDE_START:
1628
+ case XML_XINCLUDE_END:
1629
+ node = NULL;
1630
+ break;
1631
+ default:
1632
+ node = rxn->node->parent;
1633
+ break;
1634
+ }
1635
+
1636
+ if (node == NULL)
1637
+ return(Qnil);
1638
+ else
1639
+ return(ruby_xml_node2_wrap(cXMLNode, node));
1640
+ }
1641
+
1642
+
1643
+ /*
1644
+ * call-seq:
1645
+ * node.parent? => (true|false)
1646
+ *
1647
+ * Determine whether this node has a parent node.
1648
+ */
1649
+ VALUE
1650
+ ruby_xml_node_parent_q(VALUE self) {
1651
+ ruby_xml_node *rxn;
1652
+ xmlNodePtr node;
1653
+
1654
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1655
+
1656
+ switch (rxn->node->type) {
1657
+ case XML_DOCUMENT_NODE:
1658
+ case XML_HTML_DOCUMENT_NODE:
1659
+ #ifdef LIBXML_DOCB_ENABLED
1660
+ case XML_DOCB_DOCUMENT_NODE:
1661
+ #endif
1662
+ node = NULL;
1663
+ break;
1664
+ case XML_ATTRIBUTE_NODE:
1665
+ {
1666
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1667
+ node = attr->parent;
1668
+ }
1669
+ case XML_ENTITY_DECL:
1670
+ case XML_NAMESPACE_DECL:
1671
+ case XML_XINCLUDE_START:
1672
+ case XML_XINCLUDE_END:
1673
+ node = NULL;
1674
+ break;
1675
+ default:
1676
+ node = rxn->node->parent;
1677
+ break;
1678
+ }
1679
+
1680
+ if (node == NULL)
1681
+ return(Qfalse);
1682
+ else
1683
+ return(Qtrue);
1684
+ }
1685
+
1686
+
1687
+ /*
1688
+ * call-seq:
1689
+ * node.path => path
1690
+ *
1691
+ * Obtain this node's path.
1692
+ */
1693
+ VALUE
1694
+ ruby_xml_node_path(VALUE self) {
1695
+ ruby_xml_node *rxn;
1696
+ xmlChar *path;
1697
+
1698
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1699
+ path = xmlGetNodePath(rxn->node);
1700
+
1701
+ if (path == NULL)
1702
+ return(Qnil);
1703
+ else
1704
+ return(rb_str_new2((const char*)path));
1705
+ }
1706
+
1707
+
1708
+ /*
1709
+ * call-seq:
1710
+ * node.pi? => (true|false)
1711
+ *
1712
+ * Determine whether this is a processing instruction node.
1713
+ */
1714
+ VALUE
1715
+ ruby_xml_node_pi_q(VALUE self) {
1716
+ ruby_xml_node *rxn;
1717
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1718
+ if (rxn->node->type == XML_PI_NODE)
1719
+ return(Qtrue);
1720
+ else
1721
+ return(Qfalse);
1722
+ }
1723
+
1724
+
1725
+ /*
1726
+ * call-seq:
1727
+ * node.pointer => node_set
1728
+ *
1729
+ * Evaluates an XPointer expression relative to this node.
1730
+ */
1731
+ VALUE
1732
+ ruby_xml_node_pointer(VALUE self, VALUE xptr_str) {
1733
+ return(ruby_xml_xpointer_point2(self, xptr_str));
1734
+ }
1735
+
1736
+
1737
+ /*
1738
+ * call-seq:
1739
+ * node.prev => node
1740
+ *
1741
+ * Obtain the previous sibling, if any.
1742
+ */
1743
+ VALUE
1744
+ ruby_xml_node_prev_get(VALUE self) {
1745
+ ruby_xml_node *rxn;
1746
+ xmlNodePtr node;
1747
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1748
+
1749
+ switch (rxn->node->type) {
1750
+ case XML_DOCUMENT_NODE:
1751
+ #ifdef LIBXML_DOCB_ENABLED
1752
+ case XML_DOCB_DOCUMENT_NODE:
1753
+ #endif
1754
+ case XML_HTML_DOCUMENT_NODE:
1755
+ case XML_NAMESPACE_DECL:
1756
+ node = NULL;
1757
+ break;
1758
+ case XML_ATTRIBUTE_NODE:
1759
+ {
1760
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1761
+ node = (xmlNodePtr) attr->prev;
1762
+ }
1763
+ break;
1764
+ default:
1765
+ node = rxn->node->prev;
1766
+ break;
1767
+ }
1768
+
1769
+ if (node == NULL)
1770
+ return(Qnil);
1771
+ else
1772
+ return(ruby_xml_node2_wrap(cXMLNode, node));
1773
+ }
1774
+
1775
+
1776
+ /*
1777
+ * call-seq:
1778
+ * node.prev? => (true|false)
1779
+ *
1780
+ * Determines whether this node has a previous sibling node.
1781
+ */
1782
+ VALUE
1783
+ ruby_xml_node_prev_q(VALUE self) {
1784
+ ruby_xml_node *rxn;
1785
+ xmlNodePtr node;
1786
+
1787
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1788
+
1789
+ switch (rxn->node->type) {
1790
+ case XML_DOCUMENT_NODE:
1791
+ #ifdef LIBXML_DOCB_ENABLED
1792
+ case XML_DOCB_DOCUMENT_NODE:
1793
+ #endif
1794
+ case XML_HTML_DOCUMENT_NODE:
1795
+ case XML_NAMESPACE_DECL:
1796
+ node = NULL;
1797
+ break;
1798
+ case XML_ATTRIBUTE_NODE:
1799
+ {
1800
+ xmlAttrPtr attr = (xmlAttrPtr) rxn->node;
1801
+ node = (xmlNodePtr) attr->prev;
1802
+ }
1803
+ break;
1804
+ default:
1805
+ node = rxn->node->prev;
1806
+ break;
1807
+ }
1808
+
1809
+ if (node == NULL)
1810
+ return(Qfalse);
1811
+ else
1812
+ return(Qtrue);
1813
+ }
1814
+
1815
+
1816
+ /*
1817
+ * call-seq:
1818
+ * node.prev = node
1819
+ *
1820
+ * Insert the specified node as this node's previous sibling.
1821
+ */
1822
+ VALUE
1823
+ ruby_xml_node_prev_set(VALUE self, VALUE rnode) {
1824
+ ruby_xml_node *cnode, *pnode;
1825
+ xmlNodePtr ret;
1826
+
1827
+ if (rb_obj_is_kind_of(rnode, cXMLNode) == Qfalse)
1828
+ rb_raise(rb_eTypeError, "Must pass an XML::Node object");
1829
+
1830
+ Data_Get_Struct(self, ruby_xml_node, pnode);
1831
+ Data_Get_Struct(rnode, ruby_xml_node, cnode);
1832
+
1833
+ ret = xmlAddPrevSibling(pnode->node, cnode->node);
1834
+ if (ret == NULL)
1835
+ rb_raise(eXMLNodeFailedModify, "unable to add a sibling to the document");
1836
+
1837
+ return(ruby_xml_node2_wrap(cXMLNode, ret));
1838
+ }
1839
+
1840
+
1841
+ /*
1842
+ * call-seq:
1843
+ * node.property("name") => "string"
1844
+ * node["name"] => "string"
1845
+ *
1846
+ * Obtain the named property.
1847
+ */
1848
+ VALUE
1849
+ ruby_xml_node_property_get(VALUE self, VALUE prop) {
1850
+ ruby_xml_node *rxn;
1851
+ xmlChar *p;
1852
+ VALUE result = Qnil;
1853
+
1854
+ prop = check_string_or_symbol( prop );
1855
+
1856
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1857
+ p = xmlGetProp(rxn->node, (xmlChar*)StringValuePtr(prop));
1858
+
1859
+ if (p) {
1860
+ result = rb_str_new2((const char*)p);
1861
+ xmlFree(p);
1862
+ }
1863
+
1864
+ return result;
1865
+ }
1866
+
1867
+
1868
+ /*
1869
+ * call-seq:
1870
+ * node["name"] = "string"
1871
+ *
1872
+ * Set the named property.
1873
+ */
1874
+ VALUE
1875
+ ruby_xml_node_property_set(VALUE self, VALUE key, VALUE val) {
1876
+ ruby_xml_node *node;
1877
+ xmlAttrPtr attr;
1878
+
1879
+ key = check_string_or_symbol( key );
1880
+ Data_Get_Struct(self, ruby_xml_node, node);
1881
+
1882
+ if( val == Qnil ) {
1883
+ attr = xmlSetProp(node->node, (xmlChar*)StringValuePtr(key), NULL);
1884
+ if (attr->_private == NULL)
1885
+ xmlRemoveProp( attr );
1886
+ else
1887
+ xmlUnlinkNode( attr );
1888
+ return Qnil;
1889
+ } else {
1890
+ Check_Type(val, T_STRING);
1891
+ }
1892
+
1893
+ attr = xmlSetProp(node->node, (xmlChar*)StringValuePtr(key), (xmlChar*)StringValuePtr(val));
1894
+ if (attr == NULL) {
1895
+ attr = xmlNewProp(node->node, (xmlChar*)StringValuePtr(key), (xmlChar*)StringValuePtr(val));
1896
+ if (attr == NULL)
1897
+ return(Qnil);
1898
+ }
1899
+ return(ruby_xml_attr_new(cXMLAttr, attr));
1900
+ }
1901
+
1902
+
1903
+ /*
1904
+ * call-seq:
1905
+ * node.properties => attributes
1906
+ *
1907
+ * Returns the +XML::Attr+ for this node.
1908
+ */
1909
+ VALUE
1910
+ ruby_xml_node_properties_get(VALUE self) {
1911
+ ruby_xml_node *node;
1912
+ xmlAttrPtr attr;
1913
+
1914
+ Data_Get_Struct(self, ruby_xml_node, node);
1915
+
1916
+ if (node->node->type == XML_ELEMENT_NODE) {
1917
+ attr = node->node->properties;
1918
+
1919
+ if (attr == NULL) {
1920
+ return(Qnil);
1921
+ } else {
1922
+ return(ruby_xml_attr_wrap(cXMLAttr, attr));
1923
+ }
1924
+ } else {
1925
+ return(Qnil);
1926
+ }
1927
+ }
1928
+
1929
+
1930
+ /*
1931
+ * call-seq:
1932
+ * node.properties? => (true|false)
1933
+ *
1934
+ * Determine whether this node has properties
1935
+ * (attributes).
1936
+ */
1937
+ VALUE
1938
+ ruby_xml_node_properties_q(VALUE self) {
1939
+ ruby_xml_node *rxn;
1940
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1941
+ if (rxn->node->type == XML_ELEMENT_NODE && rxn->node->properties != NULL)
1942
+ return(Qtrue);
1943
+ else
1944
+ return(Qfalse);
1945
+ }
1946
+
1947
+
1948
+ /*
1949
+ * call-seq:
1950
+ * node.remove! => nil
1951
+ *
1952
+ * Removes this node from it's parent.
1953
+ */
1954
+ VALUE
1955
+ ruby_xml_node_remove_ex(VALUE self) {
1956
+ ruby_xml_node *rxn;
1957
+ Data_Get_Struct(self, ruby_xml_node, rxn);
1958
+ xmlUnlinkNode(rxn->node);
1959
+ return(Qnil);
1960
+ }
1961
+
1962
+
1963
+ /*
1964
+ * call-seq:
1965
+ * node.search_href => namespace
1966
+ *
1967
+ * Search for a namespace by href.
1968
+ */
1969
+ VALUE
1970
+ ruby_xml_node_search_href(VALUE self, VALUE href) {
1971
+ ruby_xml_node *node;
1972
+
1973
+ Check_Type(href, T_STRING);
1974
+ Data_Get_Struct(self, ruby_xml_node, node);
1975
+ return(ruby_xml_ns_new2(cXMLNS, ruby_xml_document_wrap(node->node->doc),
1976
+ xmlSearchNsByHref(node->node->doc, node->node,
1977
+ (xmlChar*)StringValuePtr(href))));
1978
+ }
1979
+
1980
+
1981
+ /*
1982
+ * call-seq:
1983
+ * node.search_ns => namespace
1984
+ *
1985
+ * Search for a namespace by namespace.
1986
+ */
1987
+ VALUE
1988
+ ruby_xml_node_search_ns(VALUE self, VALUE ns) {
1989
+ ruby_xml_node *node;
1990
+
1991
+ Check_Type(ns, T_STRING);
1992
+ Data_Get_Struct(self, ruby_xml_node, node);
1993
+ return(ruby_xml_ns_new2(cXMLNS,
1994
+ ruby_xml_document_wrap(node->node->doc),
1995
+ xmlSearchNs(node->node->doc, node->node,
1996
+ (xmlChar*)StringValuePtr(ns))));
1997
+ }
1998
+
1999
+
2000
+ /*
2001
+ * call-seq:
2002
+ * node.sibling(node) => node
2003
+ *
2004
+ * Add the specified node as a sibling of this node.
2005
+ */
2006
+ VALUE
2007
+ ruby_xml_node_sibling_set(VALUE self, VALUE rnode) {
2008
+ ruby_xml_node *cnode, *pnode;
2009
+ xmlNodePtr ret;
2010
+ VALUE obj;
2011
+
2012
+ if (rb_obj_is_kind_of(rnode, cXMLNode) == Qfalse)
2013
+ rb_raise(rb_eTypeError, "Must pass an XML::Node object");
2014
+
2015
+ Data_Get_Struct(self, ruby_xml_node, pnode);
2016
+ Data_Get_Struct(rnode, ruby_xml_node, cnode);
2017
+
2018
+ ret = xmlAddSibling(pnode->node, cnode->node);
2019
+ if (ret == NULL)
2020
+ rb_raise(eXMLNodeFailedModify, "unable to add a sibling to the document");
2021
+ if (ret->_private==NULL)
2022
+ obj=ruby_xml_node2_wrap(cXMLNode,ret);
2023
+ else
2024
+ obj=(VALUE)ret->_private;
2025
+
2026
+ return obj;
2027
+ }
2028
+
2029
+
2030
+ /*
2031
+ * call-seq:
2032
+ * node.space_preserve => (true|false)
2033
+ *
2034
+ * Determine whether this node preserves whitespace.
2035
+ */
2036
+ VALUE
2037
+ ruby_xml_node_space_preserve_get(VALUE self) {
2038
+ ruby_xml_node *rxn;
2039
+
2040
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2041
+ return(INT2NUM(xmlNodeGetSpacePreserve(rxn->node)));
2042
+ }
2043
+
2044
+
2045
+ /*
2046
+ * call-seq:
2047
+ * node.space_preserve = true|false
2048
+ *
2049
+ * Control whether this node preserves whitespace.
2050
+ */
2051
+ VALUE
2052
+ ruby_xml_node_space_preserve_set(VALUE self, VALUE bool) {
2053
+ ruby_xml_node *rxn;
2054
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2055
+
2056
+ if (TYPE(bool) == T_FALSE)
2057
+ xmlNodeSetSpacePreserve(rxn->node, 1);
2058
+ else
2059
+ xmlNodeSetSpacePreserve(rxn->node, 0);
2060
+
2061
+ return(Qnil);
2062
+ }
2063
+
2064
+
2065
+ /*
2066
+ * call-seq:
2067
+ * node.text? => (true|false)
2068
+ *
2069
+ * Determine whether this node has text.
2070
+ */
2071
+ VALUE
2072
+ ruby_xml_node_text_q(VALUE self) {
2073
+ ruby_xml_node *rxn;
2074
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2075
+ if (rxn->node == NULL)
2076
+ return(Qnil);
2077
+
2078
+ return((xmlNodeIsText(rxn->node) == 1) ? Qtrue : Qfalse);
2079
+ }
2080
+
2081
+
2082
+ /*
2083
+ * call-seq:
2084
+ * node.to_s => "string"
2085
+ *
2086
+ * Coerce this node to a string representation of
2087
+ * it's XML.
2088
+ */
2089
+ VALUE
2090
+ ruby_xml_node_to_s(VALUE self) {
2091
+ ruby_xml_node *rxn;
2092
+ xmlBufferPtr buf;
2093
+ VALUE result;
2094
+
2095
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2096
+ buf = xmlBufferCreate();
2097
+ xmlNodeDump(buf, rxn->node->doc, rxn->node, 0, 1);
2098
+ result = rb_str_new2((const char*)buf->content);
2099
+
2100
+ xmlBufferFree(buf);
2101
+ return result;
2102
+ }
2103
+
2104
+
2105
+ /*
2106
+ * call-seq:
2107
+ * node.type => num
2108
+ *
2109
+ * Obtain this node's type identifier.
2110
+ */
2111
+ VALUE
2112
+ ruby_xml_node_type(VALUE self) {
2113
+ ruby_xml_node *rxn;
2114
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2115
+ return(INT2NUM(rxn->node->type));
2116
+ }
2117
+
2118
+
2119
+ /*
2120
+ * call-seq:
2121
+ * node.type_name => num
2122
+ *
2123
+ * Obtain this node's type name.
2124
+ */
2125
+ VALUE
2126
+ ruby_xml_node_type_name(VALUE self) {
2127
+ ruby_xml_node *rxn;
2128
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2129
+
2130
+ switch(rxn->node->type) {
2131
+ case XML_ELEMENT_NODE:
2132
+ return(rb_str_new2("element"));
2133
+ case XML_ATTRIBUTE_NODE:
2134
+ return(rb_str_new2("attribute"));
2135
+ case XML_TEXT_NODE:
2136
+ return(rb_str_new2("text"));
2137
+ case XML_CDATA_SECTION_NODE:
2138
+ return(rb_str_new2("cdata"));
2139
+ case XML_ENTITY_REF_NODE:
2140
+ return(rb_str_new2("entity_ref"));
2141
+ case XML_ENTITY_NODE:
2142
+ return(rb_str_new2("entity"));
2143
+ case XML_PI_NODE:
2144
+ return(rb_str_new2("pi"));
2145
+ case XML_COMMENT_NODE:
2146
+ return(rb_str_new2("comment"));
2147
+ case XML_DOCUMENT_NODE:
2148
+ return(rb_str_new2("document_xml"));
2149
+ case XML_DOCUMENT_TYPE_NODE:
2150
+ return(rb_str_new2("doctype"));
2151
+ case XML_DOCUMENT_FRAG_NODE:
2152
+ return(rb_str_new2("fragment"));
2153
+ case XML_NOTATION_NODE:
2154
+ return(rb_str_new2("notation"));
2155
+ case XML_HTML_DOCUMENT_NODE:
2156
+ return(rb_str_new2("document_html"));
2157
+ case XML_DTD_NODE:
2158
+ return(rb_str_new2("dtd"));
2159
+ case XML_ELEMENT_DECL:
2160
+ return(rb_str_new2("elem_decl"));
2161
+ case XML_ATTRIBUTE_DECL:
2162
+ return(rb_str_new2("attribute_decl"));
2163
+ case XML_ENTITY_DECL:
2164
+ return(rb_str_new2("entity_decl"));
2165
+ case XML_NAMESPACE_DECL:
2166
+ return(rb_str_new2("namespace"));
2167
+ case XML_XINCLUDE_START:
2168
+ return(rb_str_new2("xinclude_start"));
2169
+ case XML_XINCLUDE_END:
2170
+ return(rb_str_new2("xinclude_end"));
2171
+ #ifdef LIBXML_DOCB_ENABLED
2172
+ case XML_DOCB_DOCUMENT_NODE:
2173
+ return(rb_str_new2("document_docbook"));
2174
+ #endif
2175
+ default:
2176
+ rb_raise(eXMLNodeUnknownType, "Unknown node type: %n", rxn->node->type);
2177
+ return(Qfalse);
2178
+ }
2179
+ }
2180
+
2181
+
2182
+ /*
2183
+ * call-seq:
2184
+ * node.xinclude_end? => num
2185
+ *
2186
+ * Determine whether this node is an xinclude end node.
2187
+ */
2188
+ VALUE
2189
+ ruby_xml_node_xinclude_end_q(VALUE self) {
2190
+ ruby_xml_node *rxn;
2191
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2192
+ if (rxn->node->type == XML_XINCLUDE_END)
2193
+ return(Qtrue);
2194
+ else
2195
+ return(Qfalse);
2196
+ }
2197
+
2198
+
2199
+ /*
2200
+ * call-seq:
2201
+ * node.xinclude_start? => num
2202
+ *
2203
+ * Determine whether this node is an xinclude start node.
2204
+ */
2205
+ VALUE
2206
+ ruby_xml_node_xinclude_start_q(VALUE self) {
2207
+ ruby_xml_node *rxn;
2208
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2209
+ if (rxn->node->type == XML_XINCLUDE_START)
2210
+ return(Qtrue);
2211
+ else
2212
+ return(Qfalse);
2213
+ }
2214
+
2215
+
2216
+ /*
2217
+ * call-seq:
2218
+ * node.copy => node
2219
+ *
2220
+ * Create a copy of this node.
2221
+ */
2222
+ VALUE
2223
+ ruby_xml_node_copy(VALUE self, VALUE deep) {
2224
+ ruby_xml_node *rxn;
2225
+ xmlNode *copy;
2226
+ VALUE obj;
2227
+
2228
+ Data_Get_Struct(self, ruby_xml_node, rxn);
2229
+ copy = xmlCopyNode( rxn->node, ((deep==Qnil)||(deep==Qfalse))?0:1 );
2230
+
2231
+ if (copy == NULL)
2232
+ return Qnil;
2233
+
2234
+ obj=ruby_xml_node2_wrap(cXMLNode,copy);
2235
+ copy->_private = (void*) obj;
2236
+ return obj;
2237
+ }
2238
+
2239
+ /*
2240
+ * call-seq:
2241
+ * XML::Node.new_text(content = nil) => node
2242
+ *
2243
+ * Create a new text node, optionally setting
2244
+ * the node's content.
2245
+ *
2246
+ */
2247
+ VALUE
2248
+ ruby_xml_node_new_text(VALUE class, VALUE text)
2249
+ {
2250
+ VALUE obj;
2251
+ xmlNodePtr xnode;
2252
+
2253
+ if ( NIL_P(text) )
2254
+ return Qnil;
2255
+
2256
+ if (TYPE(text) != T_STRING )
2257
+ rb_raise(rb_eTypeError, "requires string argument");
2258
+
2259
+ xnode=xmlNewText((xmlChar*)STR2CSTR(text));
2260
+ if ( xnode == NULL )
2261
+ return Qnil;
2262
+
2263
+ obj=ruby_xml_node2_wrap(class,xnode);
2264
+ rb_obj_call_init(obj,0,NULL);
2265
+ return obj;
2266
+ }
2267
+
2268
+ void
2269
+ ruby_xml_node_registerNode(xmlNodePtr node)
2270
+ {
2271
+ node->_private=NULL;
2272
+ }
2273
+
2274
+ void
2275
+ ruby_xml_node_deregisterNode(xmlNodePtr node)
2276
+ {
2277
+ ruby_xml_node *rxn;
2278
+ if ( node->_private==NULL ) return;
2279
+ Data_Get_Struct(node->_private, ruby_xml_node, rxn);
2280
+ rxn->node=NULL;
2281
+ }
2282
+
2283
+ // Rdoc needs to know
2284
+ #ifdef RDOC_NEVER_DEFINED
2285
+ mXML = rb_define_module("XML");
2286
+ #endif
2287
+
2288
+ void
2289
+ ruby_init_xml_node(void) {
2290
+ VALUE singleton;
2291
+
2292
+ xmlRegisterNodeDefault(ruby_xml_node_registerNode);
2293
+ xmlDeregisterNodeDefault(ruby_xml_node_deregisterNode);
2294
+
2295
+ cXMLNode = rb_define_class_under(mXML, "Node", rb_cObject);
2296
+ eXMLNodeSetNamespace = rb_define_class_under(cXMLNode, "SetNamespace", eXMLError);
2297
+ eXMLNodeFailedModify = rb_define_class_under(cXMLNode, "FailedModify", eXMLError);
2298
+ eXMLNodeUnknownType = rb_define_class_under(cXMLNode, "UnknownType", eXMLError);
2299
+
2300
+ singleton = rb_singleton_class(cXMLNode);
2301
+
2302
+ rb_define_const(cXMLNode, "SPACE_DEFAULT", INT2NUM(0));
2303
+ rb_define_const(cXMLNode, "SPACE_PRESERVE", INT2NUM(1));
2304
+ rb_define_const(cXMLNode, "SPACE_NOT_INHERIT", INT2NUM(-1));
2305
+ rb_define_const(cXMLNode, "XLINK_ACTUATE_AUTO", INT2NUM(1));
2306
+ rb_define_const(cXMLNode, "XLINK_ACTUATE_NONE", INT2NUM(0));
2307
+ rb_define_const(cXMLNode, "XLINK_ACTUATE_ONREQUEST", INT2NUM(2));
2308
+ rb_define_const(cXMLNode, "XLINK_SHOW_EMBED", INT2NUM(2));
2309
+ rb_define_const(cXMLNode, "XLINK_SHOW_NEW", INT2NUM(1));
2310
+ rb_define_const(cXMLNode, "XLINK_SHOW_NONE", INT2NUM(0));
2311
+ rb_define_const(cXMLNode, "XLINK_SHOW_REPLACE", INT2NUM(3));
2312
+ rb_define_const(cXMLNode, "XLINK_TYPE_EXTENDED", INT2NUM(2));
2313
+ rb_define_const(cXMLNode, "XLINK_TYPE_EXTENDED_SET", INT2NUM(3));
2314
+ rb_define_const(cXMLNode, "XLINK_TYPE_NONE", INT2NUM(0));
2315
+ rb_define_const(cXMLNode, "XLINK_TYPE_SIMPLE", INT2NUM(1));
2316
+
2317
+ rb_define_singleton_method(cXMLNode, "new2", ruby_xml_node2_new_native, 2);
2318
+ rb_define_singleton_method(cXMLNode, "new", ruby_xml_node2_new_string_bc, -1);
2319
+ rb_define_singleton_method(cXMLNode, "new_cdata", ruby_xml_node_new_cdata, -1);
2320
+ rb_define_singleton_method(cXMLNode, "new_comment", ruby_xml_node_new_comment, -1);
2321
+ rb_define_singleton_method(cXMLNode, "new_text", ruby_xml_node_new_text, 1);
2322
+
2323
+ rb_define_alias(singleton, "new_element", "new");
2324
+
2325
+ rb_define_method(cXMLNode, "<<", ruby_xml_node_content_add, 1);
2326
+ rb_define_method(cXMLNode, "[]", ruby_xml_node_property_get, 1);
2327
+ rb_define_method(cXMLNode, "[]=", ruby_xml_node_property_set, 2);
2328
+ rb_define_method(cXMLNode, "attribute?", ruby_xml_node_attribute_q, 0);
2329
+ rb_define_method(cXMLNode, "attribute_decl?", ruby_xml_node_attribute_decl_q, 0);
2330
+ rb_define_method(cXMLNode, "base", ruby_xml_node_base_get, 0);
2331
+ rb_define_method(cXMLNode, "base=", ruby_xml_node_base_set, 1);
2332
+ rb_define_method(cXMLNode, "blank?", ruby_xml_node_empty_q, 0);
2333
+ rb_define_method(cXMLNode, "cdata?", ruby_xml_node_cdata_q, 0);
2334
+ rb_define_method(cXMLNode, "comment?", ruby_xml_node_comment_q, 0);
2335
+ rb_define_method(cXMLNode, "copy", ruby_xml_node_copy, 1);
2336
+ rb_define_method(cXMLNode, "child", ruby_xml_node_child_get, 0);
2337
+ rb_define_method(cXMLNode, "child?", ruby_xml_node_child_q, 0);
2338
+ rb_define_method(cXMLNode, "child=", ruby_xml_node_child_set, 1);
2339
+ rb_define_method(cXMLNode, "child_add", ruby_xml_node_child_add, 1);
2340
+ rb_define_method(cXMLNode, "children", ruby_xml_node_child_get, 0);
2341
+ rb_define_method(cXMLNode, "children?", ruby_xml_node_child_q, 0);
2342
+ rb_define_method(cXMLNode, "content", ruby_xml_node_content_get, 0);
2343
+ rb_define_method(cXMLNode, "content=", ruby_xml_node_content_set, 1);
2344
+ rb_define_method(cXMLNode, "content_stripped", ruby_xml_node_content_stripped_get, 0);
2345
+ rb_define_method(cXMLNode, "doc", ruby_xml_node_doc, 0);
2346
+ rb_define_method(cXMLNode, "docbook_doc?", ruby_xml_node_docbook_doc_q, 0);
2347
+ rb_define_method(cXMLNode, "doctype?", ruby_xml_node_doctype_q, 0);
2348
+ rb_define_method(cXMLNode, "document?", ruby_xml_node_document_q, 0);
2349
+ rb_define_method(cXMLNode, "dtd?", ruby_xml_node_dtd_q, 0);
2350
+ rb_define_method(cXMLNode, "dump", ruby_xml_node_dump, 0);
2351
+ rb_define_method(cXMLNode, "debug_dump", ruby_xml_node_debug_dump, 0);
2352
+ rb_define_method(cXMLNode, "element?", ruby_xml_node_element_q, 0);
2353
+ rb_define_method(cXMLNode, "element_decl?", ruby_xml_node_element_decl_q, 0);
2354
+ rb_define_method(cXMLNode, "empty?", ruby_xml_node_empty_q, 0);
2355
+ rb_define_method(cXMLNode, "entity?", ruby_xml_node_entity_q, 0);
2356
+ rb_define_method(cXMLNode, "entity_ref?", ruby_xml_node_entity_ref_q, 0);
2357
+ rb_define_method(cXMLNode, "eql?", ruby_xml_node_eql_q, 1);
2358
+ rb_define_method(cXMLNode, "find", ruby_xml_node_find, -1);
2359
+ rb_define_method(cXMLNode, "find_first", ruby_xml_node_find_first, -1);
2360
+ rb_define_method(cXMLNode, "fragment?", ruby_xml_node_fragment_q, 0);
2361
+ rb_define_method(cXMLNode, "hash", ruby_xml_node_hash, 0);
2362
+ rb_define_method(cXMLNode, "html_doc?", ruby_xml_node_html_doc_q, 0);
2363
+ rb_define_method(cXMLNode, "lang", ruby_xml_node_lang_get, 0);
2364
+ rb_define_method(cXMLNode, "lang=", ruby_xml_node_lang_set, 1);
2365
+ rb_define_method(cXMLNode, "last", ruby_xml_node_last_get, 0);
2366
+ rb_define_method(cXMLNode, "last?", ruby_xml_node_last_q, 0);
2367
+ rb_define_method(cXMLNode, "line_num", ruby_xml_node_line_num, 0);
2368
+ rb_define_method(cXMLNode, "name", ruby_xml_node_name_get, 0);
2369
+ rb_define_method(cXMLNode, "name=", ruby_xml_node_name_set, 1);
2370
+ rb_define_method(cXMLNode, "namespace", ruby_xml_node_namespace_get, 0);
2371
+ rb_define_method(cXMLNode, "namespace_node", ruby_xml_node_namespace_get_node, 0);
2372
+ rb_define_method(cXMLNode, "namespace?", ruby_xml_node_namespace_q, 0);
2373
+ rb_define_method(cXMLNode, "namespace=", ruby_xml_node_namespace_set, -1);
2374
+ rb_define_method(cXMLNode, "next", ruby_xml_node_next_get, 0);
2375
+ rb_define_method(cXMLNode, "next?", ruby_xml_node_next_q, 0);
2376
+ rb_define_method(cXMLNode, "next=", ruby_xml_node_next_set, 1);
2377
+ rb_define_method(cXMLNode, "node_type", ruby_xml_node_type, 0);
2378
+ rb_define_method(cXMLNode, "node_type_name", ruby_xml_node_type_name, 0);
2379
+ rb_define_method(cXMLNode, "notation?", ruby_xml_node_notation_q, 0);
2380
+ rb_define_method(cXMLNode, "ns", ruby_xml_node_namespace_get, 0);
2381
+ rb_define_method(cXMLNode, "ns?", ruby_xml_node_ns_q, 0);
2382
+ rb_define_method(cXMLNode, "ns_def", ruby_xml_node_ns_def_get, 0);
2383
+ rb_define_method(cXMLNode, "ns_def?", ruby_xml_node_ns_def_q, 0);
2384
+ rb_define_method(cXMLNode, "parent", ruby_xml_node_parent_get, 0);
2385
+ rb_define_method(cXMLNode, "parent?", ruby_xml_node_parent_q, 0);
2386
+ rb_define_method(cXMLNode, "path", ruby_xml_node_path, 0);
2387
+ rb_define_method(cXMLNode, "pi?", ruby_xml_node_pi_q, 0);
2388
+ rb_define_method(cXMLNode, "pointer", ruby_xml_node_pointer, 1);
2389
+ rb_define_method(cXMLNode, "prev", ruby_xml_node_prev_get, 0);
2390
+ rb_define_method(cXMLNode, "prev?", ruby_xml_node_prev_q, 0);
2391
+ rb_define_method(cXMLNode, "prev=", ruby_xml_node_prev_set, 1);
2392
+ rb_define_method(cXMLNode, "property", ruby_xml_node_property_get, 1);
2393
+ rb_define_method(cXMLNode, "properties", ruby_xml_node_properties_get, 0);
2394
+ rb_define_method(cXMLNode, "properties?", ruby_xml_node_properties_q, 0);
2395
+ rb_define_method(cXMLNode, "remove!", ruby_xml_node_remove_ex, 0);
2396
+ rb_define_method(cXMLNode, "search_ns", ruby_xml_node_search_ns, 1);
2397
+ rb_define_method(cXMLNode, "search_href", ruby_xml_node_search_href, 1);
2398
+ rb_define_method(cXMLNode, "sibling=", ruby_xml_node_sibling_set, 1);
2399
+ rb_define_method(cXMLNode, "space_preserve", ruby_xml_node_space_preserve_get, 0);
2400
+ rb_define_method(cXMLNode, "space_preserve=", ruby_xml_node_space_preserve_set, 1);
2401
+ rb_define_method(cXMLNode, "text?", ruby_xml_node_text_q, 0);
2402
+ rb_define_method(cXMLNode, "to_s", ruby_xml_node_to_s, 0);
2403
+ rb_define_method(cXMLNode, "xinclude_end?", ruby_xml_node_xinclude_end_q, 0);
2404
+ rb_define_method(cXMLNode, "xinclude_start?", ruby_xml_node_xinclude_start_q, 0);
2405
+ rb_define_method(cXMLNode, "xlink?", ruby_xml_node_xlink_q, 0);
2406
+ rb_define_method(cXMLNode, "xlink_type", ruby_xml_node_xlink_type, 0);
2407
+ rb_define_method(cXMLNode, "xlink_type_name", ruby_xml_node_xlink_type_name, 0);
2408
+
2409
+ rb_define_alias(cXMLNode, "==", "eql?");
2410
+ }