safemode 1.3.1 → 1.3.6

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
- SHA1:
3
- metadata.gz: 7a2ae334b96360e57f06053963af98bb3565e1d1
4
- data.tar.gz: 4ad12d5c492b17595d6dda6aa8caec4ca154f03f
2
+ SHA256:
3
+ metadata.gz: 9c122fc8f941080a885c335b7356d2e1af7545cec8633ca23571273f069f36e0
4
+ data.tar.gz: f5555df33c321fbc85bff612c80568c4667e1c17d77aaa74da3311ea659b2574
5
5
  SHA512:
6
- metadata.gz: '0942dbc88ee4246dc414c598555822b58b5ba18f6b7471edcb3e583ed1e42c442b3b0724a927d4150ea705b9eb95f7f33cd947074f83f2326dfecaabc65d880a'
7
- data.tar.gz: 9338694a4120ca2190e4dcf6151d2cf8822b155fc887396ae63e0671734075ba325cad4c5a38a44cc7b98540fa0b37ea28b611aed76be50e6d216c5a4a4f7cec
6
+ metadata.gz: 253de818e490f1e03030dfb9600960322ee6ea3c2d1d7ae571ccbc9ad44c99cb58af2d23227d6244a4de4006e0d56716b6b12c5fe83fc2fb8c874bbae5f1aca1
7
+ data.tar.gz: 2b468cf47ef692c3623daba9b1ea100ab4e74243d701aad3c86e46a04cc09d91470a9a57c5ecd117f26142b223ec33f1169b09bc90756d5dc96104d9b00c341e
@@ -0,0 +1,16 @@
1
+ ---
2
+ os: linux
3
+ dist: xenial
4
+ language: ruby
5
+ rvm:
6
+ - 2.2
7
+ - 2.3
8
+ - 2.4
9
+ - 2.5
10
+ - 2.6
11
+ - 2.7
12
+ - jruby-9
13
+ matrix:
14
+ allow_failures:
15
+ - rvm: jruby-9
16
+ before_install: gem install bundler --version 1.17.3
data/Gemfile CHANGED
@@ -1,18 +1,17 @@
1
- source "http://rubygems.org"
1
+ # frozen_string_literal: true
2
2
 
3
- gem 'sexp_processor', ">= 4.3.0"
4
- gem 'ruby2ruby', ">= 2.0.6"
5
- gem "ruby_parser", ">= 3.2.0"
3
+ source 'http://rubygems.org'
4
+
5
+ gem 'ruby2ruby', '>= 2.4.0'
6
+ gem 'ruby_parser', '>= 3.10.1'
7
+ gem 'sexp_processor', '>= 4.10.0'
6
8
 
7
9
  # Add dependencies to develop your gem here.
8
10
  # Include everything needed to run rake, tests, features, etc.
9
11
  group :development do
10
- gem "shoulda", ">= 0"
11
- gem "rdoc", "~> 3.12"
12
- gem "bundler", "~> 1.0"
13
- gem "jeweler", ">= 0"
14
- gem "rcov", :platforms => :ruby_18
15
- gem "simplecov", :platforms => [:ruby_19, :ruby_20, :ruby_21, :ruby_22, :ruby_23, :ruby_24]
16
- gem "test-unit", :platforms => [:ruby_19, :ruby_20, :ruby_21, :ruby_22, :ruby_23, :ruby_24]
17
- gem "rake"
12
+ gem 'jeweler'
13
+ gem 'rake'
14
+ gem 'rdoc', '~> 3.12'
15
+ gem 'simplecov'
16
+ gem 'test-unit'
18
17
  end
@@ -3,6 +3,8 @@
3
3
  A library for safe evaluation of Ruby code based on RubyParser and
4
4
  Ruby2Ruby. Provides Rails ActionView template handlers for ERB and Haml.
5
5
 
6
+ [![Build Status](https://travis-ci.org/svenfuchs/safemode.svg?branch=master)](https://travis-ci.org/svenfuchs/safemode)
7
+
6
8
  ### Word of warning
7
9
 
8
10
  This library is still highly experimental. Only use it at your own risk for
@@ -52,9 +54,9 @@ class is only accessible when returned by a method or passed into a template.
52
54
  For more details about the concepts behind Safemode please refer to the
53
55
  following blog posts until a more comprehensive writeup is available:
54
56
 
55
- * Initial reasoning: [http://www.artweb-design.de/2008/2/5/sexy-theme-templating-with-haml-safemode-finally](http://www.artweb-design.de/2008/2/5/sexy-theme-templating-with-haml-safemode-finally)
56
- * Refined concept: [http://www.artweb-design.de/2008/2/17/sending-ruby-to-the-jail-an-attemp-on-a-haml-safemode](http://www.artweb-design.de/2008/2/17/sending-ruby-to-the-jail-an-attemp-on-a-haml-safemode)
57
- * ActionView ERB handler: [http://www.artweb-design.de/2008/4/22/an-erb-safemode-handler-for-actionview](http://www.artweb-design.de/2008/4/22/an-erb-safemode-handler-for-actionview)
57
+ * Initial reasoning: http://www.artweb-design.de/2008/2/5/sexy-theme-templating-with-haml-safemode-finally
58
+ * Refined concept: http://www.artweb-design.de/2008/2/17/sending-ruby-to-the-jail-an-attemp-on-a-haml-safemode
59
+ * ActionView ERB handler: http://www.artweb-design.de/2008/4/22/an-erb-safemode-handler-for-actionview
58
60
 
59
61
  ### Dependencies
60
62
 
@@ -64,14 +66,14 @@ Requires the gems:
64
66
  * Ruby2Ruby
65
67
 
66
68
  As of writing RubyParser alters StringIO and thus breaks usage with Rails.
67
- See [http://www.zenspider.com/pipermail/parsetree/2008-April/000026.html](http://www.zenspider.com/pipermail/parsetree/2008-April/000026.html)
69
+ See http://www.zenspider.com/pipermail/parsetree/2008-April/000026.html
68
70
 
69
71
  A patch is included that fixes this issue and can be applied to RubyParser.
70
72
  See lib/ruby\_parser\_string\_io\_patch.diff
71
73
 
72
74
  ### Credits
73
75
 
74
- * Sven Fuchs - Maintainer
76
+ * Sven Fuchs - Initial Maintainer
75
77
  * Peter Cooper
76
78
  * Matthias Viehweger
77
79
  * Ohad Levy
data/Rakefile CHANGED
@@ -47,20 +47,10 @@ Rake::TestTask.new(:test) do |test|
47
47
  test.verbose = true
48
48
  end
49
49
 
50
- if RUBY_VERSION >= "1.9"
51
- desc "Generate coverage report for tests"
52
- task :coverage do |cov|
53
- ENV['COVERAGE'] = 'true'
54
- Rake::Task[:test].execute
55
- end
56
- else
57
- require 'rcov/rcovtask'
58
- Rcov::RcovTask.new do |test|
59
- test.libs << 'test'
60
- test.pattern = 'test/**/test_*.rb'
61
- test.verbose = true
62
- test.rcov_opts << '--exclude "gems/*"'
63
- end
50
+ desc "Generate coverage report for tests"
51
+ task :coverage do |cov|
52
+ ENV['COVERAGE'] = 'true'
53
+ Rake::Task[:test].execute
64
54
  end
65
55
 
66
56
  task :default => :test
data/VERSION CHANGED
@@ -1 +1 @@
1
- 1.3.1
1
+ 1.3.6
@@ -20,9 +20,9 @@ module ActionView
20
20
 
21
21
  # code = ::ERB.new(src, nil, @view.erb_trim_mode).src
22
22
  code = ::ERB.new("<% __in_erb_template=true %>#{src}", nil, erb_trim_mode, '@output_buffer').src
23
- # Ruby 1.9 prepends an encoding to the source. However this is
23
+ # Ruby 1.9+ prepends an encoding to the source. However this is
24
24
  # useless because you can only set an encoding on the first line
25
- RUBY_VERSION >= '1.9' ? src.sub(/\A#coding:.*\n/, '') : src
25
+ src.sub(/\A#coding:.*\n/, '') : src
26
26
 
27
27
  code.gsub!('\\','\\\\\\') # backslashes would disappear in compile_template/modul_eval, so we escape them
28
28
 
@@ -1,7 +1,13 @@
1
1
  module Safemode
2
2
  class Blankslate
3
3
  @@allow_instance_methods = ['class', 'methods', 'respond_to?', 'respond_to_missing?', 'to_s', 'instance_variable_get']
4
- @@allow_class_methods = ['methods', 'new', 'name', '<', 'ancestors', '=='] # < needed in Rails Object#subclasses_of
4
+ @@allow_class_methods = ['methods', 'new', 'name', '<', 'ancestors', '=='] # < needed in Rails Object#subclasses_of
5
+ if defined?(JRUBY_VERSION)
6
+ # JRuby seems to silently fail to remove method_missing
7
+ # (also see https://github.com/jruby/jruby/blob/9.1.7.0/core/src/main/java/org/jruby/RubyModule.java#L1109)
8
+ @@allow_class_methods << 'method_missing'
9
+ (@@allow_class_methods << ['singleton_method_undefined', 'singleton_method_added']).flatten! # needed for JRuby support
10
+ end
5
11
 
6
12
  silently { undef_methods(*instance_methods.map(&:to_s) - @@allow_instance_methods) }
7
13
  class << self
@@ -41,7 +41,7 @@ module Safemode
41
41
  # these methods are allowed in all classes if they are present
42
42
  @@default_methods = %w( % & * ** + +@ - -@ / < << <= <=> ! != == === > >= >> ^ | ~
43
43
  eql? equal? new methods is_a? kind_of? nil?
44
- [] []= to_a to_jail to_s inspect to_param not)
44
+ [] []= to_a to_jail to_s inspect to_param not freeze)
45
45
 
46
46
  # whitelisted methods for core classes ... kind of arbitrary selection
47
47
  @@methods_whitelist = {
@@ -51,8 +51,8 @@ module Safemode
51
51
  indexes indices inject insert join last length map map!
52
52
  nitems pop push present? rassoc reject reject! reverse
53
53
  reverse! reverse_each rindex select shift size slice
54
- slice! sort sort! transpose uniq uniq! unshift values_at
55
- zip),
54
+ slice! sort sort! transpose to_sentence uniq uniq! unshift
55
+ values_at zip),
56
56
 
57
57
  'Bignum' => %w(abs blank? ceil chr coerce div divmod downto floor hash
58
58
  integer? modulo next nonzero? present? quo remainder round
@@ -1,17 +1,17 @@
1
- module Safemode
2
- class Jail < Blankslate
1
+ module Safemode
2
+ class Jail < Blankslate
3
3
  def initialize(source = nil)
4
4
  @source = source
5
5
  end
6
-
6
+
7
7
  def to_jail
8
8
  self
9
9
  end
10
-
10
+
11
11
  def to_s
12
12
  @source.to_s
13
13
  end
14
-
14
+
15
15
  def method_missing(method, *args, &block)
16
16
  if @source.is_a?(Class)
17
17
  unless self.class.allowed_class_method?(method)
@@ -22,7 +22,7 @@ module Safemode
22
22
  raise Safemode::NoMethodError.new("##{method}", self.class.name, @source.class.name)
23
23
  end
24
24
  end
25
-
25
+
26
26
  # As every call to an object in the eval'ed string will be jailed by the
27
27
  # parser we don't need to "proactively" jail arrays and hashes. Likewise we
28
28
  # don't need to jail objects returned from a jail. Doing so would provide
@@ -31,11 +31,6 @@ module Safemode
31
31
  @source.send(method, *args, &block)
32
32
  end
33
33
 
34
- # needed for compatibility with 1.8.7; remove this method once 1.8.7 support has been dropped
35
- def respond_to?(method, *)
36
- respond_to_missing?(method)
37
- end
38
-
39
34
  def respond_to_missing?(method_name, include_private = false)
40
35
  self.class.allowed_instance_method?(method_name)
41
36
  end
@@ -2,14 +2,14 @@ module Safemode
2
2
  class Parser < Ruby2Ruby
3
3
  # @@parser = defined?(RubyParser) ? 'RubyParser' : 'ParseTree'
4
4
  @@parser = 'RubyParser'
5
-
5
+
6
6
  class << self
7
7
  def jail(code, allowed_fcalls = [])
8
8
  @@allowed_fcalls = allowed_fcalls
9
9
  tree = parse code
10
10
  self.new.process(tree)
11
11
  end
12
-
12
+
13
13
  def parse(code)
14
14
  case @@parser
15
15
  # when 'ParseTree'
@@ -20,12 +20,12 @@ module Safemode
20
20
  raise "unknown parser #{@@parser}"
21
21
  end
22
22
  end
23
-
23
+
24
24
  def parser=(parser)
25
25
  @@parser = parser
26
26
  end
27
27
  end
28
-
28
+
29
29
  def jail(str, parentheses = false)
30
30
  str = parentheses ? "(#{str})." : "#{str}." if str
31
31
  "#{str}to_jail"
@@ -33,13 +33,14 @@ module Safemode
33
33
 
34
34
  # split up #process_call. see below ...
35
35
  def process_call(exp)
36
+ exp.shift # remove ":call" symbol
36
37
  receiver = jail process_call_receiver(exp)
37
38
  name = exp.shift
38
39
  args = process_call_args(exp)
39
40
 
40
41
  process_call_code(receiver, name, args)
41
42
  end
42
-
43
+
43
44
  def process_fcall(exp)
44
45
  # using haml we probably never arrive here because :lasgn'ed :fcalls
45
46
  # somehow seem to change to :calls somewhere during processing
@@ -85,7 +86,7 @@ module Safemode
85
86
  # :colon2 is used for module constants
86
87
  :colon2,
87
88
  # unnecessarily advanced?
88
- :argscat, :argspush, :splat, :block_pass,
89
+ :argscat, :argspush, :splat,
89
90
  :op_asgn1, :op_asgn2, :op_asgn_and, :op_asgn_or,
90
91
  # needed for haml
91
92
  :block ]
@@ -101,13 +102,17 @@ module Safemode
101
102
  :attrasgn, :cdecl, :cvasgn, :cvdecl, :cvar, :gvar, :gasgn,
102
103
  :xstr, :dxstr,
103
104
  # not sure how secure ruby regexp is, so leave it out for now
104
- :dregx, :dregx_once, :match2, :match3, :nth_ref, :back_ref ]
105
+ :dregx, :dregx_once, :match2, :match3, :nth_ref, :back_ref,
106
+ # block_pass represents &:method, which would bypass the whitelist e.g. by array.each(&:destroy)
107
+ # at this point we don't know the receiver so we rather disable it completely,
108
+ # use array.each { |item| item.destroy } instead
109
+ :block_pass ]
105
110
 
106
- # SexpProcessor bails when we overwrite these ... but they are listed as
111
+ # SexpProcessor bails when we overwrite these ... but they are listed as
107
112
  # "internal nodes that you can't get to" in sexp_processor.rb
108
113
  # :ifunc, :method, :last, :opt_n, :cfunc, :newline, :alloca, :memo, :cref
109
-
110
- disallowed.each do |name|
114
+
115
+ disallowed.each do |name|
111
116
  define_method "process_#{name}" do |arg|
112
117
  code = super(arg)
113
118
  raise_security_error(name, code)
@@ -115,30 +120,31 @@ module Safemode
115
120
  end
116
121
 
117
122
  def process_const(arg)
118
- if RUBY_VERSION >= "1.9" && arg.sexp_type == :Encoding
119
- # handling of Encoding constants in ruby 1.9.
123
+ sexp_type = arg.sexp_body.sexp_type # constants are encoded as: "s(:const, :Encoding)"
124
+ if sexp_type == :Encoding
125
+ # handling of Encoding constants.
120
126
  # Note: ruby_parser evaluates __ENCODING__ to s(:colon2, s(:const, :Encoding), :UTF_8)
121
127
  "#{super(arg).gsub('-', '_')}"
122
- elsif arg.sexp_type == :String
128
+ elsif sexp_type == :String
123
129
  # Allow String.new as used in ERB in Ruby 2.4+ to create a string buffer
124
130
  super(arg).to_s
125
131
  else
126
132
  raise_security_error("constant", super(arg))
127
133
  end
128
134
  end
129
-
135
+
130
136
  def raise_security_error(type, info)
131
137
  raise Safemode::SecurityError.new(type, info)
132
138
  end
133
-
139
+
134
140
  # split up Ruby2Ruby#process_call monster method so we can hook into it
135
141
  # in a more readable manner
136
142
 
137
143
  def process_call_receiver(exp)
138
144
  receiver_node_type = exp.first.nil? ? nil : exp.first.first
139
- receiver = process exp.shift
145
+ receiver = process exp.shift
140
146
  receiver = "(#{receiver})" if
141
- Ruby2Ruby::ASSIGN_NODES.include? receiver_node_type
147
+ Ruby2Ruby::ASSIGN_NODES.include? receiver_node_type
142
148
  receiver
143
149
  end
144
150
 
@@ -174,15 +180,16 @@ module Safemode
174
180
  end
175
181
  end
176
182
  end
177
-
183
+
178
184
  # Ruby2Ruby process_if rewrites if and unless statements in a way that
179
185
  # makes the result unusable for evaluation in, e.g. ERB which appends a
180
- # call to to_s when using <%= %> tags. We'd need to either enclose the
186
+ # call to to_s when using <%= %> tags. We'd need to either enclose the
181
187
  # result from process_if into parentheses like (1 if true) and
182
188
  # (true ? (1) : (2)) or just use the plain if-then-else-end syntax (so
183
189
  # that ERB can safely append to_s to the resulting block).
184
190
 
185
191
  def process_if(exp)
192
+ exp.shift # remove ":if" symbol from exp
186
193
  expand = Ruby2Ruby::ASSIGN_NODES.include? exp.first.first
187
194
  c = process exp.shift
188
195
  t = process exp.shift
@@ -212,6 +219,6 @@ module Safemode
212
219
  # end
213
220
  "unless #{c} then\n#{indent(f)}\nend"
214
221
  end
215
- end
216
- end
222
+ end
223
+ end
217
224
  end
@@ -2,22 +2,23 @@
2
2
  # DO NOT EDIT THIS FILE DIRECTLY
3
3
  # Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
4
4
  # -*- encoding: utf-8 -*-
5
- # stub: safemode 1.3.1 ruby lib
5
+ # stub: safemode 1.3.6 ruby lib
6
6
 
7
7
  Gem::Specification.new do |s|
8
8
  s.name = "safemode".freeze
9
- s.version = "1.3.1"
9
+ s.version = "1.3.6"
10
10
 
11
11
  s.required_rubygems_version = Gem::Requirement.new(">= 0".freeze) if s.respond_to? :required_rubygems_version=
12
12
  s.require_paths = ["lib".freeze]
13
13
  s.authors = ["Sven Fuchs".freeze, "Peter Cooper".freeze, "Matthias Viehweger".freeze, "Kingsley Hendrickse".freeze, "Ohad Levy".freeze, "Dmitri Dolguikh".freeze]
14
- s.date = "2017-02-13"
14
+ s.date = "2020-08-31"
15
15
  s.description = "A library for safe evaluation of Ruby code based on RubyParser and Ruby2Ruby. Provides Rails ActionView template handlers for ERB and Haml.".freeze
16
16
  s.email = "ohadlevy@gmail.com".freeze
17
17
  s.extra_rdoc_files = [
18
18
  "README.markdown"
19
19
  ]
20
20
  s.files = [
21
+ ".travis.yml",
21
22
  "Gemfile",
22
23
  "LICENCSE",
23
24
  "README.markdown",
@@ -48,49 +49,40 @@ Gem::Specification.new do |s|
48
49
  ]
49
50
  s.homepage = "http://github.com/svenfuchs/safemode".freeze
50
51
  s.licenses = ["MIT".freeze]
51
- s.rubygems_version = "2.6.10".freeze
52
+ s.rubygems_version = "2.7.6".freeze
52
53
  s.summary = "A library for safe evaluation of Ruby code based on ParseTree/RubyParser and Ruby2Ruby".freeze
53
54
 
54
55
  if s.respond_to? :specification_version then
55
56
  s.specification_version = 4
56
57
 
57
58
  if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
58
- s.add_runtime_dependency(%q<sexp_processor>.freeze, [">= 4.3.0"])
59
- s.add_runtime_dependency(%q<ruby2ruby>.freeze, [">= 2.0.6"])
60
- s.add_runtime_dependency(%q<ruby_parser>.freeze, [">= 3.2.0"])
61
- s.add_development_dependency(%q<shoulda>.freeze, [">= 0"])
62
- s.add_development_dependency(%q<rdoc>.freeze, ["~> 3.12"])
63
- s.add_development_dependency(%q<bundler>.freeze, ["~> 1.0"])
59
+ s.add_runtime_dependency(%q<ruby2ruby>.freeze, [">= 2.4.0"])
60
+ s.add_runtime_dependency(%q<ruby_parser>.freeze, [">= 3.10.1"])
61
+ s.add_runtime_dependency(%q<sexp_processor>.freeze, [">= 4.10.0"])
64
62
  s.add_development_dependency(%q<jeweler>.freeze, [">= 0"])
65
- s.add_development_dependency(%q<rcov>.freeze, [">= 0"])
63
+ s.add_development_dependency(%q<rake>.freeze, [">= 0"])
64
+ s.add_development_dependency(%q<rdoc>.freeze, ["~> 3.12"])
66
65
  s.add_development_dependency(%q<simplecov>.freeze, [">= 0"])
67
66
  s.add_development_dependency(%q<test-unit>.freeze, [">= 0"])
68
- s.add_development_dependency(%q<rake>.freeze, [">= 0"])
69
67
  else
70
- s.add_dependency(%q<sexp_processor>.freeze, [">= 4.3.0"])
71
- s.add_dependency(%q<ruby2ruby>.freeze, [">= 2.0.6"])
72
- s.add_dependency(%q<ruby_parser>.freeze, [">= 3.2.0"])
73
- s.add_dependency(%q<shoulda>.freeze, [">= 0"])
74
- s.add_dependency(%q<rdoc>.freeze, ["~> 3.12"])
75
- s.add_dependency(%q<bundler>.freeze, ["~> 1.0"])
68
+ s.add_dependency(%q<ruby2ruby>.freeze, [">= 2.4.0"])
69
+ s.add_dependency(%q<ruby_parser>.freeze, [">= 3.10.1"])
70
+ s.add_dependency(%q<sexp_processor>.freeze, [">= 4.10.0"])
76
71
  s.add_dependency(%q<jeweler>.freeze, [">= 0"])
77
- s.add_dependency(%q<rcov>.freeze, [">= 0"])
72
+ s.add_dependency(%q<rake>.freeze, [">= 0"])
73
+ s.add_dependency(%q<rdoc>.freeze, ["~> 3.12"])
78
74
  s.add_dependency(%q<simplecov>.freeze, [">= 0"])
79
75
  s.add_dependency(%q<test-unit>.freeze, [">= 0"])
80
- s.add_dependency(%q<rake>.freeze, [">= 0"])
81
76
  end
82
77
  else
83
- s.add_dependency(%q<sexp_processor>.freeze, [">= 4.3.0"])
84
- s.add_dependency(%q<ruby2ruby>.freeze, [">= 2.0.6"])
85
- s.add_dependency(%q<ruby_parser>.freeze, [">= 3.2.0"])
86
- s.add_dependency(%q<shoulda>.freeze, [">= 0"])
87
- s.add_dependency(%q<rdoc>.freeze, ["~> 3.12"])
88
- s.add_dependency(%q<bundler>.freeze, ["~> 1.0"])
78
+ s.add_dependency(%q<ruby2ruby>.freeze, [">= 2.4.0"])
79
+ s.add_dependency(%q<ruby_parser>.freeze, [">= 3.10.1"])
80
+ s.add_dependency(%q<sexp_processor>.freeze, [">= 4.10.0"])
89
81
  s.add_dependency(%q<jeweler>.freeze, [">= 0"])
90
- s.add_dependency(%q<rcov>.freeze, [">= 0"])
82
+ s.add_dependency(%q<rake>.freeze, [">= 0"])
83
+ s.add_dependency(%q<rdoc>.freeze, ["~> 3.12"])
91
84
  s.add_dependency(%q<simplecov>.freeze, [">= 0"])
92
85
  s.add_dependency(%q<test-unit>.freeze, [">= 0"])
93
- s.add_dependency(%q<rake>.freeze, [">= 0"])
94
86
  end
95
87
  end
96
88
 
@@ -1,4 +1,4 @@
1
- if RUBY_VERSION >= '1.9'and ENV['COVERAGE']
1
+ if ENV['COVERAGE']
2
2
  require 'simplecov'
3
3
  SimpleCov.start {add_filter 'test_'}
4
4
  end
@@ -22,7 +22,7 @@ module TestHelper
22
22
  '@article.comment_class.new',
23
23
  'String.instance_variable_set :@a, :a' ]
24
24
  end
25
-
25
+
26
26
  def security_error_raising_calls
27
27
  [ "class A\n end",
28
28
  'File.open("/etc/passwd")',
@@ -42,10 +42,10 @@ module TestHelper
42
42
  "attr_reader :a",
43
43
  'URI("http://google.com")',
44
44
  "`ls -a`", "exec('echo *')", "syscall 4, 1, 'hello', 5", "system('touch /tmp/helloworld')",
45
- "abort",
45
+ "abort",
46
46
  "exit(0)", "exit!(0)", "at_exit{'goodbye'}",
47
47
  "autoload(::MyModule, 'my_module.rb')",
48
- "binding",
48
+ "binding",
49
49
  "callcc{|cont| cont.call}",
50
50
  'eval %Q(send(:system, "ls -a"))',
51
51
  "fork",
@@ -58,12 +58,12 @@ module TestHelper
58
58
  "open('/etc/passwd'){|f| f.read}",
59
59
  "p 'text'", "pretty_inspect",
60
60
  # "print 'text'", "puts 'text'", allowed and buffered these (see ScopeObject)
61
- "printf 'text'", "putc 'a'",
61
+ "printf 'text'", "putc 'a'",
62
62
  "raise RuntimeError, 'should not happen'",
63
- "rand(0)", "srand(0)",
63
+ "rand(0)", "srand(0)",
64
64
  "set_trace_func proc{|event| puts event}", "trace_var :$_, proc {|v| puts v }", "untrace_var :$_",
65
- "sleep", "sleep(0)",
66
- "test(1, a, b)",
65
+ "sleep", "sleep(0)",
66
+ "test(1, a, b)",
67
67
  "Signal.trap(0, proc { puts 'Terminating: #{$$}' })",
68
68
  "warn 'warning'",
69
69
  'Array.new' ]
@@ -77,31 +77,31 @@ module TestHelper
77
77
  def assert_raise_security(code = nil, assigns = {}, locals = {}, &block)
78
78
  assert_raise_safemode_error(Safemode::SecurityError, code, assigns, locals, &block)
79
79
  end
80
-
80
+
81
81
  def assert_raise_safemode_error(error, code, assigns = {}, locals = {})
82
82
  code = yield(code) if block_given?
83
83
  assert_raise(error, code) { safebox_eval(code, assigns, locals) }
84
84
  end
85
-
85
+
86
86
  def safebox_eval(code, assigns = {}, locals = {})
87
87
  # puts Safemode::Parser.jail(code)
88
88
  Safemode::Box.new.eval code, assigns, locals
89
- end
89
+ end
90
90
  end
91
91
 
92
92
  class Article
93
93
  def is_article?
94
94
  true
95
95
  end
96
-
96
+
97
97
  def title
98
98
  'an article title'
99
99
  end
100
-
100
+
101
101
  def to_jail
102
102
  Article::Jail.new self
103
103
  end
104
-
104
+
105
105
  def comments
106
106
  [Comment.new(self), Comment.new(self)]
107
107
  end
@@ -117,15 +117,15 @@ end
117
117
 
118
118
  class Comment
119
119
  attr_reader :article
120
-
120
+
121
121
  def initialize(article)
122
122
  @article = article
123
123
  end
124
-
124
+
125
125
  def text
126
126
  "comment #{object_id}"
127
127
  end
128
-
128
+
129
129
  def to_jail
130
130
  Comment::Jail.new self
131
131
  end
@@ -145,7 +145,7 @@ end
145
145
 
146
146
  class Article::Jail < Safemode::Jail
147
147
  allow :title, :comments, :is_article?, :comment_class
148
-
148
+
149
149
  def author_name
150
150
  "this article's author name"
151
151
  end
@@ -24,8 +24,7 @@ class TestJail < Test::Unit::TestCase
24
24
  end
25
25
 
26
26
  def test_jail_instances_should_have_limited_methods
27
- expected = ["class", "method_missing", "methods", "respond_to?", "respond_to_missing?", "to_jail", "to_s", "instance_variable_get"]
28
- expected.delete('respond_to_missing?') if RUBY_VERSION > '1.9.3' # respond_to_missing? is private in rubies above 1.9.3
27
+ expected = ["class", "method_missing", "methods", "respond_to?", "to_jail", "to_s", "instance_variable_get"]
29
28
  objects.each do |object|
30
29
  assert_equal expected.sort, reject_pretty_methods(object.to_jail.methods.map(&:to_s).sort)
31
30
  end
@@ -37,8 +36,12 @@ class TestJail < Test::Unit::TestCase
37
36
  "allow_instance_method", "allow_class_method", "allowed_instance_method?",
38
37
  "allowed_class_method?", "allowed_instance_methods", "allowed_class_methods",
39
38
  "<", # < needed in Rails Object#subclasses_of
40
- "ancestors", "==" # ancestors and == needed in Rails::Generator::Spec#lookup_class
41
- ]
39
+ "ancestors", "=="] # ancestors and == needed in Rails::Generator::Spec#lookup_class
40
+
41
+ if defined?(JRUBY_VERSION)
42
+ (expected << ['method_missing', 'singleton_method_undefined', 'singleton_method_added']).flatten! # needed for running under jruby
43
+ end
44
+
42
45
  objects.each do |object|
43
46
  assert_equal expected.sort, reject_pretty_methods(object.to_jail.class.methods.map(&:to_s).sort)
44
47
  end
@@ -2,7 +2,7 @@ require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
3
  class TestSafemodeEval < Test::Unit::TestCase
4
4
  include TestHelper
5
-
5
+
6
6
  def setup
7
7
  @box = Safemode::Box.new
8
8
  @locals = { :article => Article.new }
@@ -18,14 +18,10 @@ class TestSafemodeEval < Test::Unit::TestCase
18
18
  end
19
19
 
20
20
  def test_unary_operators_on_instances_of_boolean_vars
21
- if RUBY_VERSION != "1.8.7"
22
- assert @box.eval('not false')
23
- assert @box.eval('!false')
24
- assert !@box.eval('not true')
25
- assert !@box.eval('!true')
26
- else
27
- p "no unary ops under 1.8.7!"
28
- end
21
+ assert @box.eval('not false')
22
+ assert @box.eval('!false')
23
+ assert !@box.eval('not true')
24
+ assert !@box.eval('!true')
29
25
  end
30
26
 
31
27
  def test_false_class_ops
@@ -55,35 +51,35 @@ class TestSafemodeEval < Test::Unit::TestCase
55
51
  def test_should_turn_assigns_to_jails
56
52
  assert_raise_no_method "@article.system", @assigns
57
53
  end
58
-
54
+
59
55
  def test_should_turn_locals_to_jails
60
56
  assert_raise(Safemode::NoMethodError){ @box.eval "article.system", {}, @locals }
61
57
  end
62
-
58
+
63
59
  def test_should_allow_method_access_on_assigns
64
60
  assert_nothing_raised{ @box.eval "@article.title", @assigns }
65
61
  end
66
-
62
+
67
63
  def test_should_allow_method_access_on_locals
68
64
  assert_nothing_raised{ @box.eval("article.title", {}, @locals) }
69
65
  end
70
-
66
+
71
67
  def test_should_not_raise_on_if_using_return_values
72
68
  assert_nothing_raised{ @box.eval "if @article.is_article? then 1 end", @assigns }
73
69
  end
74
-
70
+
75
71
  def test_should_work_with_if_using_return_values
76
72
  assert_equal @box.eval("if @article.is_article? then 1 end", @assigns), 1
77
73
  end
78
-
74
+
79
75
  def test__FILE__should_not_render_filename
80
76
  assert_equal '(string)', @box.eval("__FILE__")
81
77
  end
82
-
78
+
83
79
  def test_interpolated_xstr_should_raise_security
84
80
  assert_raise_security '"#{`ls -a`}"'
85
- end
86
-
81
+ end
82
+
87
83
  TestHelper.no_method_error_raising_calls.each do |call|
88
84
  call.gsub!('"', '\\\\"')
89
85
  class_eval %Q(
@@ -100,6 +96,6 @@ class TestSafemodeEval < Test::Unit::TestCase
100
96
  assert_raise_security "#{call}", @assigns, @locals
101
97
  end
102
98
  )
103
- end
99
+ end
104
100
 
105
101
  end
@@ -31,6 +31,12 @@ class TestSafemodeParser < Test::Unit::TestCase
31
31
  end
32
32
  end
33
33
 
34
+ def test_block_pass_is_disabled
35
+ assert_raise Safemode::SecurityError do
36
+ jail('[].each(&:delete)')
37
+ end
38
+ end
39
+
34
40
  private
35
41
 
36
42
  def assert_jailed(expected, code)
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: safemode
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.3.1
4
+ version: 1.3.6
5
5
  platform: ruby
6
6
  authors:
7
7
  - Sven Fuchs
@@ -13,92 +13,50 @@ authors:
13
13
  autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
- date: 2017-02-13 00:00:00.000000000 Z
16
+ date: 2020-08-31 00:00:00.000000000 Z
17
17
  dependencies:
18
- - !ruby/object:Gem::Dependency
19
- name: sexp_processor
20
- requirement: !ruby/object:Gem::Requirement
21
- requirements:
22
- - - ">="
23
- - !ruby/object:Gem::Version
24
- version: 4.3.0
25
- type: :runtime
26
- prerelease: false
27
- version_requirements: !ruby/object:Gem::Requirement
28
- requirements:
29
- - - ">="
30
- - !ruby/object:Gem::Version
31
- version: 4.3.0
32
18
  - !ruby/object:Gem::Dependency
33
19
  name: ruby2ruby
34
20
  requirement: !ruby/object:Gem::Requirement
35
21
  requirements:
36
22
  - - ">="
37
23
  - !ruby/object:Gem::Version
38
- version: 2.0.6
24
+ version: 2.4.0
39
25
  type: :runtime
40
26
  prerelease: false
41
27
  version_requirements: !ruby/object:Gem::Requirement
42
28
  requirements:
43
29
  - - ">="
44
30
  - !ruby/object:Gem::Version
45
- version: 2.0.6
31
+ version: 2.4.0
46
32
  - !ruby/object:Gem::Dependency
47
33
  name: ruby_parser
48
34
  requirement: !ruby/object:Gem::Requirement
49
35
  requirements:
50
36
  - - ">="
51
37
  - !ruby/object:Gem::Version
52
- version: 3.2.0
38
+ version: 3.10.1
53
39
  type: :runtime
54
40
  prerelease: false
55
41
  version_requirements: !ruby/object:Gem::Requirement
56
42
  requirements:
57
43
  - - ">="
58
44
  - !ruby/object:Gem::Version
59
- version: 3.2.0
45
+ version: 3.10.1
60
46
  - !ruby/object:Gem::Dependency
61
- name: shoulda
47
+ name: sexp_processor
62
48
  requirement: !ruby/object:Gem::Requirement
63
49
  requirements:
64
50
  - - ">="
65
51
  - !ruby/object:Gem::Version
66
- version: '0'
67
- type: :development
52
+ version: 4.10.0
53
+ type: :runtime
68
54
  prerelease: false
69
55
  version_requirements: !ruby/object:Gem::Requirement
70
56
  requirements:
71
57
  - - ">="
72
58
  - !ruby/object:Gem::Version
73
- version: '0'
74
- - !ruby/object:Gem::Dependency
75
- name: rdoc
76
- requirement: !ruby/object:Gem::Requirement
77
- requirements:
78
- - - "~>"
79
- - !ruby/object:Gem::Version
80
- version: '3.12'
81
- type: :development
82
- prerelease: false
83
- version_requirements: !ruby/object:Gem::Requirement
84
- requirements:
85
- - - "~>"
86
- - !ruby/object:Gem::Version
87
- version: '3.12'
88
- - !ruby/object:Gem::Dependency
89
- name: bundler
90
- requirement: !ruby/object:Gem::Requirement
91
- requirements:
92
- - - "~>"
93
- - !ruby/object:Gem::Version
94
- version: '1.0'
95
- type: :development
96
- prerelease: false
97
- version_requirements: !ruby/object:Gem::Requirement
98
- requirements:
99
- - - "~>"
100
- - !ruby/object:Gem::Version
101
- version: '1.0'
59
+ version: 4.10.0
102
60
  - !ruby/object:Gem::Dependency
103
61
  name: jeweler
104
62
  requirement: !ruby/object:Gem::Requirement
@@ -114,7 +72,7 @@ dependencies:
114
72
  - !ruby/object:Gem::Version
115
73
  version: '0'
116
74
  - !ruby/object:Gem::Dependency
117
- name: rcov
75
+ name: rake
118
76
  requirement: !ruby/object:Gem::Requirement
119
77
  requirements:
120
78
  - - ">="
@@ -128,21 +86,21 @@ dependencies:
128
86
  - !ruby/object:Gem::Version
129
87
  version: '0'
130
88
  - !ruby/object:Gem::Dependency
131
- name: simplecov
89
+ name: rdoc
132
90
  requirement: !ruby/object:Gem::Requirement
133
91
  requirements:
134
- - - ">="
92
+ - - "~>"
135
93
  - !ruby/object:Gem::Version
136
- version: '0'
94
+ version: '3.12'
137
95
  type: :development
138
96
  prerelease: false
139
97
  version_requirements: !ruby/object:Gem::Requirement
140
98
  requirements:
141
- - - ">="
99
+ - - "~>"
142
100
  - !ruby/object:Gem::Version
143
- version: '0'
101
+ version: '3.12'
144
102
  - !ruby/object:Gem::Dependency
145
- name: test-unit
103
+ name: simplecov
146
104
  requirement: !ruby/object:Gem::Requirement
147
105
  requirements:
148
106
  - - ">="
@@ -156,7 +114,7 @@ dependencies:
156
114
  - !ruby/object:Gem::Version
157
115
  version: '0'
158
116
  - !ruby/object:Gem::Dependency
159
- name: rake
117
+ name: test-unit
160
118
  requirement: !ruby/object:Gem::Requirement
161
119
  requirements:
162
120
  - - ">="
@@ -177,6 +135,7 @@ extensions: []
177
135
  extra_rdoc_files:
178
136
  - README.markdown
179
137
  files:
138
+ - ".travis.yml"
180
139
  - Gemfile
181
140
  - LICENCSE
182
141
  - README.markdown
@@ -224,7 +183,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
224
183
  version: '0'
225
184
  requirements: []
226
185
  rubyforge_project:
227
- rubygems_version: 2.6.10
186
+ rubygems_version: 2.7.6
228
187
  signing_key:
229
188
  specification_version: 4
230
189
  summary: A library for safe evaluation of Ruby code based on ParseTree/RubyParser