bogo 0.2.14 → 0.2.16
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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +8 -0
- data/CONTRIBUTING.md +10 -14
- data/LICENSE +2 -2
- data/bogo.gemspec +1 -2
- data/lib/bogo/animal_strings.rb +0 -4
- data/lib/bogo/constants.rb +0 -6
- data/lib/bogo/ephemeral_file.rb +0 -3
- data/lib/bogo/http_proxy.rb +0 -2
- data/lib/bogo/lazy.rb +61 -47
- data/lib/bogo/logger.rb +5 -12
- data/lib/bogo/memoization.rb +1 -7
- data/lib/bogo/priority_queue.rb +8 -9
- data/lib/bogo/retry.rb +4 -14
- data/lib/bogo/smash.rb +5 -11
- data/lib/bogo/stack.rb +725 -0
- data/lib/bogo/utility.rb +0 -2
- data/lib/bogo/version.rb +1 -1
- data/lib/bogo.rb +1 -0
- metadata +8 -22
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: '005490ecb547fbeb1d4b941787e8a963c3c17ac8403527deb3ed6b33614312da'
|
4
|
+
data.tar.gz: f6c08b295196223458fa8649fd2224d8f46cd0e641545bed5c4173bdccda8c88
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a501ec13801d316df3d9fccec43bb86dbb6b3cb4847fc6645b266aeff41bebd51107090b733287650badbe038cfeb37cb59a6254fa366b74a65a3c4dce4b38e9
|
7
|
+
data.tar.gz: 25ff9327f54f0b8f3d4602e9834d87548a959f14a767fa9243d75037fe542efbc83eae002ca6dd9e2e461b2dda8c474d84bbcb4f0b1699aebfe551b5f86ae251
|
data/CHANGELOG.md
CHANGED
data/CONTRIBUTING.md
CHANGED
@@ -1,22 +1,18 @@
|
|
1
1
|
# Contributing
|
2
2
|
|
3
|
-
##
|
3
|
+
## Fixes
|
4
4
|
|
5
|
-
|
5
|
+
Have a fix to some bug you want to submit? Well you're
|
6
|
+
awesome. Please just include a description of the bug
|
7
|
+
(or link to originating issue) and test coverage on the
|
8
|
+
modifications.
|
6
9
|
|
7
|
-
|
10
|
+
## New Features
|
8
11
|
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
## Pull requests
|
14
|
-
|
15
|
-
* https://github.com/spox/bogo/pulls
|
16
|
-
|
17
|
-
Please base all pull requests of the `develop` branch. Merges to
|
18
|
-
`master` only occur through the `develop` branch. Pull requests
|
19
|
-
based on `master` will likely be cherry picked.
|
12
|
+
Have a new feature you want to add? Well you're awesome
|
13
|
+
too! It may be a good idea to submit an issue first to
|
14
|
+
describe the desired feature and get any feedback. Please
|
15
|
+
be sure to include tests.
|
20
16
|
|
21
17
|
## Issues
|
22
18
|
|
data/LICENSE
CHANGED
@@ -1,4 +1,4 @@
|
|
1
|
-
Copyright
|
1
|
+
Copyright 2022 Chris Roberts
|
2
2
|
|
3
3
|
Licensed under the Apache License, Version 2.0 (the "License");
|
4
4
|
you may not use this file except in compliance with the License.
|
@@ -10,4 +10,4 @@
|
|
10
10
|
distributed under the License is distributed on an "AS IS" BASIS,
|
11
11
|
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
12
12
|
See the License for the specific language governing permissions and
|
13
|
-
limitations under the License.
|
13
|
+
limitations under the License.
|
data/bogo.gemspec
CHANGED
@@ -12,9 +12,8 @@ Gem::Specification.new do |s|
|
|
12
12
|
s.license = "Apache 2.0"
|
13
13
|
s.add_runtime_dependency "hashie"
|
14
14
|
s.add_runtime_dependency "multi_json"
|
15
|
-
s.add_runtime_dependency "concurrent-ruby", "~> 1.1.3"
|
16
15
|
s.add_development_dependency "pry"
|
17
16
|
s.add_development_dependency "minitest"
|
18
|
-
s.add_development_dependency "rake"
|
17
|
+
s.add_development_dependency "rake"
|
19
18
|
s.files = Dir["lib/**/*"] + %w(bogo.gemspec README.md CHANGELOG.md CONTRIBUTING.md LICENSE)
|
20
19
|
end
|
data/lib/bogo/animal_strings.rb
CHANGED
data/lib/bogo/constants.rb
CHANGED
@@ -1,10 +1,6 @@
|
|
1
|
-
require 'bogo'
|
2
|
-
|
3
1
|
module Bogo
|
4
|
-
|
5
2
|
# Constant helper
|
6
3
|
module Constants
|
7
|
-
|
8
4
|
# Convert string to constant
|
9
5
|
#
|
10
6
|
# @param string [String] full constant name
|
@@ -40,7 +36,5 @@ module Bogo
|
|
40
36
|
constantize(klass.join('::'))
|
41
37
|
end
|
42
38
|
end
|
43
|
-
|
44
39
|
end
|
45
|
-
|
46
40
|
end
|
data/lib/bogo/ephemeral_file.rb
CHANGED
data/lib/bogo/http_proxy.rb
CHANGED
@@ -7,7 +7,6 @@ require 'http/request'
|
|
7
7
|
# library to allow easy sharing. It is the responsibility of the user
|
8
8
|
# to ensure the http gem is available!
|
9
9
|
class HTTP::Request
|
10
|
-
|
11
10
|
# Override to implicitly apply proxy as required
|
12
11
|
#
|
13
12
|
# NOTE: If dealing with https request, force port so CONNECT request
|
@@ -54,5 +53,4 @@ class HTTP::Request
|
|
54
53
|
end
|
55
54
|
"CONNECT #{@uri.host}:#{dest_port} HTTP/#{version}"
|
56
55
|
end
|
57
|
-
|
58
56
|
end
|
data/lib/bogo/lazy.rb
CHANGED
@@ -1,21 +1,32 @@
|
|
1
|
-
require 'bogo'
|
2
1
|
require 'multi_json'
|
2
|
+
require 'monitor'
|
3
3
|
require 'digest/sha2'
|
4
4
|
|
5
5
|
module Bogo
|
6
6
|
# Adds functionality to facilitate laziness
|
7
7
|
module Lazy
|
8
|
-
|
9
8
|
# Instance methods for laziness
|
10
9
|
module InstanceMethods
|
11
10
|
|
11
|
+
def self.included(klass)
|
12
|
+
klass.include(MonitorMixin)
|
13
|
+
klass.instance_variable_set(:@calling_on_missing, false)
|
14
|
+
end
|
15
|
+
|
16
|
+
# @return [Monitor] Monitor instance for synchronization
|
17
|
+
def _mon
|
18
|
+
@mon ||= Monitor.new
|
19
|
+
end
|
20
|
+
|
12
21
|
# @return [Smash] argument hash
|
13
22
|
def data
|
14
|
-
|
15
|
-
@data
|
16
|
-
|
17
|
-
|
18
|
-
|
23
|
+
_mon.synchronize do
|
24
|
+
unless(@data)
|
25
|
+
@data = Smash.new
|
26
|
+
self.class.attributes.each do |key, value|
|
27
|
+
if(value.has_key?('default'))
|
28
|
+
@data[key] = value['default']
|
29
|
+
end
|
19
30
|
end
|
20
31
|
end
|
21
32
|
end
|
@@ -24,15 +35,17 @@ module Bogo
|
|
24
35
|
|
25
36
|
# @return [Smash] updated data
|
26
37
|
def dirty
|
27
|
-
|
28
|
-
@dirty
|
38
|
+
_mon.synchronize do
|
39
|
+
unless(@dirty)
|
40
|
+
@dirty = Smash.new
|
41
|
+
end
|
29
42
|
end
|
30
43
|
@dirty
|
31
44
|
end
|
32
45
|
|
33
46
|
# @return [Smash] current data state
|
34
47
|
def attributes
|
35
|
-
data.merge(dirty)
|
48
|
+
_mon.synchronize { data.merge(dirty) }
|
36
49
|
end
|
37
50
|
|
38
51
|
# Create new instance
|
@@ -40,20 +53,22 @@ module Bogo
|
|
40
53
|
# @param args [Hash]
|
41
54
|
# @return [self]
|
42
55
|
def load_data(args={})
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
if(options[:default])
|
52
|
-
|
56
|
+
_mon.synchronize do
|
57
|
+
args = args.to_smash
|
58
|
+
@data = Smash.new
|
59
|
+
self.class.attributes.each do |name, options|
|
60
|
+
val = args[name]
|
61
|
+
if(options[:required] && !args.has_key?(name) && !options.has_key?(:default))
|
62
|
+
raise ArgumentError.new("Missing required option: `#{name}`")
|
63
|
+
end
|
64
|
+
if(val.nil? && !args.has_key?(name) && options[:default])
|
65
|
+
if(options[:default])
|
66
|
+
val = options[:default].respond_to?(:call) ? options[:default].call : options[:default]
|
67
|
+
end
|
68
|
+
end
|
69
|
+
if(args.has_key?(name) || val)
|
70
|
+
self.send("#{name}=", val)
|
53
71
|
end
|
54
|
-
end
|
55
|
-
if(args.has_key?(name) || val)
|
56
|
-
self.send("#{name}=", val)
|
57
72
|
end
|
58
73
|
end
|
59
74
|
self
|
@@ -65,9 +80,11 @@ module Bogo
|
|
65
80
|
#
|
66
81
|
# @return [self]
|
67
82
|
def valid_state
|
68
|
-
|
69
|
-
|
70
|
-
|
83
|
+
_mon.synchronize do
|
84
|
+
data.merge!(dirty)
|
85
|
+
dirty.clear
|
86
|
+
@_checksum = Digest::SHA256.hexdigest(MultiJson.dump(data.inspect).to_s)
|
87
|
+
end
|
71
88
|
self
|
72
89
|
end
|
73
90
|
|
@@ -76,14 +93,16 @@ module Bogo
|
|
76
93
|
# @param attr [String, Symbol] name of attribute
|
77
94
|
# @return [TrueClass, FalseClass] model or attribute is dirty
|
78
95
|
def dirty?(attr=nil)
|
79
|
-
|
80
|
-
|
81
|
-
|
82
|
-
if(@_checksum)
|
83
|
-
!dirty.empty? ||
|
84
|
-
@_checksum != Digest::SHA256.hexdigest(MultiJson.dump(data.inspect).to_s)
|
96
|
+
_mon.synchronize do
|
97
|
+
if(attr)
|
98
|
+
dirty.has_key?(attr)
|
85
99
|
else
|
86
|
-
|
100
|
+
if(@_checksum)
|
101
|
+
!dirty.empty? ||
|
102
|
+
@_checksum != Digest::SHA256.hexdigest(MultiJson.dump(data.inspect).to_s)
|
103
|
+
else
|
104
|
+
true
|
105
|
+
end
|
87
106
|
end
|
88
107
|
end
|
89
108
|
end
|
@@ -100,19 +119,20 @@ module Bogo
|
|
100
119
|
|
101
120
|
# @return [Hash]
|
102
121
|
def to_h
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
v.
|
107
|
-
|
108
|
-
|
109
|
-
|
122
|
+
_mon.synchronize do
|
123
|
+
Hash[
|
124
|
+
attributes.map{|k,v|
|
125
|
+
[k, v.is_a?(Array) ?
|
126
|
+
v.map{|x| x.respond_to?(:to_h) ? x.to_h : x} :
|
127
|
+
v.respond_to?(:to_h) ? v.to_h : v]
|
128
|
+
}
|
129
|
+
]
|
130
|
+
end
|
110
131
|
end
|
111
132
|
end
|
112
133
|
|
113
134
|
# Class methods for laziness
|
114
135
|
module ClassMethods
|
115
|
-
|
116
136
|
# Disable dirty state
|
117
137
|
def always_clean!
|
118
138
|
self.class_eval do
|
@@ -264,11 +284,9 @@ module Bogo
|
|
264
284
|
@attributes = attrs.to_smash
|
265
285
|
true
|
266
286
|
end
|
267
|
-
|
268
287
|
end
|
269
288
|
|
270
289
|
class << self
|
271
|
-
|
272
290
|
# Injects laziness into class
|
273
291
|
#
|
274
292
|
# @param klass [Class]
|
@@ -278,16 +296,12 @@ module Bogo
|
|
278
296
|
extend ClassMethods
|
279
297
|
|
280
298
|
class << self
|
281
|
-
|
282
299
|
def inherited(klass)
|
283
300
|
klass.set_attributes(self.attributes.to_smash)
|
284
301
|
end
|
285
|
-
|
286
302
|
end
|
287
303
|
end
|
288
304
|
end
|
289
|
-
|
290
305
|
end
|
291
|
-
|
292
306
|
end
|
293
307
|
end
|
data/lib/bogo/logger.rb
CHANGED
@@ -1,4 +1,3 @@
|
|
1
|
-
require "concurrent"
|
2
1
|
require "logger"
|
3
2
|
|
4
3
|
module Bogo
|
@@ -46,9 +45,9 @@ module Bogo
|
|
46
45
|
logger_args = [$stderr]
|
47
46
|
end
|
48
47
|
@base_args = logger_args
|
49
|
-
logger = ::Logger.new(*@base_args)
|
50
|
-
logger.level = :fatal
|
51
|
-
@
|
48
|
+
@logger = ::Logger.new(*@base_args)
|
49
|
+
@logger.level = :fatal
|
50
|
+
@lock = Mutex.new
|
52
51
|
end
|
53
52
|
|
54
53
|
# Create a new logger with the sub-name provided
|
@@ -56,7 +55,7 @@ module Bogo
|
|
56
55
|
# @param name [String] sub-name for logger
|
57
56
|
# @return [Logger]
|
58
57
|
def named(name)
|
59
|
-
new_name = self.progname.to_s
|
58
|
+
new_name = self.progname.to_s.dup
|
60
59
|
new_name << "." unless new_name.empty?
|
61
60
|
new_name << name
|
62
61
|
new_logger = Logger.new(*@base_args)
|
@@ -71,15 +70,9 @@ module Bogo
|
|
71
70
|
next if l_m.to_s.start_with?("_") || l_m.to_s == "object_id"
|
72
71
|
class_eval <<-EOC
|
73
72
|
def #{l_m}(*ma, &mb)
|
74
|
-
|
73
|
+
@lock.synchronize { @logger.send(:#{l_m}, *ma, &mb) }
|
75
74
|
end
|
76
75
|
EOC
|
77
76
|
end
|
78
|
-
|
79
|
-
protected
|
80
|
-
|
81
|
-
def wrapped_logger
|
82
|
-
@wrapped_logger
|
83
|
-
end
|
84
77
|
end
|
85
78
|
end
|
data/lib/bogo/memoization.rb
CHANGED
@@ -1,16 +1,12 @@
|
|
1
|
-
require 'bogo'
|
2
|
-
|
3
1
|
module Bogo
|
4
2
|
# Memoization helpers
|
5
3
|
module Memoization
|
6
|
-
|
7
4
|
# Lock for providing exclusive access
|
8
5
|
EXCLUSIVE_LOCK = Mutex.new
|
9
6
|
# Holder for global memoization items
|
10
7
|
GLOBAL_MEMOS = Smash.new
|
11
8
|
|
12
9
|
class << self
|
13
|
-
|
14
10
|
# Clean up isolated memoizations
|
15
11
|
#
|
16
12
|
# @param object_id [Object]
|
@@ -19,7 +15,7 @@ module Bogo
|
|
19
15
|
proc do
|
20
16
|
Thread.current[:bogo_memoization].delete_if do |k,v|
|
21
17
|
k.to_s.start_with?(object_id.to_s)
|
22
|
-
end
|
18
|
+
end if Thread.current[:bogo_memoization].is_a?(Hash)
|
23
19
|
end
|
24
20
|
end
|
25
21
|
|
@@ -38,7 +34,6 @@ module Bogo
|
|
38
34
|
GLOBAL_MEMOS.clear
|
39
35
|
end
|
40
36
|
end
|
41
|
-
|
42
37
|
end
|
43
38
|
|
44
39
|
# Memoize data
|
@@ -123,6 +118,5 @@ module Bogo
|
|
123
118
|
end
|
124
119
|
true
|
125
120
|
end
|
126
|
-
|
127
121
|
end
|
128
122
|
end
|
data/lib/bogo/priority_queue.rb
CHANGED
@@ -1,10 +1,7 @@
|
|
1
|
-
require 'bogo'
|
2
|
-
|
3
1
|
module Bogo
|
4
2
|
# Specialized priority based queue
|
5
3
|
# @note does not allow duplicate objects to be queued
|
6
4
|
class PriorityQueue
|
7
|
-
|
8
5
|
# Create a new priority queue
|
9
6
|
#
|
10
7
|
# @return [self]
|
@@ -24,10 +21,12 @@ module Bogo
|
|
24
21
|
def push(item, cost=nil, &block)
|
25
22
|
lock.synchronize do
|
26
23
|
if(queue[item])
|
27
|
-
raise ArgumentError
|
24
|
+
raise ArgumentError,
|
25
|
+
"Item already exists in queue. Items must be unique! (#{item})"
|
28
26
|
end
|
29
27
|
unless(cost || block_given?)
|
30
|
-
raise ArgumentError
|
28
|
+
raise ArgumentError,
|
29
|
+
'Cost must be provided as parameter or block!'
|
31
30
|
end
|
32
31
|
@block_costs += 1 if cost.nil?
|
33
32
|
queue[item] = cost || block
|
@@ -45,10 +44,12 @@ module Bogo
|
|
45
44
|
items.each do |item_pair|
|
46
45
|
item, cost = item_pair
|
47
46
|
if(queue[item])
|
48
|
-
raise ArgumentError
|
47
|
+
raise ArgumentError,
|
48
|
+
"Item already exists in queue. Items must be unique! (#{item})"
|
49
49
|
end
|
50
50
|
unless(cost.is_a?(Numeric) || cost.is_a?(Proc))
|
51
|
-
raise ArgumentError
|
51
|
+
raise ArgumentError,
|
52
|
+
"Cost must be provided as parameter or proc! (item: #{item})"
|
52
53
|
end
|
53
54
|
@block_costs += 1 if cost.is_a?(Proc)
|
54
55
|
queue[item] = cost
|
@@ -106,7 +107,5 @@ module Bogo
|
|
106
107
|
protected
|
107
108
|
|
108
109
|
attr_reader :queue, :lock
|
109
|
-
|
110
110
|
end
|
111
|
-
|
112
111
|
end
|
data/lib/bogo/retry.rb
CHANGED
@@ -1,10 +1,6 @@
|
|
1
|
-
require 'bogo'
|
2
|
-
|
3
1
|
module Bogo
|
4
|
-
|
5
2
|
# Perform action and retry until successful or abort
|
6
3
|
class Retry
|
7
|
-
|
8
4
|
# Create a type of retry
|
9
5
|
#
|
10
6
|
# @param type [String, Symbol] name of retry type
|
@@ -38,7 +34,8 @@ module Bogo
|
|
38
34
|
# @return [self]
|
39
35
|
def initialize(args={}, &block)
|
40
36
|
unless(block)
|
41
|
-
raise ArgumentError
|
37
|
+
raise ArgumentError,
|
38
|
+
'Expecting block but no block was provided!'
|
42
39
|
end
|
43
40
|
args = args.to_smash
|
44
41
|
@ui = args[:ui]
|
@@ -58,7 +55,8 @@ module Bogo
|
|
58
55
|
# @return [Object] result of action
|
59
56
|
def run!
|
60
57
|
if(dead)
|
61
|
-
raise RuntimeError
|
58
|
+
raise RuntimeError,
|
59
|
+
"Action has already reached maximum allowed attempts (#{max_attempts})!"
|
62
60
|
else
|
63
61
|
begin
|
64
62
|
log_attempt!
|
@@ -110,7 +108,6 @@ module Bogo
|
|
110
108
|
|
111
109
|
# Flat retry implementation
|
112
110
|
class Flat < Retry
|
113
|
-
|
114
111
|
# @return [Numeric]
|
115
112
|
attr_reader :wait_interval
|
116
113
|
|
@@ -133,12 +130,10 @@ module Bogo
|
|
133
130
|
def wait_on_failure(*_)
|
134
131
|
wait_interval
|
135
132
|
end
|
136
|
-
|
137
133
|
end
|
138
134
|
|
139
135
|
# Linear retry implementation
|
140
136
|
class Linear < Retry
|
141
|
-
|
142
137
|
# @return [Numeric]
|
143
138
|
attr_reader :wait_interval
|
144
139
|
|
@@ -161,12 +156,10 @@ module Bogo
|
|
161
156
|
def wait_on_failure(*_)
|
162
157
|
wait_interval * attempts
|
163
158
|
end
|
164
|
-
|
165
159
|
end
|
166
160
|
|
167
161
|
# Exponential retry implementation
|
168
162
|
class Exponential < Retry
|
169
|
-
|
170
163
|
# @return [Numeric]
|
171
164
|
attr_reader :wait_interval
|
172
165
|
# @return [Numeric]
|
@@ -196,9 +189,6 @@ module Bogo
|
|
196
189
|
def wait_on_failure(*_)
|
197
190
|
retries == 0 ? wait_interval : (wait_interval + retries) ** wait_exponent
|
198
191
|
end
|
199
|
-
|
200
192
|
end
|
201
|
-
|
202
193
|
end
|
203
|
-
|
204
194
|
end
|
data/lib/bogo/smash.rb
CHANGED
@@ -1,12 +1,9 @@
|
|
1
1
|
require 'hashie'
|
2
2
|
require 'digest/sha2'
|
3
|
-
require 'bogo'
|
4
3
|
|
5
4
|
module Bogo
|
6
|
-
|
7
5
|
# Customized Hash
|
8
6
|
class Smash < Hash
|
9
|
-
|
10
7
|
class NoValue; end
|
11
8
|
NO_VALUE = NoValue.new
|
12
9
|
|
@@ -25,7 +22,7 @@ module Bogo
|
|
25
22
|
if(args.first.is_a?(::Hash))
|
26
23
|
base = args.shift
|
27
24
|
end
|
28
|
-
super
|
25
|
+
super(*args)
|
29
26
|
if(base)
|
30
27
|
self.replace(base.to_smash)
|
31
28
|
end
|
@@ -89,7 +86,8 @@ module Bogo
|
|
89
86
|
elsif(args.size > 1)
|
90
87
|
default_value = args.pop
|
91
88
|
elsif(args.size < 1)
|
92
|
-
raise ArgumentError
|
89
|
+
raise ArgumentError,
|
90
|
+
"Default value must be provided for #fetch"
|
93
91
|
end
|
94
92
|
result = retrieve(*args)
|
95
93
|
if(result == NO_VALUE)
|
@@ -105,7 +103,8 @@ module Bogo
|
|
105
103
|
# @return [Object] value set
|
106
104
|
def set(*args)
|
107
105
|
unless(args.size > 1)
|
108
|
-
raise ArgumentError
|
106
|
+
raise ArgumentError,
|
107
|
+
'Set requires at least one key and a value'
|
109
108
|
end
|
110
109
|
value = args.pop
|
111
110
|
set_key = args.pop
|
@@ -132,13 +131,11 @@ module Bogo
|
|
132
131
|
def checksum
|
133
132
|
Digest::SHA256.hexdigest(self.to_smash(:sorted).to_s)
|
134
133
|
end
|
135
|
-
|
136
134
|
end
|
137
135
|
end
|
138
136
|
|
139
137
|
# Hook helper into toplevel `Hash`
|
140
138
|
class Hash
|
141
|
-
|
142
139
|
# Convert to Smash
|
143
140
|
#
|
144
141
|
# @return [Smash]
|
@@ -198,11 +195,9 @@ class Hash
|
|
198
195
|
args.include?(:freeze) ? obj.freeze : obj
|
199
196
|
end
|
200
197
|
end
|
201
|
-
|
202
198
|
end
|
203
199
|
|
204
200
|
class Array
|
205
|
-
|
206
201
|
# Iterates searching for Hash types to auto convert
|
207
202
|
#
|
208
203
|
# @return [Array]
|
@@ -215,7 +210,6 @@ class Array
|
|
215
210
|
end
|
216
211
|
end
|
217
212
|
end
|
218
|
-
|
219
213
|
end
|
220
214
|
|
221
215
|
unless(defined?(Smash))
|