ox 1.4.2 → 1.4.3

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

Potentially problematic release.


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

data/README.md CHANGED
@@ -26,10 +26,10 @@ A fast XML parser and Object marshaller as a Ruby gem.
26
26
 
27
27
  ## <a name="release">Release Notes</a>
28
28
 
29
- ### Release 1.4.2
29
+ ### Release 1.4.3
30
30
 
31
- - Made Ox more tolerant when parsing invalid XML files without a prolog.
32
- - DOCTYPE value was one character too long.
31
+ - In tolerant mode attribute values can now be surrounded by single quotes.
32
+ - In tolerant mode attribute values can now be without quotes as long as they do not contain spaces and are followed by a white space character.
33
33
 
34
34
  ## <a name="description">Description</a>
35
35
 
data/ext/ox/ox.c CHANGED
@@ -355,16 +355,16 @@ load(char *xml, int argc, VALUE *argv, VALUE self) {
355
355
  obj = parse(xml, ox_obj_callbacks, 0, options.trace, options.effort);
356
356
  break;
357
357
  case GenMode:
358
- obj = parse(xml, ox_gen_callbacks, 0, options.trace, StrictEffort);
358
+ obj = parse(xml, ox_gen_callbacks, 0, options.trace, options.effort);
359
359
  break;
360
360
  case LimMode:
361
- obj = parse(xml, ox_limited_callbacks, 0, options.trace, StrictEffort);
361
+ obj = parse(xml, ox_limited_callbacks, 0, options.trace, options.effort);
362
362
  break;
363
363
  case NoMode:
364
364
  obj = parse(xml, ox_nomode_callbacks, 0, options.trace, options.effort);
365
365
  break;
366
366
  default:
367
- obj = parse(xml, ox_gen_callbacks, 0, options.trace, StrictEffort);
367
+ obj = parse(xml, ox_gen_callbacks, 0, options.trace, options.effort);
368
368
  break;
369
369
  }
370
370
  free(xml);
data/ext/ox/parse.c CHANGED
@@ -78,6 +78,23 @@ next_non_white(PInfo pi) {
78
78
  }
79
79
  }
80
80
 
81
+ inline static void
82
+ next_white(PInfo pi) {
83
+ for (; 1; pi->s++) {
84
+ switch(*pi->s) {
85
+ case ' ':
86
+ case '\t':
87
+ case '\f':
88
+ case '\n':
89
+ case '\r':
90
+ case '\0':
91
+ return;
92
+ default:
93
+ break;
94
+ }
95
+ }
96
+ }
97
+
81
98
  VALUE
82
99
  parse(char *xml, ParseCallbacks pcb, char **endp, int trace, Effort effort) {
83
100
  struct _PInfo pi;
@@ -599,26 +616,53 @@ read_cdata(PInfo pi) {
599
616
  }
600
617
  }
601
618
 
619
+ inline static void
620
+ next_non_token(PInfo pi) {
621
+ for (; 1; pi->s++) {
622
+ switch(*pi->s) {
623
+ case ' ':
624
+ case '\t':
625
+ case '\f':
626
+ case '\n':
627
+ case '\r':
628
+ case '/':
629
+ case '>':
630
+ return;
631
+ default:
632
+ break;
633
+ }
634
+ }
635
+ }
636
+
602
637
  /* Assume the value starts immediately and goes until the quote character is
603
638
  * reached again. Do not read the character after the terminating quote.
604
639
  */
605
640
  static char*
606
641
  read_quoted_value(PInfo pi) {
607
- char *value;
642
+ char *value = 0;
608
643
 
609
- if ('"' != *pi->s) {
644
+ if ('"' == *pi->s || ('\'' == *pi->s && StrictEffort != pi->effort)) {
645
+ char term = *pi->s;
646
+
647
+ pi->s++; // skip quote character
648
+ value = pi->s;
649
+ for (; *pi->s != term; pi->s++) {
650
+ if ('\0' == *pi->s) {
651
+ raise_error("invalid format, document not terminated", pi->str, pi->s);
652
+ }
653
+ }
654
+ *pi->s = '\0'; // terminate value
655
+ pi->s++; // move past quote
656
+ } else if (StrictEffort == pi->effort) {
610
657
  raise_error("invalid format, expected a quote character", pi->str, pi->s);
611
- }
612
- pi->s++; // skip quote character
613
- value = pi->s;
614
- for (; *pi->s != '"'; pi->s++) {
658
+ } else {
659
+ value = pi->s;
660
+ next_white(pi);
615
661
  if ('\0' == *pi->s) {
616
662
  raise_error("invalid format, document not terminated", pi->str, pi->s);
617
- }
663
+ }
664
+ *pi->s++ = '\0'; // terminate value
618
665
  }
619
- *pi->s = '\0'; // terminate value
620
- pi->s++; // move past quote
621
-
622
666
  return value;
623
667
  }
624
668
 
data/ext/ox/sax.c CHANGED
@@ -131,6 +131,29 @@ next_non_white(SaxDrive dr) {
131
131
  return '\0';
132
132
  }
133
133
 
134
+ /* Starts by reading a character so it is safe to use with an empty or
135
+ * compacted buffer.
136
+ */
137
+ inline static char
138
+ next_white(SaxDrive dr) {
139
+ char c;
140
+
141
+ while ('\0' != (c = sax_drive_get(dr))) {
142
+ switch(c) {
143
+ case ' ':
144
+ case '\t':
145
+ case '\f':
146
+ case '\n':
147
+ case '\r':
148
+ case '\0':
149
+ return c;
150
+ default:
151
+ break;
152
+ }
153
+ }
154
+ return '\0';
155
+ }
156
+
134
157
  inline static int
135
158
  is_white(char c) {
136
159
  switch(c) {
@@ -727,19 +750,23 @@ read_quoted_value(SaxDrive dr) {
727
750
  if (is_white(c)) {
728
751
  c = next_non_white(dr);
729
752
  }
730
- if ('"' != c) {
731
- sax_drive_error(dr, "invalid format, attibute value not in quotes", 1);
732
- return -1;
733
- }
734
- dr->str = dr->cur;
735
- while ('"' != (c = sax_drive_get(dr))) {
736
- if ('\0' == c) {
737
- sax_drive_error(dr, "invalid format, quoted value not terminated", 1);
738
- return -1;
753
+ if ('"' == c || '\'' == c) {
754
+ char term = c;
755
+
756
+ dr->str = dr->cur;
757
+ while (term != (c = sax_drive_get(dr))) {
758
+ if ('\0' == c) {
759
+ sax_drive_error(dr, "invalid format, quoted value not terminated", 1);
760
+ return -1;
761
+ }
739
762
  }
740
- }
763
+ } else {
764
+ dr->str = dr->cur - 1;
765
+ if ('\0' == (c = next_white(dr))) {
766
+ sax_drive_error(dr, "invalid format, attibute value not in quotes", 1);
767
+ }
768
+ }
741
769
  *(dr->cur - 1) = '\0'; // terminate value
742
-
743
770
  return 0;
744
771
  }
745
772
 
data/lib/ox/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
 
2
2
  module Ox
3
3
  # Current version of the module.
4
- VERSION = '1.4.2'
4
+ VERSION = '1.4.3'
5
5
  end
data/test/bug3.rb CHANGED
@@ -3,21 +3,19 @@
3
3
  $: << '../lib'
4
4
  $: << '../ext'
5
5
 
6
- if __FILE__ == $0
7
- if (i = ARGV.index('-I'))
8
- x,path = ARGV.slice!(i, 2)
9
- $: << path
10
- end
11
- end
12
-
13
6
  require 'ox'
14
7
 
15
- def dump(cnt = 100000)
16
- cnt.times do |i|
17
- xml = Ox.dump([:inc, 1])
18
- #puts xml
19
-
8
+ def name_it()
9
+ begin
10
+ "x".foo
11
+ rescue Exception => e
12
+ #puts e.message
13
+ xml = Ox.dump(e, effort: :tolerant)
14
+ puts xml
15
+ o = Ox.load(xml, mode: :object)
16
+ puts o.message
17
+ puts Ox.dump(e)
20
18
  end
21
19
  end
22
20
 
23
- dump()
21
+ name_it()
data/test/func.rb CHANGED
@@ -222,6 +222,24 @@ class Func < ::Test::Unit::TestCase
222
222
  assert_equal('html', doc.nodes[0].value)
223
223
  end
224
224
 
225
+ def test_quote_value
226
+ xml = %{<top name="Pete"/>}
227
+ doc = Ox.parse(xml)
228
+ assert_equal('Pete', doc.attributes[:name])
229
+ end
230
+
231
+ def test_single_quote
232
+ xml = %{<top name='Pete'/>}
233
+ doc = Ox.load(xml, :effort => :tolerant)
234
+ assert_equal('Pete', doc.attributes[:name])
235
+ end
236
+
237
+ def test_no_quote
238
+ xml = %{<top name=Pete />}
239
+ doc = Ox.load(xml, :effort => :tolerant)
240
+ assert_equal('Pete', doc.attributes[:name])
241
+ end
242
+
225
243
  def test_class
226
244
  dump_and_load(Bag, false)
227
245
  end
@@ -0,0 +1,37 @@
1
+ #!/usr/bin/env ruby -wW1
2
+
3
+ $: << '../lib'
4
+ $: << '../ext'
5
+
6
+ require 'stringio'
7
+ require 'ox'
8
+
9
+ class Sample < ::Ox::Sax
10
+ def start_element(name); puts "start: #{name}"; end
11
+ def end_element(name); puts "end: #{name}"; end
12
+ def attr(name, value); puts " #{name} => #{value}"; end
13
+ def text(value); puts "text #{value}"; end
14
+ end
15
+
16
+ io = StringIO.new(%{
17
+ <top name="sample">
18
+ <middle name="second">
19
+ <bottom name="third"/>
20
+ </middle>
21
+ </top>
22
+ })
23
+
24
+ handler = Sample.new()
25
+ Ox.sax_parse(handler, io)
26
+
27
+ # outputs
28
+ # start: top
29
+ # name => sample
30
+ # start: middle
31
+ # name => second
32
+ # start: bottom
33
+ # name => third
34
+ # end: bottom
35
+ # end: middle
36
+ # end: top
37
+
data/test/sax_test.rb CHANGED
@@ -127,10 +127,11 @@ encoding = "UTF-8" ?>},
127
127
  end
128
128
 
129
129
  def test_sax_element_attrs
130
- parse_compare(%{<top x="57" y="42"/>},
130
+ parse_compare(%{<top x="57" y='42' z=33 />},
131
131
  [[:start_element, :top],
132
132
  [:attr, :x, "57"],
133
133
  [:attr, :y, "42"],
134
+ [:attr, :z, "33"],
134
135
  [:end_element, :top]])
135
136
  end
136
137
 
metadata CHANGED
@@ -1,24 +1,28 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: ox
3
- version: !ruby/object:Gem::Version
4
- version: 1.4.2
3
+ version: !ruby/object:Gem::Version
5
4
  prerelease:
5
+ version: 1.4.3
6
6
  platform: ruby
7
- authors:
7
+ authors:
8
8
  - Peter Ohler
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2011-12-03 00:00:00.000000000Z
12
+
13
+ date: 2011-12-08 00:00:00 +09:00
14
+ default_executable:
13
15
  dependencies: []
16
+
14
17
  description: A fast XML parser and object serializer that uses only standard C lib.
15
18
  email: peter@ohler.com
16
19
  executables: []
17
- extensions:
20
+
21
+ extensions:
18
22
  - ext/ox/extconf.rb
19
- extra_rdoc_files:
23
+ extra_rdoc_files:
20
24
  - README.md
21
- files:
25
+ files:
22
26
  - lib/ox/bag.rb
23
27
  - lib/ox/cdata.rb
24
28
  - lib/ox/comment.rb
@@ -47,11 +51,9 @@ files:
47
51
  - ext/ox/parse.c
48
52
  - ext/ox/sax.c
49
53
  - test/bench.rb
50
- - test/big.rb
51
54
  - test/bug1.rb
52
55
  - test/bug2.rb
53
56
  - test/bug3.rb
54
- - test/bug4.rb
55
57
  - test/cache16_test.rb
56
58
  - test/cache8_test.rb
57
59
  - test/cache_test.rb
@@ -79,36 +81,41 @@ files:
79
81
  - test/perf_sax.rb
80
82
  - test/perf_write.rb
81
83
  - test/sample.rb
84
+ - test/sax_example.rb
82
85
  - test/sax_test.rb
83
86
  - test/test.rb
84
87
  - test/Sample.graffle
85
88
  - LICENSE
86
89
  - README.md
90
+ has_rdoc: true
87
91
  homepage: https://github.com/ohler55/ox
88
92
  licenses: []
93
+
89
94
  post_install_message:
90
- rdoc_options:
95
+ rdoc_options:
91
96
  - --main
92
97
  - README.md
93
- require_paths:
98
+ require_paths:
94
99
  - lib
95
100
  - ext
96
- required_ruby_version: !ruby/object:Gem::Requirement
101
+ required_ruby_version: !ruby/object:Gem::Requirement
97
102
  none: false
98
- requirements:
99
- - - ! '>='
100
- - !ruby/object:Gem::Version
101
- version: '0'
102
- required_rubygems_version: !ruby/object:Gem::Requirement
103
+ requirements:
104
+ - - ">="
105
+ - !ruby/object:Gem::Version
106
+ version: "0"
107
+ required_rubygems_version: !ruby/object:Gem::Requirement
103
108
  none: false
104
- requirements:
105
- - - ! '>='
106
- - !ruby/object:Gem::Version
107
- version: '0'
109
+ requirements:
110
+ - - ">="
111
+ - !ruby/object:Gem::Version
112
+ version: "0"
108
113
  requirements: []
114
+
109
115
  rubyforge_project: ox
110
- rubygems_version: 1.8.10
116
+ rubygems_version: 1.6.2
111
117
  signing_key:
112
118
  specification_version: 3
113
119
  summary: A fast XML parser and object serializer.
114
120
  test_files: []
121
+
data/test/big.rb DELETED
@@ -1,24 +0,0 @@
1
- #!/usr/bin/env ruby -wW1
2
-
3
- $: << '../lib'
4
- $: << '../ext'
5
-
6
- if __FILE__ == $0
7
- while (i = ARGV.index('-I'))
8
- x,path = ARGV.slice!(i, 2)
9
- $: << path
10
- end
11
- end
12
-
13
- require 'ox'
14
-
15
- def dump(cnt = 10000)
16
- h = { }
17
- cnt.times do |i|
18
- h[i] = [i * 2, "this is #{i}"]
19
- end
20
- xml = Ox.dump(h)
21
- puts "size: #{xml.size}"
22
- end
23
-
24
- dump(200000)
data/test/bug4.rb DELETED
@@ -1,11 +0,0 @@
1
- #!/usr/bin/env ruby -wW1
2
-
3
- $: << '../lib'
4
- $: << '../ext'
5
-
6
- require 'ox'
7
-
8
- #xml = File.read('bug4.xml')
9
- xml = File.read('bug4.xml')
10
-
11
- doc = Ox.parse(xml)