stark 0.5.0 → 0.6.0

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.
data/History.txt CHANGED
@@ -1,4 +1,14 @@
1
- === 1.0.0 / 2012-08-20
1
+ === 0.6.0 / 2013-03-02
2
+
3
+ * 5 bugfixes:
4
+
5
+ * Add oneway support and add throw on server side
6
+ * Add support for throws. Fixes #1
7
+ * Disable regenerating the parser on test run
8
+ * Fix code generation bug
9
+ * Fix running in travis
10
+
11
+ === 0.5.0 / 2012-08-20
2
12
 
3
13
  * 1 major enhancement
4
14
 
data/Rakefile CHANGED
@@ -3,6 +3,7 @@
3
3
  require 'rubygems'
4
4
  require 'hoe'
5
5
 
6
+ Hoe.plugin :travis
6
7
  Hoe.plugin :gemspec
7
8
  Hoe.plugin :git
8
9
 
@@ -16,6 +17,6 @@ task :parser do
16
17
  sh "kpeg -o lib/stark/raw_parser.rb -s -f lib/stark/thrift.kpeg"
17
18
  end
18
19
 
19
- task :test => :parser
20
+ # task :test => :parser
20
21
 
21
22
  # vim: syntax=ruby
data/lib/stark/ast.rb CHANGED
@@ -43,5 +43,11 @@ class Stark::Parser
43
43
  obj.process_enum self
44
44
  end
45
45
  end
46
+
47
+ class Exception
48
+ def accept(obj)
49
+ obj.process_exception self
50
+ end
51
+ end
46
52
  end
47
53
  end
data/lib/stark/client.rb CHANGED
@@ -16,6 +16,29 @@ module Stark
16
16
  end
17
17
  end
18
18
 
19
+ def handle_throw(cls)
20
+ ip = @iprot
21
+
22
+ obj = cls::Struct.new
23
+
24
+ ip.read_struct_begin
25
+
26
+ while true
27
+ _, ftype, fid = ip.read_field_begin
28
+ break if ftype == ::Thrift::Types::STOP
29
+
30
+ obj.set_from_index ftype, fid, ip
31
+
32
+ ip.read_field_end
33
+ end
34
+
35
+ ip.read_struct_end
36
+
37
+ ip.read_message_end
38
+
39
+ raise cls.new(obj)
40
+ end
41
+
19
42
  def handle_unexpected(rtype)
20
43
  return if rtype == ::Thrift::Types::STOP
21
44
  @iprot.skip(rtype)
@@ -12,6 +12,10 @@ module Stark
12
12
  def read(ip)
13
13
  ip.read_i32
14
14
  end
15
+
16
+ def write(op, value)
17
+ op.write_i32 value
18
+ end
15
19
  end
16
20
 
17
21
  module STRING
@@ -24,6 +28,10 @@ module Stark
24
28
  def read(ip)
25
29
  ip.read_string
26
30
  end
31
+
32
+ def write(op, value)
33
+ op.write_string value
34
+ end
27
35
  end
28
36
  end
29
37
  end
data/lib/stark/field.rb CHANGED
@@ -17,5 +17,11 @@ module Stark
17
17
  def read(ip)
18
18
  @converter.read ip
19
19
  end
20
+
21
+ def write(op, val)
22
+ op.write_field_begin @name, type, @index
23
+ @converter.write op, val
24
+ op.write_field_end
25
+ end
20
26
  end
21
27
  end
@@ -6,6 +6,8 @@ module Stark
6
6
 
7
7
  def process(iprot, oprot)
8
8
  name, type, seqid = iprot.read_message_begin
9
+ fail unless type == Thrift::MessageTypes::CALL
10
+
9
11
  if respond_to?("process_#{name}")
10
12
  send("process_#{name}", seqid, iprot, oprot)
11
13
  true
@@ -21,6 +23,31 @@ module Stark
21
23
  end
22
24
  end
23
25
 
26
+ def check_raise_specific(name, seqid, op, c)
27
+ begin
28
+ yield
29
+ rescue c => e
30
+ op.write_message_begin name, ::Thrift::MessageTypes::REPLY, seqid
31
+ op.write_struct_begin 'result_struct'
32
+
33
+ op.write_field_begin 'result', ::Thrift::Types::STRUCT, 1
34
+ op.write_struct_begin c.class.name
35
+ e.struct.write_fields op
36
+ op.write_field_end
37
+ op.write_field_stop
38
+ op.write_struct_end
39
+
40
+ op.write_field_end
41
+ op.write_field_stop
42
+ op.write_struct_end
43
+
44
+ op.write_message_end
45
+ op.trans.flush
46
+
47
+ nil
48
+ end
49
+ end
50
+
24
51
  def hash_cast(obj)
25
52
  return obj if obj.kind_of? Hash
26
53
  return obj.to_h if obj.respond_to? :to_h
@@ -428,14 +428,18 @@ class Stark::Parser
428
428
  attr_reader :options
429
429
  end
430
430
  class Function < Node
431
- def initialize(name, return_type, arguments)
431
+ def initialize(name, return_type, arguments, throws, options)
432
432
  @name = name
433
433
  @return_type = return_type
434
434
  @arguments = arguments
435
+ @throws = throws
436
+ @options = options
435
437
  end
436
438
  attr_reader :name
437
439
  attr_reader :return_type
438
440
  attr_reader :arguments
441
+ attr_reader :throws
442
+ attr_reader :options
439
443
  end
440
444
  class Include < Node
441
445
  def initialize(path)
@@ -520,8 +524,8 @@ class Stark::Parser
520
524
  def field(index, type, name, value, options)
521
525
  AST::Field.new(index, type, name, value, options)
522
526
  end
523
- def function(name, return_type, arguments)
524
- AST::Function.new(name, return_type, arguments)
527
+ def function(name, return_type, arguments, throws, options)
528
+ AST::Function.new(name, return_type, arguments, throws, options)
525
529
  end
526
530
  def include(path)
527
531
  AST::Include.new(path)
@@ -3028,7 +3032,7 @@ class Stark::Parser
3028
3032
  return _tmp
3029
3033
  end
3030
3034
 
3031
- # Function = CaptureDocText OneWay? FunctionType:rt - tok_identifier:name osp "(" FieldList?:args ")" Throws? CommaOrSemicolonOptional {function(name, rt, args)}
3035
+ # Function = CaptureDocText OneWay?:o FunctionType:rt - tok_identifier:name osp "(" FieldList?:args ")" Throws?:t CommaOrSemicolonOptional {function(name, rt, args, t, o)}
3032
3036
  def _Function
3033
3037
 
3034
3038
  _save = self.pos
@@ -3040,10 +3044,12 @@ class Stark::Parser
3040
3044
  end
3041
3045
  _save1 = self.pos
3042
3046
  _tmp = apply(:_OneWay)
3047
+ @result = nil unless _tmp
3043
3048
  unless _tmp
3044
3049
  _tmp = true
3045
3050
  self.pos = _save1
3046
3051
  end
3052
+ o = @result
3047
3053
  unless _tmp
3048
3054
  self.pos = _save
3049
3055
  break
@@ -3094,10 +3100,12 @@ class Stark::Parser
3094
3100
  end
3095
3101
  _save3 = self.pos
3096
3102
  _tmp = apply(:_Throws)
3103
+ @result = nil unless _tmp
3097
3104
  unless _tmp
3098
3105
  _tmp = true
3099
3106
  self.pos = _save3
3100
3107
  end
3108
+ t = @result
3101
3109
  unless _tmp
3102
3110
  self.pos = _save
3103
3111
  break
@@ -3107,7 +3115,7 @@ class Stark::Parser
3107
3115
  self.pos = _save
3108
3116
  break
3109
3117
  end
3110
- @result = begin; function(name, rt, args); end
3118
+ @result = begin; function(name, rt, args, t, o); end
3111
3119
  _tmp = true
3112
3120
  unless _tmp
3113
3121
  self.pos = _save
@@ -3119,7 +3127,7 @@ class Stark::Parser
3119
3127
  return _tmp
3120
3128
  end
3121
3129
 
3122
- # OneWay = ("oneway" | "async") -
3130
+ # OneWay = ("oneway" | "async") - { :oneway }
3123
3131
  def _OneWay
3124
3132
 
3125
3133
  _save = self.pos
@@ -3141,6 +3149,12 @@ class Stark::Parser
3141
3149
  break
3142
3150
  end
3143
3151
  _tmp = apply(:__hyphen_)
3152
+ unless _tmp
3153
+ self.pos = _save
3154
+ break
3155
+ end
3156
+ @result = begin; :oneway ; end
3157
+ _tmp = true
3144
3158
  unless _tmp
3145
3159
  self.pos = _save
3146
3160
  end
@@ -3151,11 +3165,16 @@ class Stark::Parser
3151
3165
  return _tmp
3152
3166
  end
3153
3167
 
3154
- # Throws = "throws" - "(" FieldList ")"
3168
+ # Throws = - "throws" - "(" FieldList ")"
3155
3169
  def _Throws
3156
3170
 
3157
3171
  _save = self.pos
3158
3172
  while true # sequence
3173
+ _tmp = apply(:__hyphen_)
3174
+ unless _tmp
3175
+ self.pos = _save
3176
+ break
3177
+ end
3159
3178
  _tmp = match_string("throws")
3160
3179
  unless _tmp
3161
3180
  self.pos = _save
@@ -3995,9 +4014,9 @@ class Stark::Parser
3995
4014
  Rules[:_Service] = rule_info("Service", "\"service\" - tok_identifier:name - Extends? osp \"{\" obsp FunctionList?:funcs obsp \"}\" {service(name, funcs)}")
3996
4015
  Rules[:_Extends] = rule_info("Extends", "\"extends\" - tok_identifier")
3997
4016
  Rules[:_FunctionList] = rule_info("FunctionList", "(FunctionList:l Function:f { l + [f] } | Function:f { [f] })")
3998
- Rules[:_Function] = rule_info("Function", "CaptureDocText OneWay? FunctionType:rt - tok_identifier:name osp \"(\" FieldList?:args \")\" Throws? CommaOrSemicolonOptional {function(name, rt, args)}")
3999
- Rules[:_OneWay] = rule_info("OneWay", "(\"oneway\" | \"async\") -")
4000
- Rules[:_Throws] = rule_info("Throws", "\"throws\" - \"(\" FieldList \")\"")
4017
+ Rules[:_Function] = rule_info("Function", "CaptureDocText OneWay?:o FunctionType:rt - tok_identifier:name osp \"(\" FieldList?:args \")\" Throws?:t CommaOrSemicolonOptional {function(name, rt, args, t, o)}")
4018
+ Rules[:_OneWay] = rule_info("OneWay", "(\"oneway\" | \"async\") - { :oneway }")
4019
+ Rules[:_Throws] = rule_info("Throws", "- \"throws\" - \"(\" FieldList \")\"")
4001
4020
  Rules[:_FieldList] = rule_info("FieldList", "(FieldList:l Field:f { l + [f] } | Field:f { [f] })")
4002
4021
  Rules[:_Field] = rule_info("Field", "CaptureDocText FieldIdentifier?:i osp FieldRequiredness?:req osp FieldType:t osp tok_identifier:n osp FieldValue?:val CommaOrSemicolonOptional {field(i,t,n,val,req)}")
4003
4022
  Rules[:_FieldIdentifier] = rule_info("FieldIdentifier", "tok_int_constant:n \":\" {n}")
data/lib/stark/ruby.rb CHANGED
@@ -8,6 +8,7 @@ module Stark
8
8
  @indent = 0
9
9
  @structs = {}
10
10
  @enums = {}
11
+ @exceptions = {}
11
12
 
12
13
  @stream = stream
13
14
 
@@ -17,6 +18,7 @@ module Stark
17
18
  o "require 'stark/field'"
18
19
  o "require 'stark/converters'"
19
20
  o "require 'stark/processor'"
21
+ o "require 'stark/exception'"
20
22
  end
21
23
 
22
24
  def process_namespace(ns)
@@ -58,11 +60,53 @@ module Stark
58
60
 
59
61
  outdent
60
62
  o "}"
63
+
64
+ str.fields.each do |f|
65
+ o "def #{f.name}; @fields['#{f.name}']; end"
66
+ end
67
+
61
68
  outdent
62
69
  o "end"
63
70
 
64
71
  end
65
72
 
73
+ def process_exception(str)
74
+ @exceptions[str.name] = str
75
+
76
+ o "class #{str.name} < Stark::Exception"
77
+ indent
78
+
79
+ o "class Struct < Stark::Struct"
80
+ indent
81
+ o "Fields = {"
82
+ indent
83
+
84
+ str.fields.each do |f|
85
+ c = "Stark::Converters::#{f.type.upcase}"
86
+
87
+ o "#{f.index} => Stark::Field.new(#{f.index}, '#{f.name}', #{c}),"
88
+ end
89
+
90
+ o ":count => #{str.fields.size}"
91
+
92
+ outdent
93
+ o "}"
94
+
95
+ str.fields.each do |f|
96
+ o "def #{f.name}; @fields['#{f.name}']; end"
97
+ end
98
+
99
+ outdent
100
+ o "end"
101
+
102
+ str.fields.each do |f|
103
+ o "def #{f.name}; @struct.#{f.name}; end"
104
+ end
105
+
106
+ outdent
107
+ o "end"
108
+ end
109
+
66
110
  def o(str)
67
111
  @stream.print(" " * @indent)
68
112
  @stream.puts str
@@ -243,7 +287,23 @@ module Stark
243
287
  o "ip.read_struct_end"
244
288
  o "ip.read_message_end"
245
289
 
246
- o "result = @handler.#{func.name}(*args)"
290
+ if t = func.throws
291
+ o "result = check_raise_specific('#{func.name}', seqid, op, #{t.first.type}) do"
292
+ o " @handler.#{func.name}(*args)"
293
+ o "end"
294
+
295
+ o "return unless result"
296
+
297
+ else
298
+ o "result = @handler.#{func.name}(*args)"
299
+ end
300
+
301
+ if func.options == :oneway
302
+ o "return result"
303
+ outdent
304
+ o "end"
305
+ next
306
+ end
247
307
 
248
308
  o "op.write_message_begin '#{func.name}', ::Thrift::MessageTypes::REPLY, seqid"
249
309
  o "op.write_struct_begin '#{func.name}_result'"
@@ -313,10 +373,12 @@ module Stark
313
373
 
314
374
  o " :args => {"
315
375
 
316
- Array(func.arguments).each do |a|
317
- o " #{a.index} => #{wire_type(a.type)}"
376
+ mapped_args = Array(func.arguments).map do |a|
377
+ "#{a.index} => #{wire_type(a.type)}"
318
378
  end
319
379
 
380
+ o " #{mapped_args.join(', ')}"
381
+
320
382
  o " }"
321
383
  o " }"
322
384
  end
@@ -374,25 +436,40 @@ module Stark
374
436
  o "op.write_message_end"
375
437
  o "op.trans.flush"
376
438
 
439
+ if func.options == :oneway
440
+ o "return"
441
+ outdent
442
+ o "end"
443
+ next
444
+ end
445
+
377
446
  o "ip = @iprot"
378
447
  o "_, mtype, _ = ip.read_message_begin"
448
+
379
449
  o "handle_exception mtype"
380
450
 
381
451
  o "ip.read_struct_begin"
452
+
453
+ o "_, rtype, rid = ip.read_field_begin"
454
+
455
+ if t = func.throws
456
+ o "if rid == 1"
457
+ o " handle_throw #{t.first.type}"
458
+ o "end"
459
+ end
460
+
461
+ o "fail unless rid == 0"
462
+
382
463
  o "result = nil"
383
464
 
384
- if func.return_type == "void"
385
- o "_, rtype, _ = ip.read_field_begin"
386
- else
465
+ if func.return_type != "void"
387
466
  if desc = @structs[func.return_type]
388
- o "_, rtype, rid = ip.read_field_begin"
389
467
  o "if rtype != #{wire_type(func.return_type)}"
390
468
  o " handle_unexpected rtype"
391
469
  o "else"
392
470
  o " result = read_generic rtype, rid, #{desc.name}"
393
471
  o "end"
394
472
  elsif desc = @enums[func.return_type]
395
- o "_, rtype, rid = ip.read_field_begin"
396
473
  o "if rtype != #{wire_type(func.return_type)}"
397
474
  o " handle_unexpected rtype"
398
475
  o "else"
@@ -402,7 +479,6 @@ module Stark
402
479
  elsif func.return_type.kind_of? Stark::Parser::AST::Map
403
480
  ft = func.return_type
404
481
 
405
- o "_, rtype, rid = ip.read_field_begin"
406
482
  o "if rtype != #{wire_type(func.return_type)}"
407
483
  o " handle_unexpected rtype"
408
484
  o "else"
@@ -419,7 +495,6 @@ module Stark
419
495
  o "end"
420
496
  elsif func.return_type.kind_of? Stark::Parser::AST::List
421
497
  ft = func.return_type
422
- o "_, rtype, rid = ip.read_field_begin"
423
498
  o "if rtype == ::Thrift::Types::LIST"
424
499
  o " vt, size = ip.read_list_begin"
425
500
  o " if vt == #{wire_type(ft.value)}"
@@ -432,7 +507,6 @@ module Stark
432
507
  o " handle_unexpected rtype"
433
508
  o "end"
434
509
  else
435
- o "_, rtype, _ = ip.read_field_begin"
436
510
  o "if rtype == #{type(func.return_type)}"
437
511
  o " result = ip.#{read_func(func.return_type)}"
438
512
  o "else"
data/lib/stark/struct.rb CHANGED
@@ -15,12 +15,11 @@ module Stark
15
15
  end
16
16
  end
17
17
 
18
- def method_missing(meth, *args)
19
- if val = @fields[meth.to_s]
20
- return val
18
+ def write_fields(op)
19
+ self.class::Fields.each do |idx, field|
20
+ next if idx == :count
21
+ field.write op, @fields[field.name]
21
22
  end
22
-
23
- super
24
23
  end
25
24
  end
26
25
  end
@@ -4,7 +4,7 @@
4
4
  %% include = ast Include(path)
5
5
  %% struct = ast Struct(type, name, fields)
6
6
  %% field = ast Field(index, type, name, value, options)
7
- %% function = ast Function(name, return_type, arguments)
7
+ %% function = ast Function(name, return_type, arguments, throws, options)
8
8
  %% service = ast Service(name, functions)
9
9
  %% comment = ast Comment(text)
10
10
  %% enum = ast Enum(name, values)
@@ -271,13 +271,13 @@ Extends = "extends" - tok_identifier
271
271
  FunctionList = FunctionList:l Function:f { l + [f] }
272
272
  | Function:f { [f] }
273
273
 
274
- Function = CaptureDocText OneWay? FunctionType:rt - tok_identifier:name
275
- osp "(" FieldList?:args ")" Throws? CommaOrSemicolonOptional
276
- ~function(name, rt, args)
274
+ Function = CaptureDocText OneWay?:o FunctionType:rt - tok_identifier:name
275
+ osp "(" FieldList?:args ")" Throws?:t CommaOrSemicolonOptional
276
+ ~function(name, rt, args, t, o)
277
277
 
278
- OneWay = ("oneway" | "async") -
278
+ OneWay = ("oneway" | "async") - { :oneway }
279
279
 
280
- Throws = "throws" - "(" FieldList ")"
280
+ Throws = - "throws" - "(" FieldList ")"
281
281
 
282
282
  FieldList = FieldList:l Field:f { l + [f] }
283
283
  | Field:f { [f] }
data/lib/stark.rb CHANGED
@@ -1,7 +1,7 @@
1
1
  require 'thrift'
2
2
 
3
3
  module Stark
4
- VERSION = '0.5.0'
4
+ VERSION = '0.6.0'
5
5
 
6
6
  def self.pipe_transport
7
7
  cr, cw = IO.pipe
@@ -34,3 +34,19 @@ class UserProfile
34
34
  ::Thrift::Struct.generate_accessors self
35
35
  end
36
36
 
37
+ class RockTooHard < ::Thrift::Exception
38
+ include ::Thrift::Struct, ::Thrift::Struct_Union
39
+ VOLUME = 1
40
+
41
+ FIELDS = {
42
+ VOLUME => {:type => ::Thrift::Types::I32, :name => 'volume'}
43
+ }
44
+
45
+ def struct_fields; FIELDS; end
46
+
47
+ def validate
48
+ end
49
+
50
+ ::Thrift::Struct.generate_accessors self
51
+ end
52
+
@@ -127,6 +127,44 @@ module UserStorage
127
127
  raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'last_status failed: unknown result')
128
128
  end
129
129
 
130
+ def volume_up()
131
+ send_volume_up()
132
+ return recv_volume_up()
133
+ end
134
+
135
+ def send_volume_up()
136
+ send_message('volume_up', Volume_up_args)
137
+ end
138
+
139
+ def recv_volume_up()
140
+ result = receive_message(Volume_up_result)
141
+ return result.success unless result.success.nil?
142
+ raise result.exc unless result.exc.nil?
143
+ raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'volume_up failed: unknown result')
144
+ end
145
+
146
+ def make_bitcoins()
147
+ send_make_bitcoins()
148
+ end
149
+
150
+ def send_make_bitcoins()
151
+ send_message('make_bitcoins', Make_bitcoins_args)
152
+ end
153
+ def add(a, b)
154
+ send_add(a, b)
155
+ return recv_add()
156
+ end
157
+
158
+ def send_add(a, b)
159
+ send_message('add', Add_args, :a => a, :b => b)
160
+ end
161
+
162
+ def recv_add()
163
+ result = receive_message(Add_result)
164
+ return result.success unless result.success.nil?
165
+ raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'add failed: unknown result')
166
+ end
167
+
130
168
  end
131
169
 
132
170
  class Processor
@@ -188,6 +226,30 @@ module UserStorage
188
226
  write_result(result, oprot, 'last_status', seqid)
189
227
  end
190
228
 
229
+ def process_volume_up(seqid, iprot, oprot)
230
+ args = read_args(iprot, Volume_up_args)
231
+ result = Volume_up_result.new()
232
+ begin
233
+ result.success = @handler.volume_up()
234
+ rescue RockTooHard => exc
235
+ result.exc = exc
236
+ end
237
+ write_result(result, oprot, 'volume_up', seqid)
238
+ end
239
+
240
+ def process_make_bitcoins(seqid, iprot, oprot)
241
+ args = read_args(iprot, Make_bitcoins_args)
242
+ @handler.make_bitcoins()
243
+ return
244
+ end
245
+
246
+ def process_add(seqid, iprot, oprot)
247
+ args = read_args(iprot, Add_args)
248
+ result = Add_result.new()
249
+ result.success = @handler.add(args.a, args.b)
250
+ write_result(result, oprot, 'add', seqid)
251
+ end
252
+
191
253
  end
192
254
 
193
255
  # HELPER FUNCTIONS AND STRUCTURES
@@ -447,5 +509,102 @@ module UserStorage
447
509
  ::Thrift::Struct.generate_accessors self
448
510
  end
449
511
 
512
+ class Volume_up_args
513
+ include ::Thrift::Struct, ::Thrift::Struct_Union
514
+
515
+ FIELDS = {
516
+
517
+ }
518
+
519
+ def struct_fields; FIELDS; end
520
+
521
+ def validate
522
+ end
523
+
524
+ ::Thrift::Struct.generate_accessors self
525
+ end
526
+
527
+ class Volume_up_result
528
+ include ::Thrift::Struct, ::Thrift::Struct_Union
529
+ SUCCESS = 0
530
+ EXC = 1
531
+
532
+ FIELDS = {
533
+ SUCCESS => {:type => ::Thrift::Types::I32, :name => 'success'},
534
+ EXC => {:type => ::Thrift::Types::STRUCT, :name => 'exc', :class => RockTooHard}
535
+ }
536
+
537
+ def struct_fields; FIELDS; end
538
+
539
+ def validate
540
+ end
541
+
542
+ ::Thrift::Struct.generate_accessors self
543
+ end
544
+
545
+ class Make_bitcoins_args
546
+ include ::Thrift::Struct, ::Thrift::Struct_Union
547
+
548
+ FIELDS = {
549
+
550
+ }
551
+
552
+ def struct_fields; FIELDS; end
553
+
554
+ def validate
555
+ end
556
+
557
+ ::Thrift::Struct.generate_accessors self
558
+ end
559
+
560
+ class Make_bitcoins_result
561
+ include ::Thrift::Struct, ::Thrift::Struct_Union
562
+
563
+ FIELDS = {
564
+
565
+ }
566
+
567
+ def struct_fields; FIELDS; end
568
+
569
+ def validate
570
+ end
571
+
572
+ ::Thrift::Struct.generate_accessors self
573
+ end
574
+
575
+ class Add_args
576
+ include ::Thrift::Struct, ::Thrift::Struct_Union
577
+ A = 1
578
+ B = 2
579
+
580
+ FIELDS = {
581
+ A => {:type => ::Thrift::Types::I32, :name => 'a'},
582
+ B => {:type => ::Thrift::Types::I32, :name => 'b'}
583
+ }
584
+
585
+ def struct_fields; FIELDS; end
586
+
587
+ def validate
588
+ end
589
+
590
+ ::Thrift::Struct.generate_accessors self
591
+ end
592
+
593
+ class Add_result
594
+ include ::Thrift::Struct, ::Thrift::Struct_Union
595
+ SUCCESS = 0
596
+
597
+ FIELDS = {
598
+ SUCCESS => {:type => ::Thrift::Types::I32, :name => 'success'}
599
+ }
600
+
601
+ def struct_fields; FIELDS; end
602
+
603
+ def validate
604
+ end
605
+
606
+ ::Thrift::Struct.generate_accessors self
607
+ end
608
+
450
609
  end
451
610
 
@@ -34,3 +34,19 @@ class UserProfile
34
34
  ::Thrift::Struct.generate_accessors self
35
35
  end
36
36
 
37
+ class RockTooHard < ::Thrift::Exception
38
+ include ::Thrift::Struct, ::Thrift::Struct_Union
39
+ VOLUME = 1
40
+
41
+ FIELDS = {
42
+ VOLUME => {:type => ::Thrift::Types::I32, :name => 'volume'}
43
+ }
44
+
45
+ def struct_fields; FIELDS; end
46
+
47
+ def validate
48
+ end
49
+
50
+ ::Thrift::Struct.generate_accessors self
51
+ end
52
+
@@ -127,6 +127,44 @@ module UserStorage
127
127
  raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'last_status failed: unknown result')
128
128
  end
129
129
 
130
+ def volume_up()
131
+ send_volume_up()
132
+ return recv_volume_up()
133
+ end
134
+
135
+ def send_volume_up()
136
+ send_message('volume_up', Volume_up_args)
137
+ end
138
+
139
+ def recv_volume_up()
140
+ result = receive_message(Volume_up_result)
141
+ return result.success unless result.success.nil?
142
+ raise result.exc unless result.exc.nil?
143
+ raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'volume_up failed: unknown result')
144
+ end
145
+
146
+ def make_bitcoins()
147
+ send_make_bitcoins()
148
+ end
149
+
150
+ def send_make_bitcoins()
151
+ send_message('make_bitcoins', Make_bitcoins_args)
152
+ end
153
+ def add(a, b)
154
+ send_add(a, b)
155
+ return recv_add()
156
+ end
157
+
158
+ def send_add(a, b)
159
+ send_message('add', Add_args, :a => a, :b => b)
160
+ end
161
+
162
+ def recv_add()
163
+ result = receive_message(Add_result)
164
+ return result.success unless result.success.nil?
165
+ raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'add failed: unknown result')
166
+ end
167
+
130
168
  end
131
169
 
132
170
  class Processor
@@ -188,6 +226,30 @@ module UserStorage
188
226
  write_result(result, oprot, 'last_status', seqid)
189
227
  end
190
228
 
229
+ def process_volume_up(seqid, iprot, oprot)
230
+ args = read_args(iprot, Volume_up_args)
231
+ result = Volume_up_result.new()
232
+ begin
233
+ result.success = @handler.volume_up()
234
+ rescue RockTooHard => exc
235
+ result.exc = exc
236
+ end
237
+ write_result(result, oprot, 'volume_up', seqid)
238
+ end
239
+
240
+ def process_make_bitcoins(seqid, iprot, oprot)
241
+ args = read_args(iprot, Make_bitcoins_args)
242
+ @handler.make_bitcoins()
243
+ return
244
+ end
245
+
246
+ def process_add(seqid, iprot, oprot)
247
+ args = read_args(iprot, Add_args)
248
+ result = Add_result.new()
249
+ result.success = @handler.add(args.a, args.b)
250
+ write_result(result, oprot, 'add', seqid)
251
+ end
252
+
191
253
  end
192
254
 
193
255
  # HELPER FUNCTIONS AND STRUCTURES
@@ -447,5 +509,102 @@ module UserStorage
447
509
  ::Thrift::Struct.generate_accessors self
448
510
  end
449
511
 
512
+ class Volume_up_args
513
+ include ::Thrift::Struct, ::Thrift::Struct_Union
514
+
515
+ FIELDS = {
516
+
517
+ }
518
+
519
+ def struct_fields; FIELDS; end
520
+
521
+ def validate
522
+ end
523
+
524
+ ::Thrift::Struct.generate_accessors self
525
+ end
526
+
527
+ class Volume_up_result
528
+ include ::Thrift::Struct, ::Thrift::Struct_Union
529
+ SUCCESS = 0
530
+ EXC = 1
531
+
532
+ FIELDS = {
533
+ SUCCESS => {:type => ::Thrift::Types::I32, :name => 'success'},
534
+ EXC => {:type => ::Thrift::Types::STRUCT, :name => 'exc', :class => RockTooHard}
535
+ }
536
+
537
+ def struct_fields; FIELDS; end
538
+
539
+ def validate
540
+ end
541
+
542
+ ::Thrift::Struct.generate_accessors self
543
+ end
544
+
545
+ class Make_bitcoins_args
546
+ include ::Thrift::Struct, ::Thrift::Struct_Union
547
+
548
+ FIELDS = {
549
+
550
+ }
551
+
552
+ def struct_fields; FIELDS; end
553
+
554
+ def validate
555
+ end
556
+
557
+ ::Thrift::Struct.generate_accessors self
558
+ end
559
+
560
+ class Make_bitcoins_result
561
+ include ::Thrift::Struct, ::Thrift::Struct_Union
562
+
563
+ FIELDS = {
564
+
565
+ }
566
+
567
+ def struct_fields; FIELDS; end
568
+
569
+ def validate
570
+ end
571
+
572
+ ::Thrift::Struct.generate_accessors self
573
+ end
574
+
575
+ class Add_args
576
+ include ::Thrift::Struct, ::Thrift::Struct_Union
577
+ A = 1
578
+ B = 2
579
+
580
+ FIELDS = {
581
+ A => {:type => ::Thrift::Types::I32, :name => 'a'},
582
+ B => {:type => ::Thrift::Types::I32, :name => 'b'}
583
+ }
584
+
585
+ def struct_fields; FIELDS; end
586
+
587
+ def validate
588
+ end
589
+
590
+ ::Thrift::Struct.generate_accessors self
591
+ end
592
+
593
+ class Add_result
594
+ include ::Thrift::Struct, ::Thrift::Struct_Union
595
+ SUCCESS = 0
596
+
597
+ FIELDS = {
598
+ SUCCESS => {:type => ::Thrift::Types::I32, :name => 'success'}
599
+ }
600
+
601
+ def struct_fields; FIELDS; end
602
+
603
+ def validate
604
+ end
605
+
606
+ ::Thrift::Struct.generate_accessors self
607
+ end
608
+
450
609
  end
451
610
 
data/test/profile.thrift CHANGED
@@ -11,6 +11,10 @@ enum Status {
11
11
  ALIVE
12
12
  }
13
13
 
14
+ exception RockTooHard {
15
+ 1: i32 volume
16
+ }
17
+
14
18
  service UserStorage {
15
19
  void store(1: UserProfile xuser),
16
20
  UserProfile retrieve(1: i32 xuid),
@@ -19,6 +23,9 @@ service UserStorage {
19
23
  void set_list(1: list<string> l),
20
24
  list<string> last_list(),
21
25
  void set_status(1: Status s),
22
- Status last_status()
26
+ Status last_status(),
27
+ i32 volume_up() throws (1: RockTooHard exc),
28
+ oneway void make_bitcoins(),
29
+ i32 add(1: i32 a, 2: i32 b)
23
30
  }
24
31
 
data/test/test_client.rb CHANGED
@@ -19,7 +19,7 @@ class TestClient < Test::Unit::TestCase
19
19
  Stark.materialize "test/profile.thrift", @n
20
20
 
21
21
  @client = @n::UserStorage::Client.new @client_p, @client_p
22
- @handler = Handler.new
22
+ @handler = Handler.new(@n)
23
23
  @server = UserStorage::Processor.new @handler
24
24
  end
25
25
 
@@ -29,11 +29,12 @@ class TestClient < Test::Unit::TestCase
29
29
  end
30
30
 
31
31
  class Handler
32
- def initialize
32
+ def initialize(n)
33
33
  @users = {}
34
34
  @last_map = nil
35
35
  @last_list = nil
36
36
  @last_status = nil
37
+ @n = n
37
38
  end
38
39
 
39
40
  attr_accessor :last_map, :last_list, :last_status
@@ -57,6 +58,18 @@ class TestClient < Test::Unit::TestCase
57
58
  def set_status(s)
58
59
  @last_status = s
59
60
  end
61
+
62
+ def volume_up
63
+ raise RockTooHard.new(:volume => 11)
64
+ end
65
+
66
+ def make_bitcoins
67
+ sleep 2
68
+ end
69
+
70
+ def add(a,b)
71
+ a + b
72
+ end
60
73
  end
61
74
 
62
75
  def test_store_and_retrieve
@@ -181,4 +194,46 @@ class TestClient < Test::Unit::TestCase
181
194
 
182
195
  st.join
183
196
  end
197
+
198
+ def test_throw
199
+ st = Thread.new do
200
+ @server.process @server_p, @server_p
201
+ end
202
+
203
+ e = assert_raises @n::RockTooHard do
204
+ @client.volume_up
205
+ end
206
+
207
+ st.join
208
+
209
+ assert_equal 11, e.volume
210
+ end
211
+
212
+ # Thread.abort_on_exception = true
213
+
214
+ def test_oneway
215
+ st = Thread.new do
216
+ @server.process @server_p, @server_p
217
+ end
218
+
219
+ t = Time.now
220
+
221
+ Timeout.timeout 3 do
222
+ assert_equal nil, @client.make_bitcoins
223
+ end
224
+
225
+ assert Time.now - t < 0.1
226
+
227
+ st.join
228
+ end
229
+
230
+ def test_2args
231
+ st = Thread.new do
232
+ @server.process @server_p, @server_p
233
+ end
234
+
235
+ assert_equal 7, @client.add(3, 4)
236
+
237
+ st.join
238
+ end
184
239
  end
data/test/test_parser.rb CHANGED
@@ -10,6 +10,8 @@ class TestParser < Test::Unit::TestCase
10
10
  end
11
11
 
12
12
  assert tg.result
13
+
14
+ return tg.result
13
15
  end
14
16
 
15
17
  def test_ccomment
@@ -121,6 +123,21 @@ struct Foo {
121
123
  end
122
124
  end
123
125
 
126
+ def test_throws
127
+ o = parse <<-EOM
128
+ service Foo {
129
+ i32 foo() throws (1: i32 code)
130
+ }
131
+ EOM
132
+
133
+ o = o.first
134
+
135
+ assert_equal "Foo", o.name
136
+
137
+ assert_func o.functions[0], "i32", "foo", nil
138
+ assert_field o.functions[0].throws.first, 1, "i32", "code"
139
+ end
140
+
124
141
  def test_spec
125
142
  data = File.read "test/ThriftSpec.thrift"
126
143
 
data/test/test_server.rb CHANGED
@@ -17,7 +17,7 @@ class TestServer < Test::Unit::TestCase
17
17
  Stark.materialize "test/profile.thrift", @n
18
18
 
19
19
  @client = @n::UserStorage::Client.new @client_p, @client_p
20
- @handler = Handler.new
20
+ @handler = Handler.new @n
21
21
  @server = @n::UserStorage::Processor.new @handler
22
22
  end
23
23
 
@@ -27,11 +27,12 @@ class TestServer < Test::Unit::TestCase
27
27
  end
28
28
 
29
29
  class Handler
30
- def initialize
30
+ def initialize(n)
31
31
  @users = {}
32
32
  @last_map = nil
33
33
  @last_list = nil
34
34
  @last_status = nil
35
+ @n = n
35
36
  end
36
37
 
37
38
  attr_accessor :last_map, :last_list, :last_status
@@ -55,6 +56,14 @@ class TestServer < Test::Unit::TestCase
55
56
  def set_status(s)
56
57
  @last_status = s
57
58
  end
59
+
60
+ def volume_up
61
+ raise @n::RockTooHard.new('volume' => 11)
62
+ end
63
+
64
+ def make_bitcoins
65
+ sleep 2
66
+ end
58
67
  end
59
68
 
60
69
  def test_store_and_retrieve
@@ -172,4 +181,35 @@ class TestServer < Test::Unit::TestCase
172
181
  st.join
173
182
  end
174
183
 
184
+ def test_throw
185
+ st = Thread.new do
186
+ @server.process @server_p, @server_p
187
+ end
188
+
189
+ e = assert_raises @n::RockTooHard do
190
+ @client.volume_up
191
+ end
192
+
193
+ st.join
194
+
195
+ assert_equal 11, e.volume
196
+ end
197
+
198
+ # Thread.abort_on_exception = true
199
+
200
+ def test_oneway
201
+ st = Thread.new do
202
+ @server.process @server_p, @server_p
203
+ end
204
+
205
+ t = Time.now
206
+
207
+ Timeout.timeout 3 do
208
+ assert_equal nil, @client.make_bitcoins
209
+ end
210
+
211
+ assert Time.now - t < 0.1
212
+
213
+ st.join
214
+ end
175
215
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: stark
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.5.0
4
+ version: 0.6.0
5
5
  prerelease:
6
6
  platform: ruby
7
7
  authors:
@@ -9,7 +9,7 @@ authors:
9
9
  autorequire:
10
10
  bindir: bin
11
11
  cert_chain: []
12
- date: 2013-02-28 00:00:00.000000000 Z
12
+ date: 2013-03-03 00:00:00.000000000 Z
13
13
  dependencies:
14
14
  - !ruby/object:Gem::Dependency
15
15
  name: thrift