nokogiri 1.4.0 → 1.4.1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of nokogiri might be problematic. Click here for more details.

Files changed (75) hide show
  1. data.tar.gz.sig +0 -0
  2. data/.autotest +5 -6
  3. data/CHANGELOG.ja.rdoc +47 -11
  4. data/CHANGELOG.rdoc +31 -0
  5. data/Manifest.txt +8 -1
  6. data/README.ja.rdoc +4 -3
  7. data/README.rdoc +9 -1
  8. data/Rakefile +4 -0
  9. data/deps.rip +5 -0
  10. data/ext/nokogiri/extconf.rb +4 -0
  11. data/ext/nokogiri/html_element_description.c +1 -1
  12. data/ext/nokogiri/nokogiri.c +7 -0
  13. data/ext/nokogiri/nokogiri.h +4 -1
  14. data/ext/nokogiri/xml_document.c +3 -5
  15. data/ext/nokogiri/xml_encoding_handler.c +79 -0
  16. data/ext/nokogiri/xml_encoding_handler.h +8 -0
  17. data/ext/nokogiri/xml_namespace.c +8 -0
  18. data/ext/nokogiri/xml_namespace.h +1 -0
  19. data/ext/nokogiri/xml_node.c +61 -41
  20. data/ext/nokogiri/xml_node_set.c +22 -14
  21. data/ext/nokogiri/xml_sax_parser.c +0 -3
  22. data/ext/nokogiri/xml_sax_parser_context.c +2 -0
  23. data/ext/nokogiri/xml_sax_push_parser.c +26 -3
  24. data/ext/nokogiri/xml_syntax_error.c +18 -227
  25. data/lib/nokogiri/css/generated_parser.rb +173 -160
  26. data/lib/nokogiri/css/generated_tokenizer.rb +4 -1
  27. data/lib/nokogiri/css/parser.y +4 -1
  28. data/lib/nokogiri/css/tokenizer.rex +2 -1
  29. data/lib/nokogiri/css/xpath_visitor.rb +2 -0
  30. data/lib/nokogiri/ffi/encoding_handler.rb +42 -0
  31. data/lib/nokogiri/ffi/html/element_description.rb +5 -9
  32. data/lib/nokogiri/ffi/libxml.rb +21 -5
  33. data/lib/nokogiri/ffi/structs/xml_char_encoding_handler.rb +11 -0
  34. data/lib/nokogiri/ffi/structs/xml_document.rb +3 -3
  35. data/lib/nokogiri/ffi/structs/xml_sax_push_parser_context.rb +110 -1
  36. data/lib/nokogiri/ffi/xml/dtd.rb +2 -4
  37. data/lib/nokogiri/ffi/xml/node.rb +38 -17
  38. data/lib/nokogiri/ffi/xml/node_set.rb +21 -8
  39. data/lib/nokogiri/ffi/xml/reader.rb +1 -1
  40. data/lib/nokogiri/ffi/xml/sax/parser.rb +1 -8
  41. data/lib/nokogiri/ffi/xml/sax/push_parser.rb +16 -4
  42. data/lib/nokogiri/ffi/xml/syntax_error.rb +9 -2
  43. data/lib/nokogiri/ffi/xslt/stylesheet.rb +12 -9
  44. data/lib/nokogiri/version.rb +1 -1
  45. data/lib/nokogiri/xml/builder.rb +1 -1
  46. data/lib/nokogiri/xml/document.rb +35 -4
  47. data/lib/nokogiri/xml/document_fragment.rb +5 -1
  48. data/lib/nokogiri/xml/fragment_handler.rb +28 -20
  49. data/lib/nokogiri/xml/node.rb +84 -13
  50. data/lib/nokogiri/xml/node_set.rb +19 -2
  51. data/lib/nokogiri/xml/sax/push_parser.rb +1 -1
  52. data/lib/nokogiri/xml/syntax_error.rb +10 -5
  53. data/lib/nokogiri/xslt/stylesheet.rb +1 -1
  54. data/lib/xsd/xmlparser/nokogiri.rb +20 -1
  55. data/test/css/test_parser.rb +5 -0
  56. data/test/css/test_tokenizer.rb +7 -0
  57. data/test/helper.rb +0 -5
  58. data/test/html/test_document_fragment.rb +39 -1
  59. data/test/html/test_node.rb +14 -0
  60. data/test/test_encoding_handler.rb +46 -0
  61. data/test/test_memory_leak.rb +10 -0
  62. data/test/test_nokogiri.rb +5 -1
  63. data/test/test_soap4r_sax.rb +52 -0
  64. data/test/test_xslt_transforms.rb +69 -26
  65. data/test/xml/sax/test_parser_context.rb +7 -0
  66. data/test/xml/sax/test_push_parser.rb +33 -0
  67. data/test/xml/test_document.rb +27 -1
  68. data/test/xml/test_document_fragment.rb +6 -0
  69. data/test/xml/test_node.rb +63 -214
  70. data/test/xml/test_node_reparenting.rb +261 -0
  71. data/test/xml/test_node_set.rb +51 -0
  72. data/test/xml/test_syntax_error.rb +0 -15
  73. metadata +35 -5
  74. metadata.gz.sig +0 -0
  75. data/test/test_gc.rb +0 -15
@@ -52,7 +52,10 @@ class GeneratedTokenizer < GeneratedParser
52
52
  token = case @state
53
53
  when nil
54
54
  case
55
- when (text = @ss.scan(/[-@]?([_A-Za-z]|[^\0-\177]|\\[0-9A-Fa-f]{1,6}(\r\n|[\s\n\r\t\f])?|\\[^\n\r\f0-9A-Fa-f])([_A-Za-z0-9-]|[^\0-\177]|\\[0-9A-Fa-f]{1,6}(\r\n|[\s\n\r\t\f])?|\\[^\n\r\f0-9A-Fa-f])*\(\s*/))
55
+ when (text = @ss.scan(/has\([\s\r\n\f]*/))
56
+ action { [:HAS, text] }
57
+
58
+ when (text = @ss.scan(/[-@]?([_A-Za-z]|[^\0-\177]|\\[0-9A-Fa-f]{1,6}(\r\n|[\s\n\r\t\f])?|\\[^\n\r\f0-9A-Fa-f])([_A-Za-z0-9-]|[^\0-\177]|\\[0-9A-Fa-f]{1,6}(\r\n|[\s\n\r\t\f])?|\\[^\n\r\f0-9A-Fa-f])*\([\s\r\n\f]*/))
56
59
  action { [:FUNCTION, text] }
57
60
 
58
61
  when (text = @ss.scan(/[-@]?([_A-Za-z]|[^\0-\177]|\\[0-9A-Fa-f]{1,6}(\r\n|[\s\n\r\t\f])?|\\[^\n\r\f0-9A-Fa-f])([_A-Za-z0-9-]|[^\0-\177]|\\[0-9A-Fa-f]{1,6}(\r\n|[\s\n\r\t\f])?|\\[^\n\r\f0-9A-Fa-f])*/))
@@ -2,7 +2,7 @@ class Nokogiri::CSS::GeneratedParser
2
2
 
3
3
  token FUNCTION INCLUDES DASHMATCH LBRACE HASH PLUS GREATER S STRING IDENT
4
4
  token COMMA NUMBER PREFIXMATCH SUFFIXMATCH SUBSTRINGMATCH TILDE NOT_EQUAL
5
- token SLASH DOUBLESLASH NOT EQUAL RPAREN LSQUARE RSQUARE
5
+ token SLASH DOUBLESLASH NOT EQUAL RPAREN LSQUARE RSQUARE HAS
6
6
 
7
7
  rule
8
8
  selector
@@ -112,6 +112,9 @@ rule
112
112
  | NOT expr RPAREN {
113
113
  result = Node.new(:FUNCTION, [val.first.strip, val[1]].flatten)
114
114
  }
115
+ | HAS selector RPAREN {
116
+ result = Node.new(:FUNCTION, [val.first.strip, val[1]].flatten)
117
+ }
115
118
  ;
116
119
  expr
117
120
  : NUMBER COMMA expr { result = [val.first, val.last] }
@@ -22,7 +22,8 @@ rule
22
22
 
23
23
  # [:state] pattern [actions]
24
24
 
25
- {ident}\(\s* { [:FUNCTION, text] }
25
+ has\({w} { [:HAS, text] }
26
+ {ident}\({w} { [:FUNCTION, text] }
26
27
  {ident} { [:IDENT, text] }
27
28
  \#{name} { [:HASH, text] }
28
29
  {w}~={w} { [:INCLUDES, text] }
@@ -31,6 +31,8 @@ module Nokogiri
31
31
  "last() = 1"
32
32
  when /^comment\(/
33
33
  "comment()"
34
+ when /^has\(/
35
+ node.value[1].accept(self)
34
36
  else
35
37
  args = ['.'] + node.value[1..-1]
36
38
  "#{node.value.first}#{args.join(', ')})"
@@ -0,0 +1,42 @@
1
+ module Nokogiri
2
+ class EncodingHandler
3
+ # :stopdoc:
4
+ attr_accessor :cstruct
5
+
6
+ class << self
7
+ def [](key)
8
+ handler = LibXML.xmlFindCharEncodingHandler(key)
9
+ handler.null? ? nil : wrap(handler)
10
+ end
11
+
12
+ def delete(name)
13
+ (LibXML.xmlDelEncodingAlias(name) != 0) ? nil : true
14
+ end
15
+
16
+ def alias(from, to)
17
+ LibXML.xmlAddEncodingAlias(from, to)
18
+ to
19
+ end
20
+
21
+ def clear_aliases!
22
+ LibXML.xmlCleanupEncodingAliases
23
+ self
24
+ end
25
+
26
+ private
27
+
28
+ def wrap(ptr)
29
+ cstruct = LibXML::XmlCharEncodingHandler.new(ptr)
30
+ eh = Nokogiri::EncodingHandler.allocate
31
+ eh.cstruct = cstruct
32
+ eh
33
+ end
34
+
35
+ end
36
+
37
+ def name
38
+ cstruct[:name]
39
+ end
40
+ # :startdoc:
41
+ end
42
+ end
@@ -68,16 +68,12 @@ module Nokogiri
68
68
  private
69
69
 
70
70
  def get_string_array_from(sym) # :nodoc:
71
- list = []
72
- return list if cstruct[sym].null?
73
-
74
- j = 0
75
- while (ptr = cstruct[sym].get_pointer(j * FFI.type_size(:pointer))) && ! ptr.null?
76
- list << ptr.read_string
77
- j += 1
71
+ ptr = cstruct[sym]
72
+ unless ptr.null?
73
+ ptr.get_array_of_string(0)
74
+ else
75
+ []
78
76
  end
79
-
80
- list
81
77
  end
82
78
 
83
79
  end
@@ -3,8 +3,12 @@ module Nokogiri
3
3
  module LibXML
4
4
  extend FFI::Library
5
5
  if RUBY_PLATFORM =~ /java/ && java.lang.System.getProperty('os.name') =~ /windows/i
6
- raise(RuntimeError, "Nokogiri requires JRuby 1.4.0RC1 or later on Windows") if JRUBY_VERSION < "1.4.0RC1"
7
- ffi_lib 'libxml2', 'libxslt', 'libexslt', 'msvcrt'
6
+ raise(RuntimeError, "Nokogiri requires JRuby 1.4.0 or later on Windows") if JRUBY_VERSION < "1.4.0"
7
+ dll_dir = File.expand_path(File.join(File.dirname(__FILE__), "..", "..", "..", "ext", "nokogiri"))
8
+ libs = ["libxml2.dll", "libxslt.dll", "libexslt.dll"].collect do |lib|
9
+ File.join(dll_dir, lib).tr("/","\\") # see http://jira.codehaus.org/browse/JRUBY-2763
10
+ end + ["msvcrt"]
11
+ ffi_lib(*libs)
8
12
  else
9
13
  ffi_lib 'xml2', 'xslt', 'exslt'
10
14
  end
@@ -18,6 +22,8 @@ module Nokogiri
18
22
 
19
23
  LIBXML_PARSER_VERSION = LibXML.__xmlParserVersion().read_pointer.read_string
20
24
  LIBXML_VERSION = LIBXML_PARSER_VERSION.scan(/^(.*)(..)(..)$/).first.collect{|j|j.to_i}.join(".")
25
+
26
+ LIBXML_ICONV_ENABLED = true # sigh.
21
27
  end
22
28
 
23
29
  require 'nokogiri/version'
@@ -57,6 +63,12 @@ module Nokogiri
57
63
  callback :start_element_ns_sax2_func, [:pointer, :pointer, :pointer, :pointer, :int, :pointer, :int, :int, :pointer], :void
58
64
  callback :end_element_ns_sax2_func, [:pointer, :pointer, :pointer, :pointer], :void
59
65
 
66
+ # encoding.c
67
+ attach_function :xmlFindCharEncodingHandler, [:string], :pointer
68
+ attach_function :xmlDelEncodingAlias, [:string], :int
69
+ attach_function :xmlAddEncodingAlias, [:string, :string], :int
70
+ attach_function :xmlCleanupEncodingAliases, [], :void
71
+
60
72
  # HTMLparser.c
61
73
  attach_function :htmlReadMemory, [:string, :int, :string, :string, :int], :pointer
62
74
  attach_function :htmlReadIO, [:io_read_callback, :io_close_callback, :pointer, :string, :string, :int], :pointer
@@ -88,6 +100,7 @@ module Nokogiri
88
100
  attach_function :xmlFreeParserCtxt, [:pointer], :void
89
101
  attach_function :xmlCreatePushParserCtxt, [:pointer, :pointer, :string, :int, :string], :pointer
90
102
  attach_function :xmlParseChunk, [:pointer, :string, :int, :int], :int
103
+ attach_function :xmlCtxtUseOptions, [:pointer, :int], :int
91
104
 
92
105
  # tree.c
93
106
  attach_function :xmlNewDoc, [:string], :pointer
@@ -131,7 +144,7 @@ module Nokogiri
131
144
  attach_function :xmlGetIntSubset, [:pointer], :pointer
132
145
  attach_function :xmlBufferCreate, [], :pointer
133
146
  attach_function :xmlBufferFree, [:pointer], :void
134
- attach_function :xmlSplitQName2, [:string, :pointer], :pointer # returns char* that must be freed
147
+ attach_function :xmlSplitQName2, [:string, :buffer_out], :pointer # returns char* that must be freed
135
148
  attach_function :xmlNewDocProp, [:pointer, :string, :string], :pointer
136
149
  attach_function :xmlFreePropList, [:pointer], :void
137
150
  attach_function :xmlCreateIntSubset, [:pointer] * 4, :pointer
@@ -245,7 +258,7 @@ module Nokogiri
245
258
  attach_function :xsltParseStylesheetDoc, [:pointer], :pointer
246
259
  attach_function :xsltFreeStylesheet, [:pointer], :void
247
260
  attach_function :xsltApplyStylesheet, [:pointer, :pointer, :pointer], :pointer
248
- attach_function :xsltSaveResultToString, [:pointer, :pointer, :pointer, :pointer], :int
261
+ attach_function :xsltSaveResultToString, [:buffer_out, :buffer_out, :pointer, :pointer], :int
249
262
  attach_function :xsltSetGenericErrorFunc, [:pointer, :generic_error_handler], :void
250
263
 
251
264
  # exslt.c
@@ -281,8 +294,9 @@ module Nokogiri
281
294
  attach_function :xmlSwitchEncoding, [:pointer, :int], :void
282
295
 
283
296
  # helpers
297
+ POINTER_SIZE = FFI.type_size(:pointer)
284
298
  def self.pointer_offset(n)
285
- n * FFI.type_size(:pointer) # byte offset of nth pointer in an array of pointers
299
+ n * POINTER_SIZE # byte offset of nth pointer in an array of pointers
286
300
  end
287
301
  end
288
302
  end
@@ -293,8 +307,10 @@ require 'nokogiri/syntax_error'
293
307
  require 'nokogiri/xml/syntax_error'
294
308
 
295
309
  [ "io_callbacks",
310
+ "encoding_handler",
296
311
  "structs/common_node",
297
312
  "structs/xml_alloc",
313
+ "structs/xml_char_encoding_handler",
298
314
  "structs/xml_document",
299
315
  "structs/xml_node",
300
316
  "structs/xml_dtd",
@@ -0,0 +1,11 @@
1
+ module Nokogiri
2
+ module LibXML # :nodoc:
3
+ class XmlCharEncodingHandler < FFI::Struct # :nodoc:
4
+ layout(
5
+ :name, :string,
6
+ :input, :pointer,
7
+ :output, :pointer
8
+ )
9
+ end
10
+ end
11
+ end
@@ -47,12 +47,12 @@ module Nokogiri
47
47
  end
48
48
 
49
49
  def unlinked_nodes
50
- LibXML::XmlNodeSetCast.new(self[:_private].get_pointer(FFI.type_size(:pointer)))
50
+ LibXML::XmlNodeSetCast.new(self[:_private].get_pointer(LibXML.pointer_offset(1)))
51
51
  end
52
52
 
53
53
  def alloc_tuple
54
- self[:_private] = LibXML.calloc(FFI.type_size(:pointer), 2)
55
- self[:_private].put_pointer(FFI.type_size(:pointer), LibXML.xmlXPathNodeSetCreate(nil))
54
+ self[:_private] = LibXML.calloc(LibXML::POINTER_SIZE, 2)
55
+ self[:_private].put_pointer(LibXML.pointer_offset(1), LibXML.xmlXPathNodeSetCreate(nil))
56
56
  end
57
57
  end
58
58
 
@@ -3,7 +3,116 @@ module Nokogiri
3
3
  module LibXML
4
4
  class XmlSaxPushParserContext < FFI::ManagedStruct
5
5
 
6
- layout :dummy, :int, 0 # to avoid @layout warnings
6
+ layout(
7
+ :sax, :pointer, # struct _xmlSAXHandler *sax; /* The SAX handler */
8
+ :userData, :pointer, # void *userData; /* For SAX interface only, used by DOM build */
9
+ :myDoc, :pointer, # xmlDocPtr myDoc; /* the document being built */
10
+ :wellFormed, :int, # int wellFormed; /* is the document well formed */
11
+ :replaceEntities, :int, # int replaceEntities; /* shall we replace entities ? */
12
+ :version, :pointer, # const xmlChar *version; /* the XML version string */
13
+ :encoding, :pointer, # const xmlChar *encoding; /* the declared encoding, if any */
14
+ :standalone, :int, # int standalone; /* standalone document */
15
+ :html, :int, # int html; /* an HTML(1)/Docbook(2) document
16
+
17
+ :input, :pointer, # xmlParserInputPtr input; /* Current input stream */
18
+ :inputNr, :int, # int inputNr; /* Number of current input streams */
19
+ :inputMax, :int, # int inputMax; /* Max number of input streams */
20
+ :inputTab, :pointer, # xmlParserInputPtr *inputTab; /* stack of inputs */
21
+
22
+ :node, :pointer, # xmlNodePtr node; /* Current parsed Node */
23
+ :nodeNr, :int, # int nodeNr; /* Depth of the parsing stack */
24
+ :nodeMax, :int, # int nodeMax; /* Max depth of the parsing stack */
25
+ :nodeTab, :pointer, # xmlNodePtr *nodeTab; /* array of nodes */
26
+
27
+ :record_info, :int, # int record_info; /* Whether node info should be kept */
28
+
29
+ # xmlParserNodeInfoSeq node_seq; /* info about each node parsed */
30
+ :node_seq_maximum, :ulong,
31
+ :node_seq_length, :ulong,
32
+ :node_seq_buffer, :pointer,
33
+
34
+ :errNo, :int, # int errNo; /* error code */
35
+
36
+ :hasExternalSubset, :int, # int hasExternalSubset; /* reference and external subset */
37
+ :hasPErefs, :int, # int hasPErefs; /* the internal subset has PE refs */
38
+ :external, :int, # int external; /* are we parsing an external entity */
39
+
40
+ :valid, :int, # int valid; /* is the document valid */
41
+ :validate, :int, # int validate; /* shall we try to validate ? */
42
+
43
+ # xmlValidCtxt vctxt; /* The validity context */
44
+ :vctxt_userData, :pointer, # void *userData; /* user specific data block */
45
+ :vctxt_error, :pointer, # xmlValidityErrorFunc error; /* the callback in case of errors */
46
+ :vctxt_warning, :pointer, # xmlValidityWarningFunc warning; /* the callback in case of warning */
47
+ :vctxt_node, :pointer, # xmlNodePtr node; /* Current parsed Node */
48
+ :vctxt_nodeNr, :int, # int nodeNr; /* Depth of the parsing stack */
49
+ :vctxt_nodeMax, :int, # int nodeMax; /* Max depth of the parsing stack */
50
+ :vctxt_nodeTab, :pointer, # xmlNodePtr *nodeTab; /* array of nodes */
51
+
52
+ :vctxt_finishDtd, :int, # unsigned int finishDtd; /* finished validating the Dtd ? */
53
+ :vctxt_doc, :pointer, # xmlDocPtr doc; /* the document */
54
+ :vctxt_valid, :int, # int valid; /* temporary validity check result */
55
+ :vctxt_vstate, :pointer, # xmlValidState *vstate; /* current state */
56
+ :vctxt_vstatNr, :int, # int vstateNr; /* Depth of the validation stack */
57
+ :vctxt_vstateMax, :int, # int vstateMax; /* Max depth of the validation stack */
58
+ :vctxt_vstateTab, :pointer, # xmlValidState *vstateTab; /* array of validation states */
59
+ :vctxt_am, :pointer, # xmlAutomataPtr am; /* the automata */
60
+ :vctxt_state, :pointer, # xmlAutomataStatePtr state; /* used to build the automata */
61
+
62
+ :instate, :int, # xmlParserInputState instate; /* current type of input */
63
+ :token, :int, # int token; /* next char look-ahead */
64
+
65
+ :directory, :pointer, # char *directory; /* the data directory */
66
+ :name, :pointer, # const xmlChar *name; /* Current parsed Node */
67
+ :nameNr, :int, # int nameNr; /* Depth of the parsing stack */
68
+ :nameMax, :int, # int nameMax; /* Max depth of the parsing stack */
69
+ :nameTab, :pointer, # const xmlChar * *nameTab; /* array of nodes */
70
+
71
+ :nbChars, :long, # long nbChars; /* number of xmlChar processed */
72
+ :checkIndex, :long, # long checkIndex; /* used by progressive parsing lookup */
73
+ :keepBlanks, :int, # int keepBlanks; /* ugly but ... */
74
+ :disableSAX, :int, # int disableSAX; /* SAX callbacks are disabled */
75
+ :inSubset, :int, # int inSubset; /* Parsing is in int 1/ext 2 subset */
76
+ :intSubName, :pointer, # const xmlChar * intSubName; /* name of subset */
77
+ :extSubURI, :pointer, # xmlChar * extSubURI; /* URI of external subset */
78
+ :extSubSystem, :pointer, # xmlChar * extSubSystem; /* SYSTEM ID of external subset */
79
+
80
+ :space, :pointer, # int * space; /* Should the parser preserve spaces */
81
+ :spaceNr, :int, # int spaceNr; /* Depth of the parsing stack */
82
+ :spaceMax, :int, # int spaceMax; /* Max depth of the parsing stack */
83
+ :spaceTab, :pointer, # int * spaceTab; /* array of space infos */
84
+ :depth, :int, # int depth; /* to prevent entity substitution loops */
85
+ :entity, :pointer, # xmlParserInputPtr entity; /* used to check entities boundaries */
86
+ :charset, :int, # int charset; /* encoding of the in-memory content
87
+ :nodelen, :int, # int nodelen; /* Those two fields are there to */
88
+ :nodemem, :int, # int nodemem; /* Speed up large node parsing */
89
+ :pedantic, :int, # int pedantic; /* signal pedantic warnings */
90
+ :_private, :pointer, # void *_private; /* For user data, libxml won't touch it */
91
+
92
+ :loadsubset, :int, # int loadsubset; /* should the external subset be loaded */
93
+ :linenumbers, :int, # int linenumbers; /* set line number in element content */
94
+ :catalogs, :pointer, # void *catalogs; /* document's own catalog */
95
+ :recovery, :int, # int recovery; /* run in recovery mode */
96
+ :progressive, :int, # int progressive; /* is this a progressive parsing */
97
+ :dict, :pointer, # xmlDictPtr dict; /* dictionnary for the parser */
98
+ :atts, :pointer, # const xmlChar * *atts; /* array for the attributes callbacks */
99
+ :maxatts, :int, # int maxatts; /* the size of the array */
100
+ :docdict, :int, # int docdict; /* use strings from dict to build tree */
101
+ :str_xml, :pointer, # const xmlChar *str_xml;
102
+ :str_xmlns, :pointer, # const xmlChar *str_xmlns;
103
+ :str_xml_ns, :pointer, # const xmlChar *str_xml_ns;
104
+
105
+ :sax2, :int, # int sax2; /* operating in the new SAX mode */
106
+ :nsNr, :int, # int nsNr; /* the number of inherited namespaces */
107
+ :nsMax, :int, # int nsMax; /* the size of the arrays */
108
+ :nsTab, :pointer, # const xmlChar * *nsTab; /* the array of prefix/namespace name */
109
+ :attallocs, :pointer, # int *attallocs; /* which attribute were allocated */
110
+ :pushTab, :pointer, # void * *pushTab; /* array of data for push */
111
+ :attsDefault, :pointer, # xmlHashTablePtr attsDefault; /* defaulted attributes if any */
112
+ :attsSpecial, :pointer, # xmlHashTablePtr attsSpecial; /* non-CDATA attributes if any */
113
+ :nsWellFormed, :int, # int nsWellFormed; /* is the document XML Nanespace okay */
114
+ :options, :int # int options; /* Extra options */
115
+ )
7
116
 
8
117
  def self.release ptr
9
118
  LibXML.xmlFreeParserCtxt(ptr)
@@ -41,12 +41,11 @@ module Nokogiri
41
41
  return nil if attr_ptr.null?
42
42
 
43
43
  ahash = {}
44
- proc = lambda do |payload, data, name|
44
+ LibXML.xmlHashScan(attr_ptr, nil) do |payload, data, name|
45
45
  notation_cstruct = LibXML::XmlNotation.new(payload)
46
46
  ahash[name] = Notation.new(notation_cstruct[:name], notation_cstruct[:PublicID],
47
47
  notation_cstruct[:SystemID])
48
48
  end
49
- LibXML.xmlHashScan(attr_ptr, proc, nil)
50
49
  ahash
51
50
  end
52
51
 
@@ -57,10 +56,9 @@ module Nokogiri
57
56
  return nil if attr_ptr.null?
58
57
 
59
58
  ahash = {}
60
- proc = lambda do |payload, data, name|
59
+ LibXML.xmlHashScan(attr_ptr, nil) do |payload, data, name|
61
60
  ahash[name] = Node.wrap(payload)
62
61
  end
63
- LibXML.xmlHashScan(attr_ptr, proc, nil)
64
62
  ahash
65
63
  end
66
64
  end
@@ -77,9 +77,39 @@ module Nokogiri
77
77
  cstruct_node_from :prev
78
78
  end
79
79
 
80
- def replace_with_node(new_node)
81
- LibXML.xmlReplaceNode(cstruct, new_node.cstruct)
82
- Node.send(:relink_namespace, new_node.cstruct)
80
+ def next_element
81
+ sibling_ptr = cstruct[:next]
82
+
83
+ while ! sibling_ptr.null?
84
+ sibling_cstruct = LibXML::XmlNode.new(sibling_ptr)
85
+ break if sibling_cstruct[:type] == ELEMENT_NODE
86
+ sibling_ptr = sibling_cstruct[:next]
87
+ end
88
+
89
+ return sibling_ptr.null? ? nil : Node.wrap(sibling_ptr)
90
+ end
91
+
92
+ def previous_element
93
+ sibling_ptr = cstruct[:prev]
94
+
95
+ while ! sibling_ptr.null?
96
+ sibling_cstruct = LibXML::XmlNode.new(sibling_ptr)
97
+ break if sibling_cstruct[:type] == ELEMENT_NODE
98
+ sibling_ptr = sibling_cstruct[:prev]
99
+ end
100
+
101
+ return sibling_ptr.null? ? nil : Node.wrap(sibling_ptr)
102
+ end
103
+
104
+ def replace_node new_node
105
+ Node.reparent_node_with(new_node, self) do |new_node_cstruct, self_cstruct|
106
+ retval = LibXML.xmlReplaceNode(self_cstruct, new_node_cstruct)
107
+ if retval == self_cstruct.pointer
108
+ new_node_cstruct # for reparent_node_with semantics
109
+ else
110
+ retval
111
+ end
112
+ end
83
113
  self
84
114
  end
85
115
 
@@ -114,7 +144,7 @@ module Nokogiri
114
144
  def namespaced_key?(attribute, namespace)
115
145
  prop = LibXML.xmlHasNsProp(cstruct, attribute.to_s,
116
146
  namespace.nil? ? nil : namespace.to_s)
117
- prop.null? ? false : true
147
+ !prop.null?
118
148
  end
119
149
 
120
150
  def []=(property, value)
@@ -184,7 +214,7 @@ module Nokogiri
184
214
  content
185
215
  end
186
216
 
187
- def add_child(child)
217
+ def add_child_node child
188
218
  Node.reparent_node_with(child, self) do |child_cstruct, my_cstruct|
189
219
  LibXML.xmlAddChild(my_cstruct, child_cstruct)
190
220
  end
@@ -210,13 +240,13 @@ module Nokogiri
210
240
  val
211
241
  end
212
242
 
213
- def add_next_sibling(next_sibling)
243
+ def add_next_sibling_node next_sibling
214
244
  Node.reparent_node_with(next_sibling, self) do |sibling_cstruct, my_cstruct|
215
245
  LibXML.xmlAddNextSibling(my_cstruct, sibling_cstruct)
216
246
  end
217
247
  end
218
248
 
219
- def add_previous_sibling(prev_sibling)
249
+ def add_previous_sibling_node prev_sibling
220
250
  Node.reparent_node_with(prev_sibling, self) do |sibling_cstruct, my_cstruct|
221
251
  LibXML.xmlAddPrevSibling(my_cstruct, sibling_cstruct)
222
252
  end
@@ -348,15 +378,6 @@ module Nokogiri
348
378
  raise(ArgumentError, "node must be a Nokogiri::XML::Node") unless node.is_a?(Nokogiri::XML::Node)
349
379
  raise(ArgumentError, "cannot reparent a document node") if node.node_type == DOCUMENT_NODE || node.node_type == HTML_DOCUMENT_NODE
350
380
 
351
- # If a document fragment is added, we need to reparent all of it's
352
- # children
353
- if node.type == DOCUMENT_FRAG_NODE
354
- node.children.each do |child|
355
- reparent_node_with(child, other, &block)
356
- end
357
- return node
358
- end
359
-
360
381
  if node.type == TEXT_NODE
361
382
  node.cstruct.keep_reference_from_document!
362
383
  node.cstruct = LibXML::XmlNode.new(LibXML.xmlDocCopyNode(node.cstruct, other.cstruct.document, 1))
@@ -378,7 +399,7 @@ module Nokogiri
378
399
  node.cstruct.keep_reference_from_document!
379
400
  end
380
401
 
381
- reparented_struct = LibXML::XmlNode.new(reparented_struct)
402
+ reparented_struct = LibXML::XmlNode.new(reparented_struct) if reparented_struct.is_a?(FFI::Pointer)
382
403
 
383
404
  # the child was a text node that was coalesced. we need to have the object
384
405
  # point at SOMETHING, or we'll totally bomb out.