yajl-ruby 0.5.11 → 0.5.12

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of yajl-ruby might be problematic. Click here for more details.

data/CHANGELOG.md CHANGED
@@ -1,5 +1,9 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.5.12 (July 31st, 2009)
4
+ * Add another option that can be passed to Yajl::Encoder's constructor (:terminator) to allow the caller some control over
5
+ when a full JSON string has been generated by the encoder. More information on it's use in the README
6
+
3
7
  ## 0.5.11 (July 14th, 2009)
4
8
  * fixing a bug Aman found with to_json on non-primitive Ruby objects and double-quoting in the JSON compat API
5
9
 
data/README.rdoc CHANGED
@@ -1,6 +1,6 @@
1
1
  = YAJL C Bindings for Ruby
2
2
 
3
- This gem (although not in gem form just yet) is a C binding to the excellent YAJL JSON parsing and generation library.
3
+ This gem is a C binding to the excellent YAJL JSON parsing and generation library.
4
4
 
5
5
  You can read more info at the projects website http://lloydforge.org/projects/yajl or check out it's codes at http://github.com/lloyd/yajl.
6
6
 
@@ -27,6 +27,8 @@ Install it like any other gem hosted at the Githubs like so:
27
27
 
28
28
  == Example of use
29
29
 
30
+ NOTE: I'm building up a collection of small examples in the examples (http://github.com/brianmario/yajl-ruby/tree/master/examples) folder.
31
+
30
32
  First, you're probably gonna want to require it:
31
33
 
32
34
  require 'yajl'
@@ -77,6 +79,11 @@ only had access to chunks of it at a time. No problem!
77
79
  @parser << data
78
80
  end
79
81
 
82
+ Or if you don't need to stream it, it'll just return the built object from the parse when it's done.
83
+ NOTE: if there are going to be multiple JSON strings in the input, you *must* specify a block or callback as this
84
+ is how yajl-ruby will hand you (the caller) each object as it's parsed off the input.
85
+
86
+ obj = Yajl::Parser.parse(str_or_io)
80
87
 
81
88
  Or how about a JSON API HTTP request?
82
89
  This actually makes a request using a raw TCPSocket, then parses the JSON body right off the socket. While it's being received over the wire!
@@ -150,6 +157,42 @@ This example will encode and send 50 JSON objects over the same stream, continuo
150
157
  encoder.encode(hash, socket)
151
158
  end
152
159
 
160
+ Using EventMachine and you want to encode and send in chunks?
161
+ (Assume we're in an EventMachine::Connection instance)
162
+
163
+ def post_init
164
+ # Passing a :terminator character will let us determine when the encoder
165
+ # is done encoding the current object
166
+ @encoder = Yajl::Encoder.new(:terminator => nil)
167
+ motd_contents = File.read("/path/to/motd.txt")
168
+ status = File.read("/path/to/huge/status_file.txt")
169
+ @motd = {:motd => motd_contents, :system_status => status}
170
+ end
171
+
172
+ def connection_completed
173
+ # The encoder will do it's best to hand you data in chunks that
174
+ # are around 8kb (but you may see some that are larger)
175
+ #
176
+ # It should be noted that you could have also assigned the _on_progress_ callback
177
+ # much like you can assign the _on_parse_complete_ callback with the parser class.
178
+ # Passing a block (like below) essentially tells the encoder to use that block
179
+ # as the callback normally assigned to _on_progress_.
180
+ #
181
+ # Send our MOTD and status
182
+ @encoder.encode(@motd) do |chunk|
183
+ if chunk.nil?
184
+ close_connection_after_writing
185
+ else
186
+ send_data(chunk)
187
+ end
188
+ end
189
+ end
190
+
191
+ But to make things simple, you might just want to let yajl-ruby do all the hard work for you and just hand back
192
+ a string when it's finished. In that case, just don't provide and IO or block (or assign the on_progress callback).
193
+
194
+ str = Yajl::Encoder.encode(obj)
195
+
153
196
  You can also use Yajl::Bzip2::StreamWriter and Yajl::Deflate::StreamWriter. So you can pick whichever fits your CPU/bandwidth sweet-spot.
154
197
 
155
198
  == JSON gem Compatibility API
@@ -174,7 +217,7 @@ There are a lot more possibilities that I'd love to see other gems/plugins for s
174
217
  Some ideas are:
175
218
  * parsing logs in JSON format
176
219
  * a Rails plugin (http://github.com/technoweenie/yajl-rails)
177
- * builtin Rails 3 support?
220
+ * builtin support in Rails 3?
178
221
  * Rack middleware (ideally the JSON body could be handed to the parser while it's still being received)
179
222
  * use with ohai (http://github.com/brianmario/ohai)
180
223
  * JSON API clients (http://github.com/brianmario/crack, http://github.com/brianmario/freckle-api)
data/VERSION.yml CHANGED
@@ -1,4 +1,4 @@
1
1
  ---
2
- :patch: 11
3
- :major: 0
4
2
  :minor: 5
3
+ :patch: 12
4
+ :major: 0
data/ext/yajl_ext.c CHANGED
@@ -69,6 +69,7 @@ static void yajl_encoder_wrapper_free(void * wrapper) {
69
69
  static void yajl_encoder_wrapper_mark(void * wrapper) {
70
70
  struct yajl_encoder_wrapper * w = wrapper;
71
71
  rb_gc_mark(w->on_progress_callback);
72
+ rb_gc_mark(w->terminator);
72
73
  }
73
74
 
74
75
  void yajl_encode_part(void * wrapper, VALUE obj, VALUE io) {
@@ -445,11 +446,17 @@ static VALUE rb_yajl_parser_set_complete_cb(VALUE self, VALUE callback) {
445
446
  /*
446
447
  * Document-method: new
447
448
  *
448
- * call-seq: new([:pretty => false[, :indent => ' ']])
449
- *
450
- * :pretty will enable/disable beautifying or "pretty priting" the output string.
451
- *
452
- * :indent is the character(s) used to indent the output string.
449
+ * call-seq: initialize([:pretty => false[, :indent => ' '][, :terminator => "\n"]])
450
+ *
451
+ * :pretty will enable/disable beautifying or "pretty priting" the output string.
452
+ *
453
+ * :indent is the character(s) used to indent the output string.
454
+ *
455
+ * :terminator allows you to specify a character to be used as the termination character after a full JSON string has been generated by
456
+ * the encoder. This would be especially useful when encoding in chunks (via a block or callback during the encode process), to be able to
457
+ * determine when the last chunk of the current encode is sent.
458
+ * If you specify this option to be nil, it will be ignored if encoding directly to an IO or simply returning a string. But if a block is used,
459
+ * the encoder will still pass it - I hope that makes sense ;).
453
460
  */
454
461
  static VALUE rb_yajl_encoder_new(int argc, VALUE * argv, VALUE klass) {
455
462
  struct yajl_encoder_wrapper * wrapper;
@@ -476,6 +483,11 @@ static VALUE rb_yajl_encoder_new(int argc, VALUE * argv, VALUE klass) {
476
483
  obj = Data_Make_Struct(klass, struct yajl_encoder_wrapper, yajl_encoder_wrapper_mark, yajl_encoder_wrapper_free, wrapper);
477
484
  wrapper->encoder = yajl_gen_alloc(&cfg, NULL);
478
485
  wrapper->on_progress_callback = Qnil;
486
+ if (opts != Qnil && rb_funcall(opts, intern_has_key, 1, ID2SYM(sym_terminator)) == Qtrue) {
487
+ wrapper->terminator = rb_hash_aref(opts, ID2SYM(sym_terminator));
488
+ } else {
489
+ wrapper->terminator = 0;
490
+ }
479
491
  rb_obj_call_init(obj, 0, 0);
480
492
  return obj;
481
493
  }
@@ -483,11 +495,17 @@ static VALUE rb_yajl_encoder_new(int argc, VALUE * argv, VALUE klass) {
483
495
  /*
484
496
  * Document-method: initialize
485
497
  *
486
- * call-seq: initialize([:pretty => false[, :indent => ' ']])
498
+ * call-seq: initialize([:pretty => false[, :indent => ' '][, :terminator => "\n"]])
487
499
  *
488
500
  * :pretty will enable/disable beautifying or "pretty priting" the output string.
489
501
  *
490
502
  * :indent is the character(s) used to indent the output string.
503
+ *
504
+ * :terminator allows you to specify a character to be used as the termination character after a full JSON string has been generated by
505
+ * the encoder. This would be especially useful when encoding in chunks (via a block or callback during the encode process), to be able to
506
+ * determine when the last chunk of the current encode is sent.
507
+ * If you specify this option to be nil, it will be ignored if encoding directly to an IO or simply returning a string. But if a block is used,
508
+ * the encoder will still pass it - I hope that makes sense ;).
491
509
  */
492
510
  static VALUE rb_yajl_encoder_init(int argc, VALUE * argv, VALUE self) {
493
511
  return self;
@@ -530,13 +548,23 @@ static VALUE rb_yajl_encoder_encode(int argc, VALUE * argv, VALUE self) {
530
548
  yajl_gen_get_buf(wrapper->encoder, &buffer, &len);
531
549
  outBuff = rb_str_new((const char *)buffer, len);
532
550
  yajl_gen_clear(wrapper->encoder);
551
+
533
552
  if (io != Qnil) {
534
553
  rb_io_write(io, outBuff);
554
+ if (wrapper->terminator != 0 && wrapper->terminator != Qnil) {
555
+ rb_io_write(io, wrapper->terminator);
556
+ }
535
557
  return Qnil;
536
558
  } else if (blk != Qnil) {
537
559
  rb_funcall(blk, intern_call, 1, outBuff);
560
+ if (wrapper->terminator != 0) {
561
+ rb_funcall(blk, intern_call, 1, wrapper->terminator);
562
+ }
538
563
  return Qnil;
539
564
  } else {
565
+ if (wrapper->terminator != 0 && wrapper->terminator != Qnil) {
566
+ rb_str_concat(outBuff, wrapper->terminator);
567
+ }
540
568
  return outBuff;
541
569
  }
542
570
  return Qnil;
@@ -787,5 +815,7 @@ void Init_yajl_ext() {
787
815
  sym_check_utf8 = rb_intern("check_utf8");
788
816
  sym_pretty = rb_intern("pretty");
789
817
  sym_indent = rb_intern("indent");
818
+ sym_terminator = rb_intern("terminator");
790
819
  sym_symbolize_keys = rb_intern("symbolize_keys");
820
+ intern_has_key = rb_intern("has_key?");
791
821
  }
data/ext/yajl_ext.h CHANGED
@@ -6,8 +6,8 @@
6
6
  #define WRITE_BUFSIZE 8092
7
7
 
8
8
  static VALUE cParseError, cEncodeError, mYajl, cParser, cEncoder;
9
- static ID intern_io_read, intern_eof, intern_call, intern_keys, intern_to_s, intern_to_json,
10
- sym_allow_comments, sym_check_utf8, sym_pretty, sym_indent, sym_symbolize_keys;
9
+ static ID intern_io_read, intern_eof, intern_call, intern_keys, intern_to_s, intern_to_json, intern_has_key,
10
+ sym_allow_comments, sym_check_utf8, sym_pretty, sym_indent, sym_terminator, sym_symbolize_keys;
11
11
 
12
12
  #define GetParser(obj, sval) (sval = (struct yajl_parser_wrapper*)DATA_PTR(obj));
13
13
  #define GetEncoder(obj, sval) (sval = (struct yajl_encoder_wrapper*)DATA_PTR(obj));
@@ -53,6 +53,7 @@ struct yajl_parser_wrapper {
53
53
 
54
54
  struct yajl_encoder_wrapper {
55
55
  VALUE on_progress_callback;
56
+ VALUE terminator;
56
57
  yajl_gen encoder;
57
58
  };
58
59
 
data/lib/yajl.rb CHANGED
@@ -13,7 +13,7 @@ require 'yajl_ext'
13
13
  #
14
14
  # Ruby bindings to the excellent Yajl (Yet Another JSON Parser) ANSI C library.
15
15
  module Yajl
16
- VERSION = "0.5.11"
16
+ VERSION = "0.5.12"
17
17
 
18
18
  class Parser
19
19
  # A helper method for parse-and-forget use-cases
@@ -187,4 +187,40 @@ describe "Yajl JSON encoder" do
187
187
  it "should encode a hash where the key and value can be symbols" do
188
188
  Yajl::Encoder.encode({:foo => :bar}).should eql('{"foo":"bar"}')
189
189
  end
190
+
191
+ it "should encode using a newline or nil terminator" do
192
+ Yajl::Encoder.new(:terminator => "\n").encode({:foo => :bar}).should eql("{\"foo\":\"bar\"}\n")
193
+ Yajl::Encoder.new(:terminator => nil).encode({:foo => :bar}).should eql("{\"foo\":\"bar\"}")
194
+ end
195
+
196
+ it "should encode using a newline or nil terminator, to an IO" do
197
+ s = StringIO.new
198
+ Yajl::Encoder.new(:terminator => "\n").encode({:foo => :bar}, s)
199
+ s.rewind
200
+ s.read.should eql("{\"foo\":\"bar\"}\n")
201
+
202
+ s = StringIO.new
203
+ Yajl::Encoder.new(:terminator => nil).encode({:foo => :bar}, s)
204
+ s.rewind
205
+ s.read.should eql("{\"foo\":\"bar\"}")
206
+ end
207
+
208
+ it "should encode using a newline or nil terminator, using a block" do
209
+ s = StringIO.new
210
+ Yajl::Encoder.new(:terminator => "\n").encode({:foo => :bar}) do |chunk|
211
+ s << chunk
212
+ end
213
+ s.rewind
214
+ s.read.should eql("{\"foo\":\"bar\"}\n")
215
+
216
+ s = StringIO.new
217
+ nilpassed = false
218
+ Yajl::Encoder.new(:terminator => nil).encode({:foo => :bar}) do |chunk|
219
+ nilpassed = true if chunk.nil?
220
+ s << chunk
221
+ end
222
+ nilpassed.should be_true
223
+ s.rewind
224
+ s.read.should eql("{\"foo\":\"bar\"}")
225
+ end
190
226
  end
data/yajl-ruby.gemspec CHANGED
@@ -2,11 +2,11 @@
2
2
 
3
3
  Gem::Specification.new do |s|
4
4
  s.name = %q{yajl-ruby}
5
- s.version = "0.5.11"
5
+ s.version = "0.5.12"
6
6
 
7
7
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
8
8
  s.authors = ["Brian Lopez", "Lloyd Hilaiel"]
9
- s.date = %q{2009-07-14}
9
+ s.date = %q{2009-07-31}
10
10
  s.email = %q{seniorlopez@gmail.com}
11
11
  s.extensions = ["ext/extconf.rb"]
12
12
  s.extra_rdoc_files = [
@@ -152,7 +152,7 @@ Gem::Specification.new do |s|
152
152
  s.rdoc_options = ["--charset=UTF-8"]
153
153
  s.require_paths = ["lib", "ext"]
154
154
  s.rubyforge_project = %q{yajl-ruby}
155
- s.rubygems_version = %q{1.3.4}
155
+ s.rubygems_version = %q{1.3.5}
156
156
  s.summary = %q{Ruby C bindings to the excellent Yajl JSON stream-based parser library.}
157
157
  s.test_files = [
158
158
  "spec/encoding/encoding_spec.rb",
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: yajl-ruby
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.11
4
+ version: 0.5.12
5
5
  platform: ruby
6
6
  authors:
7
7
  - Brian Lopez
@@ -10,7 +10,7 @@ autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
12
 
13
- date: 2009-07-14 00:00:00 -07:00
13
+ date: 2009-07-31 00:00:00 -07:00
14
14
  default_executable:
15
15
  dependencies: []
16
16
 
@@ -182,8 +182,9 @@ required_rubygems_version: !ruby/object:Gem::Requirement
182
182
  requirements: []
183
183
 
184
184
  rubyforge_project: yajl-ruby
185
- rubygems_version: 1.3.4
185
+ rubygems_version: 1.3.5
186
186
  signing_key:
187
+ source:
187
188
  specification_version: 3
188
189
  summary: Ruby C bindings to the excellent Yajl JSON stream-based parser library.
189
190
  test_files: