rubyless 0.3.2 → 0.3.3

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,3 +1,8 @@
1
+ == 0.3.3 2009-10-26
2
+
3
+ * 1 minor enhancement
4
+ * added support for symbols (only used with helper)
5
+
1
6
  == 0.3.2 2009-10-15
2
7
 
3
8
  * 1 minor enhancement
data/lib/processor.rb CHANGED
@@ -210,8 +210,8 @@ module RubyLess
210
210
 
211
211
  def get_method(signature, receiver, is_method = true)
212
212
  res = receiver.respond_to?(:safe_method_type) ? receiver.safe_method_type(signature) : SafeClass.safe_method_type_for(receiver, signature)
213
- res = res.call(@helper) if res.kind_of?(Proc)
214
- res
213
+ res = res.call(@helper, signature) if res.kind_of?(Proc)
214
+ res.kind_of?(Symbol) ? nil : res # Symbols not allowed here (should be resolved in receiver.safe_method_type)
215
215
  end
216
216
  end
217
217
  end
data/lib/rubyless.rb CHANGED
@@ -6,7 +6,7 @@ require 'processor'
6
6
  =begin rdoc
7
7
  =end
8
8
  module RubyLess
9
- VERSION = '0.3.2'
9
+ VERSION = '0.3.3'
10
10
 
11
11
  def self.translate(string, helper)
12
12
  RubyLessProcessor.translate(string, helper)
data/lib/safe_class.rb CHANGED
@@ -10,11 +10,7 @@ module RubyLess
10
10
 
11
11
  # Return method type (options) if the given signature is a safe method for the class.
12
12
  def self.safe_method_type_for(klass, signature)
13
- if res = safe_methods_for(klass)[signature]
14
- res.dup
15
- else
16
- nil
17
- end
13
+ safe_methods_for(klass)[signature]
18
14
  end
19
15
 
20
16
  # Declare a safe method for a given class
@@ -65,7 +61,7 @@ module RubyLess
65
61
  if v.kind_of?(Hash)
66
62
  v = defaults.merge(v)
67
63
  v[:method] = v[:method] ? v[:method].to_s : k.first.to_s
68
- elsif v.kind_of?(Proc)
64
+ elsif v.kind_of?(Proc) || v.kind_of?(Symbol)
69
65
  # cannot merge defaults
70
66
  else
71
67
  v = defaults.merge(:class => v, :method => k.first.to_s)
@@ -106,22 +102,21 @@ module RubyLess
106
102
  SafeClass.safe_methods_for(self)
107
103
  end
108
104
 
109
- # Return true if the given signature corresponds to a safe method for the class.
105
+ # Return the type if the given signature corresponds to a safe method for the class.
110
106
  def self.safe_method_type(signature)
111
- if res = SafeClass.safe_method_type_for(self, signature)
112
- res.dup # TODO: replace by freeze
113
- else
114
- nil
115
- end
116
- end
117
-
118
- # Return the method type (options) if the given signature is a safe method for the class.
119
- def safe_method_type(signature)
120
- self.class.safe_method_type(signature)
107
+ SafeClass.safe_method_type_for(self, signature)
121
108
  end
122
109
  end # base.class_eval
123
110
  end # included
124
111
 
112
+
113
+ # Return the type if the given signature corresponds to a safe method for the object's class.
114
+ def safe_method_type(signature)
115
+ if type = self.class.safe_method_type(signature)
116
+ type.kind_of?(Symbol) ? self.send(type, signature) : type
117
+ end
118
+ end
119
+
125
120
  # Safe attribute reader used when 'safe_readable?' could not be called because the class
126
121
  # is not known during compile time.
127
122
  def safe_read(key)
@@ -135,12 +130,14 @@ module RubyLess
135
130
  (@@_safe_methods[klass] || {}).map do |signature, return_value|
136
131
  if return_value.kind_of?(Hash)
137
132
  return_value[:class] = parse_class(return_value[:class])
138
- elsif !return_value.kind_of?(Proc)
133
+ elsif return_value.kind_of?(Proc) || return_value.kind_of?(Symbol)
134
+ # keep
135
+ else
139
136
  return_value = {:class => return_value}
140
137
  end
141
138
  method = signature.shift
142
139
  signature = [method] + signature.map {|e| parse_class(e)}
143
- list[signature] = return_value
140
+ list[signature] = return_value.freeze
144
141
  end
145
142
  list
146
143
  end
data/rubyless.gemspec CHANGED
@@ -2,11 +2,11 @@
2
2
 
3
3
  Gem::Specification.new do |s|
4
4
  s.name = %q{rubyless}
5
- s.version = "0.3.1"
5
+ s.version = "0.3.3"
6
6
 
7
7
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
8
8
  s.authors = ["Gaspard Bucher"]
9
- s.date = %q{2009-10-03}
9
+ s.date = %q{2009-10-26}
10
10
  s.description = %q{RubyLess is an interpreter for "safe ruby". The idea is to transform some "unsafe" ruby code into safe, type checked
11
11
  ruby, eventually rewriting some variables or methods.}
12
12
  s.email = %q{gaspard@teti.ch}
@@ -86,4 +86,8 @@ multi_arg_method_arguments_can_be_nil_same_condition:
86
86
 
87
87
  literal_argument_for_method:
88
88
  src: "vowel_count('ruby')"
89
- res: "2"
89
+ res: "2"
90
+
91
+ safe_method_defined_as_symbol:
92
+ src: "foo"
93
+ tem: "contextual_foo"
@@ -10,7 +10,7 @@ zero_div:
10
10
  src: "1/(id-10)"
11
11
  tem: "(1/(var1.zip-10) rescue nil)"
12
12
  res: ""
13
-
13
+
14
14
  looping:
15
15
  src: "while(true) do puts 'flood' end"
16
16
  res: 'Bug! Unknown node-type :while to RubyLess::RubyLessProcessor'
@@ -29,4 +29,8 @@ number_argument:
29
29
 
30
30
  string_argument:
31
31
  src: "dictionary[spouse.name]"
32
- res: "'get_dict' does not respond to '[](String)'."
32
+ res: "'get_dict' does not respond to '[](String)'."
33
+
34
+ symbol_type_not_used_out_of_helper:
35
+ src: "node.foo"
36
+ res: "'var1' does not respond to 'foo()'."
@@ -12,28 +12,33 @@ class SimpleHelper < Test::Unit::TestCase
12
12
  include RubyLess::SafeClass
13
13
  safe_method :prev => {:class => Dummy, :method => 'previous'}
14
14
  safe_method :main => {:class => Dummy, :method => '@node'}
15
- safe_method :node => lambda {|h| {:class => h.context[:node_class], :method => h.context[:node]}}
15
+ safe_method :node => lambda {|h, s| {:class => h.context[:node_class], :method => h.context[:node]}}
16
16
  safe_method :now => {:class => Time, :method => "Time.now"}
17
17
  safe_method :birth => {:class => Time, :method => "Date.parse('2009-06-02 18:44')"}
18
18
  safe_method 'dictionary' => {:class => StringDictionary, :method => 'get_dict'}
19
19
  safe_method [:vowel_count, String] => Number
20
20
  safe_method [:log_info, Dummy, String] => String
21
+ safe_method :foo => :contextual_method, :bar => :contextual_method
21
22
  safe_method_for String, [:==, String] => Boolean
22
23
  safe_method_for String, [:to_s] => String
23
24
  safe_method_for Time, [:strftime, String] => String
24
25
 
25
26
  # Example to dynamically rewrite method calls during compilation
26
27
  def safe_method_type(signature)
27
- unless res = self.class.safe_method_type(signature)
28
+ unless res = super
28
29
  # try to execute method in the current var "var.method"
29
30
  if res = context[:node_class].safe_method_type(signature)
30
- res = res.call(self) if res.kind_of?(Proc)
31
- res[:method] = "#{context[:node]}.#{res[:method] || signature[0]}"
31
+ res = res.call(self, signature) if res.kind_of?(Proc)
32
+ res = res.merge(:method => "#{context[:node]}.#{res[:method] || signature[0]}")
32
33
  end
33
34
  end
34
35
  res
35
36
  end
36
37
 
38
+ def contextual_method(signature)
39
+ {:method => "contextual_#{signature[0]}", :class => String}
40
+ end
41
+
37
42
  def var1
38
43
  Dummy.new
39
44
  end
@@ -75,7 +80,7 @@ class SimpleHelper < Test::Unit::TestCase
75
80
  rescue => err
76
81
  # puts "\n\n#{err.message}"
77
82
  # puts err.backtrace
78
- err.message
83
+ err.message
79
84
  end
80
85
 
81
86
  yt_make
@@ -3,37 +3,38 @@ require File.dirname(__FILE__) + '/active_record_mock'
3
3
  class Dummy < RubyLess::ActiveRecordMock
4
4
  attr_reader :name
5
5
  include RubyLess::SafeClass
6
-
6
+
7
7
  safe_method [:ancestor?, Dummy] => Boolean
8
8
  safe_method :parent => {:class => 'Dummy', :special_option => 'foobar'},
9
9
  :children => ['Dummy'],
10
10
  :project => 'Dummy',
11
11
  :id => {:class => Number, :method => :zip},
12
- :name => String
12
+ :name => String,
13
+ :foo => :bar
13
14
  safe_method :defaults => {:nil => true},
14
15
  :spouse => 'Dummy',
15
16
  :husband => {:class => 'Dummy'}
16
-
17
+
17
18
  safe_attribute :age, :friend_id, :log_at, :format
18
-
19
+
19
20
  def initialize(name = 'dummy')
20
21
  @name = name
21
22
  end
22
-
23
+
23
24
  # This method returns pseudo-nil and does not need to be declared with :nil => true
24
25
  def project
25
26
  Dummy.new('project')
26
27
  end
27
-
28
+
28
29
  # This method can return nil and must be declared with :nil => true
29
30
  def spouse
30
31
  nil
31
32
  end
32
-
33
+
33
34
  def husband
34
35
  nil
35
36
  end
36
-
37
+
37
38
  def zip
38
39
  10
39
40
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: rubyless
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.2
4
+ version: 0.3.3
5
5
  platform: ruby
6
6
  authors:
7
7
  - Gaspard Bucher
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-10-15 00:00:00 +02:00
12
+ date: 2009-10-26 00:00:00 +01:00
13
13
  default_executable:
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency