You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@thrift.apache.org by kc...@apache.org on 2008/06/18 03:18:07 UTC

svn commit: r669015 - in /incubator/thrift/trunk: compiler/cpp/src/generate/ lib/rb/benchmark/gen-rb/ lib/rb/lib/thrift/ lib/rb/spec/ lib/rb/spec/gen-rb/

Author: kclark
Date: Tue Jun 17 18:18:07 2008
New Revision: 669015

URL: http://svn.apache.org/viewvc?rev=669015&view=rev
Log:
rb: Implement type-checking in Thrift::Struct.new and field accessors

Modified:
    incubator/thrift/trunk/compiler/cpp/src/generate/t_rb_generator.cc
    incubator/thrift/trunk/lib/rb/benchmark/gen-rb/BenchmarkService.rb
    incubator/thrift/trunk/lib/rb/lib/thrift/struct.rb
    incubator/thrift/trunk/lib/rb/spec/gen-rb/NonblockingService.rb
    incubator/thrift/trunk/lib/rb/spec/gen-rb/ThriftSpec_types.rb
    incubator/thrift/trunk/lib/rb/spec/struct_spec.rb

Modified: incubator/thrift/trunk/compiler/cpp/src/generate/t_rb_generator.cc
URL: http://svn.apache.org/viewvc/incubator/thrift/trunk/compiler/cpp/src/generate/t_rb_generator.cc?rev=669015&r1=669014&r2=669015&view=diff
==============================================================================
--- incubator/thrift/trunk/compiler/cpp/src/generate/t_rb_generator.cc (original)
+++ incubator/thrift/trunk/compiler/cpp/src/generate/t_rb_generator.cc Tue Jun 17 18:18:07 2008
@@ -490,12 +490,9 @@
   vector<t_field*>::const_iterator m_iter;
 
   if (members.size() > 0) {
-    indent(out) << "attr_accessor ";
+    indent(out) << "Thrift::Struct.field_accessor self";
     for (m_iter = members.begin(); m_iter != members.end(); ++m_iter) {
-      if (m_iter != members.begin()) {
-        out << ", ";
-      }
-      out << ":" << (*m_iter)->get_name();
+      out << ", :" << (*m_iter)->get_name();
     }
     out << endl;
   }

Modified: incubator/thrift/trunk/lib/rb/benchmark/gen-rb/BenchmarkService.rb
URL: http://svn.apache.org/viewvc/incubator/thrift/trunk/lib/rb/benchmark/gen-rb/BenchmarkService.rb?rev=669015&r1=669014&r2=669015&view=diff
==============================================================================
--- incubator/thrift/trunk/lib/rb/benchmark/gen-rb/BenchmarkService.rb (original)
+++ incubator/thrift/trunk/lib/rb/benchmark/gen-rb/BenchmarkService.rb Tue Jun 17 18:18:07 2008
@@ -46,7 +46,7 @@
 
         class Fibonacci_args
           include Thrift::Struct
-          attr_accessor :n
+          Thrift::Struct.field_accessor self, :n
           FIELDS = {
             1 => {:type => Thrift::Types::BYTE, :name => 'n'}
           }
@@ -54,7 +54,7 @@
 
         class Fibonacci_result
           include Thrift::Struct
-          attr_accessor :success
+          Thrift::Struct.field_accessor self, :success
           FIELDS = {
             0 => {:type => Thrift::Types::I32, :name => 'success'}
           }

Modified: incubator/thrift/trunk/lib/rb/lib/thrift/struct.rb
URL: http://svn.apache.org/viewvc/incubator/thrift/trunk/lib/rb/lib/thrift/struct.rb?rev=669015&r1=669014&r2=669015&view=diff
==============================================================================
--- incubator/thrift/trunk/lib/rb/lib/thrift/struct.rb (original)
+++ incubator/thrift/trunk/lib/rb/lib/thrift/struct.rb Tue Jun 17 18:18:07 2008
@@ -1,11 +1,15 @@
+require 'thrift/types'
 require 'set'
 
 module Thrift
   module Struct
     def initialize(d={})
       each_field do |fid, type, name, default|
-        instance_variable_set("@#{name}", d.fetch(name.to_s) { d.fetch(name.to_sym) { default.dup rescue default } })
+        value = d.delete(name.to_s) { d.delete(name.to_sym) { default.dup rescue default } }
+        Thrift.check_type(value, type)
+        instance_variable_set("@#{name}", value)
       end
+      raise Exception, "Unknown arguments given to #{self.class}.new" unless d.empty?
     end
 
     def struct_fields
@@ -54,6 +58,16 @@
       true
     end
 
+    def self.field_accessor(klass, *fields)
+      fields.each do |field|
+        klass.send :attr_reader, field
+        klass.send :define_method, "#{field}=" do |value|
+          Thrift.check_type(value, klass::FIELDS.values.find { |f| f[:name].to_s == field.to_s }[:type] )
+          instance_variable_set("@#{field}", value)
+        end
+      end
+    end
+
     protected
 
     def handle_message(iprot, fid, ftype)

Modified: incubator/thrift/trunk/lib/rb/spec/gen-rb/NonblockingService.rb
URL: http://svn.apache.org/viewvc/incubator/thrift/trunk/lib/rb/spec/gen-rb/NonblockingService.rb?rev=669015&r1=669014&r2=669015&view=diff
==============================================================================
--- incubator/thrift/trunk/lib/rb/spec/gen-rb/NonblockingService.rb (original)
+++ incubator/thrift/trunk/lib/rb/spec/gen-rb/NonblockingService.rb Tue Jun 17 18:18:07 2008
@@ -115,7 +115,7 @@
 
         class Greeting_args
           include Thrift::Struct
-          attr_accessor :english
+          Thrift::Struct.field_accessor self, :english
           FIELDS = {
             1 => {:type => Thrift::Types::BOOL, :name => 'english'}
           }
@@ -123,7 +123,7 @@
 
         class Greeting_result
           include Thrift::Struct
-          attr_accessor :success
+          Thrift::Struct.field_accessor self, :success
           FIELDS = {
             0 => {:type => Thrift::Types::STRUCT, :name => 'success', :class => Hello}
           }
@@ -138,7 +138,7 @@
 
         class Block_result
           include Thrift::Struct
-          attr_accessor :success
+          Thrift::Struct.field_accessor self, :success
           FIELDS = {
             0 => {:type => Thrift::Types::BOOL, :name => 'success'}
           }
@@ -174,7 +174,7 @@
 
         class Sleep_args
           include Thrift::Struct
-          attr_accessor :seconds
+          Thrift::Struct.field_accessor self, :seconds
           FIELDS = {
             1 => {:type => Thrift::Types::DOUBLE, :name => 'seconds'}
           }

Modified: incubator/thrift/trunk/lib/rb/spec/gen-rb/ThriftSpec_types.rb
URL: http://svn.apache.org/viewvc/incubator/thrift/trunk/lib/rb/spec/gen-rb/ThriftSpec_types.rb?rev=669015&r1=669014&r2=669015&view=diff
==============================================================================
--- incubator/thrift/trunk/lib/rb/spec/gen-rb/ThriftSpec_types.rb (original)
+++ incubator/thrift/trunk/lib/rb/spec/gen-rb/ThriftSpec_types.rb Tue Jun 17 18:18:07 2008
@@ -9,7 +9,7 @@
 module SpecNamespace
     class Hello
       include Thrift::Struct
-      attr_accessor :greeting
+      Thrift::Struct.field_accessor self, :greeting
       FIELDS = {
         1 => {:type => Thrift::Types::STRING, :name => 'greeting', :default => 'hello world'}
       }
@@ -17,7 +17,7 @@
 
     class Foo
       include Thrift::Struct
-      attr_accessor :simple, :words, :hello, :ints, :complex, :shorts
+      Thrift::Struct.field_accessor self, :simple, :words, :hello, :ints, :complex, :shorts
       FIELDS = {
         1 => {:type => Thrift::Types::I32, :name => 'simple', :default => 53},
         2 => {:type => Thrift::Types::STRING, :name => 'words', :default => 'words'},
@@ -40,7 +40,7 @@
 
     class BoolStruct
       include Thrift::Struct
-      attr_accessor :yesno
+      Thrift::Struct.field_accessor self, :yesno
       FIELDS = {
         1 => {:type => Thrift::Types::BOOL, :name => 'yesno', :default => true}
       }

Modified: incubator/thrift/trunk/lib/rb/spec/struct_spec.rb
URL: http://svn.apache.org/viewvc/incubator/thrift/trunk/lib/rb/spec/struct_spec.rb?rev=669015&r1=669014&r2=669015&view=diff
==============================================================================
--- incubator/thrift/trunk/lib/rb/spec/struct_spec.rb (original)
+++ incubator/thrift/trunk/lib/rb/spec/struct_spec.rb Tue Jun 17 18:18:07 2008
@@ -174,5 +174,30 @@
       struct = Foo.new
       lambda { struct.send :write_container, nil, nil, {:type => "foo"} }.should raise_error(StandardError, "Not a container type: foo")
     end
+
+    it "should support optional type-checking in Thrift::Struct.new" do
+      Thrift.type_checking = true
+      begin
+        lambda { Hello.new(:greeting => 3) }.should raise_error(TypeError, "Expected Types::STRING, received Fixnum")
+      ensure
+        Thrift.type_checking = false
+      end
+      lambda { Hello.new(:greeting => 3) }.should_not raise_error(TypeError)
+    end
+
+    it "should support optional type-checking in field accessors" do
+      Thrift.type_checking = true
+      begin
+        hello = Hello.new
+        lambda { hello.greeting = 3 }.should raise_error(TypeError, "Expected Types::STRING, received Fixnum")
+      ensure
+        Thrift.type_checking = false
+      end
+      lambda { hello.greeting = 3 }.should_not raise_error(TypeError)
+    end
+
+    it "should raise an exception when unknown types are given to Thrift::Struct.new" do
+      lambda { Hello.new(:fish => 'salmon') }.should raise_error(Exception, "Unknown arguments given to SpecNamespace::Hello.new")
+    end
   end
 end