gemsupport 0.4.2 → 0.5.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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: a02f898403ab14160bd443dae67fd77a35c37222
4
- data.tar.gz: da2b7654d900edfe427932bd24f1a3cdeb24d533
3
+ metadata.gz: 90afa88f1f6e7ee2ac0e521d7a08c4923d9d0016
4
+ data.tar.gz: 0a3a1402cbd4f216213ec063a5ed1cf2b92feb8a
5
5
  SHA512:
6
- metadata.gz: 86d3dc0d5b96a0722769f728b6f408b397181ce8c5ccaf91815da275c54205a886b4b8fea6aef6186a0b36d0d2d8b39c719972b34bb960f05e4e1aa3859cd28e
7
- data.tar.gz: 9eed7e7065000ff64d93542db531c91991e7d5a6276b9eea1eb91195710a6799155004029737e06214a33ecaa5f66a33a45dacfac5980a2daa9ab60ce51afa95
6
+ metadata.gz: deeeb97ea7962a9731e31ad1163e35ec6641e297bb5cac24561156530bde39fb1996a108b925bd984a4f5dfa56d63cc5b00c2f62e9f14fb7d923ac68ed016111
7
+ data.tar.gz: a2c216617a38baa90af04884aa67e7f990837ee2eeb2582980e4b52eed6de4e85f82032a281f2fa8918a73146b81f1b2190f4c85304aacaeddbe45c20d2abad4
data/.travis.yml CHANGED
@@ -2,4 +2,5 @@ nguage: ruby
2
2
  rvm:
3
3
  - 2.0.0
4
4
  - 2.1.3
5
+ - 2.2.3
5
6
  script: bundle exec rake
data/README.md CHANGED
@@ -1,7 +1,8 @@
1
1
  # Gemsupport
2
2
  [![Build Status](https://travis-ci.org/mdouchement/gemsupport.svg?branch=master)](https://travis-ci.org/mdouchement/gemsupport)
3
3
 
4
- TODO: Write a gem description
4
+ # Requirments
5
+ - Ruby >= 2.0 (Refinements needed)
5
6
 
6
7
  ## Installation
7
8
 
@@ -21,7 +22,24 @@ Or install it yourself as:
21
22
 
22
23
  ## Usage
23
24
 
24
- TODO: Write usage instructions here
25
+ - Included modules
26
+ ```rb
27
+ module MyModule # or class
28
+ include Gemsupport::Console # capture stdout/stderr
29
+ include Gemsupport::Error # suppress error & silent exit
30
+ end
31
+ ```
32
+
33
+ - Refinements
34
+ ```rb
35
+ module MyModule # or class
36
+ using Gemsupport::Blank # methods #blank? & #present?
37
+ using Gemsupport::HashKeys # Symbolization & stringification of Hash keys
38
+ using Gemsupport::DeepMerge # Deep merge a Hash
39
+ using Gemsupport::DeepClone # Deep clone an object
40
+ using Gemsupport::StringInterations # methods #underscore, #camelize, #unindent & #unindent!
41
+ end
42
+ ```
25
43
 
26
44
  ## Contributing
27
45
 
data/gemsupport.gemspec CHANGED
@@ -18,6 +18,8 @@ Gem::Specification.new do |spec|
18
18
  spec.test_files = spec.files.grep(%(r^(test|spec|features)/}))
19
19
  spec.require_paths = ['lib']
20
20
 
21
+ spec.required_ruby_version = '>= 2.0'
22
+
21
23
  spec.add_development_dependency 'bundler'
22
24
  spec.add_development_dependency 'rake', '~> 10.0'
23
25
  spec.add_development_dependency 'rspec', '~> 3.1.0'
data/lib/gemsupport.rb CHANGED
@@ -1,7 +1,7 @@
1
1
  require 'gemsupport/version'
2
- require 'gemsupport/core_ext'
3
- require 'gemsupport/console'
4
- require 'gemsupport/error'
2
+ require 'gemsupport/refinements'
5
3
 
6
4
  module Gemsupport
5
+ autoload :Console, 'gemsupport/console'
6
+ autoload :Error, 'gemsupport/error'
7
7
  end
@@ -0,0 +1,7 @@
1
+ module Gemsupport
2
+ autoload :Blank, 'gemsupport/refinements/blank'
3
+ autoload :HashKeys, 'gemsupport/refinements/hash_keys'
4
+ autoload :DeepMerge, 'gemsupport/refinements/deep_merge'
5
+ autoload :DeepClone, 'gemsupport/refinements/deep_clone'
6
+ autoload :StringInteractions, 'gemsupport/refinements/string_interactions'
7
+ end
@@ -0,0 +1,134 @@
1
+ # https://raw.githubusercontent.com/rails/rails/4-1-stable/activesupport/lib/active_support/core_ext/object/blank.rb
2
+ module Gemsupport
3
+ module Blank
4
+ refine Object do
5
+ # An object is blank if it's false, empty, or a whitespace string.
6
+ # For example, '', ' ', +nil+, [], and {} are all blank.
7
+ #
8
+ # This simplifies
9
+ #
10
+ # address.nil? || address.empty?
11
+ #
12
+ # to
13
+ #
14
+ # address.blank?
15
+ #
16
+ # @return [true, false]
17
+ def blank?
18
+ respond_to?(:empty?) ? !!empty? : !self
19
+ end
20
+
21
+ # An object is present if it's not blank.
22
+ #
23
+ # @return [true, false]
24
+ def present?
25
+ !blank?
26
+ end
27
+
28
+ # Returns the receiver if it's present otherwise returns +nil+.
29
+ # <tt>object.presence</tt> is equivalent to
30
+ #
31
+ # object.present? ? object : nil
32
+ #
33
+ # For example, something like
34
+ #
35
+ # state = params[:state] if params[:state].present?
36
+ # country = params[:country] if params[:country].present?
37
+ # region = state || country || 'US'
38
+ #
39
+ # becomes
40
+ #
41
+ # region = params[:state].presence || params[:country].presence || 'US'
42
+ #
43
+ # @return [Object]
44
+ def presence
45
+ self if present?
46
+ end
47
+ end
48
+
49
+ refine NilClass do
50
+ # +nil+ is blank:
51
+ #
52
+ # nil.blank? # => true
53
+ #
54
+ # @return [true]
55
+ def blank?
56
+ true
57
+ end
58
+ end
59
+
60
+ refine FalseClass do
61
+ # +false+ is blank:
62
+ #
63
+ # false.blank? # => true
64
+ #
65
+ # @return [true]
66
+ def blank?
67
+ true
68
+ end
69
+ end
70
+
71
+ refine TrueClass do
72
+ # +true+ is not blank:
73
+ #
74
+ # true.blank? # => false
75
+ #
76
+ # @return [false]
77
+ def blank?
78
+ false
79
+ end
80
+ end
81
+
82
+ refine Array do
83
+ # An array is blank if it's empty:
84
+ #
85
+ # [].blank? # => true
86
+ # [1,2,3].blank? # => false
87
+ #
88
+ # @return [true, false]
89
+ alias_method :blank?, :empty?
90
+ end
91
+
92
+ refine Hash do
93
+ # A hash is blank if it's empty:
94
+ #
95
+ # {}.blank? # => true
96
+ # { key: 'value' }.blank? # => false
97
+ #
98
+ # @return [true, false]
99
+ alias_method :blank?, :empty?
100
+ end
101
+
102
+ refine String do
103
+ BLANK_RE = /\A[[:space:]]*\z/
104
+
105
+ # A string is blank if it's empty or contains whitespaces only:
106
+ #
107
+ # ''.blank? # => true
108
+ # ' '.blank? # => true
109
+ # "\t\n\r".blank? # => true
110
+ # ' blah '.blank? # => false
111
+ #
112
+ # Unicode whitespace is supported:
113
+ #
114
+ # "\u00a0".blank? # => true
115
+ #
116
+ # @return [true, false]
117
+ def blank?
118
+ BLANK_RE === self
119
+ end
120
+ end
121
+
122
+ refine Numeric do #:nodoc:
123
+ # No number is blank:
124
+ #
125
+ # 1.blank? # => false
126
+ # 0.blank? # => false
127
+ #
128
+ # @return [false]
129
+ def blank?
130
+ false
131
+ end
132
+ end
133
+ end
134
+ end
@@ -0,0 +1,31 @@
1
+ module Gemsupport
2
+ module DeepClone
3
+ refine Object do
4
+ def deep_clone(is_root: true)
5
+ clone.tap do |deep_cloning_obj|
6
+ deep_cloning_obj.instance_variables.each do |var|
7
+ val = deep_cloning_obj.instance_variable_get(var)
8
+ deep_cloning_obj.instance_variable_set(var, val.deep_clone(is_root: false))
9
+ end
10
+ end
11
+ rescue TypeError
12
+ return self unless is_root
13
+ raise
14
+ end
15
+ end
16
+
17
+ refine Hash do
18
+ def deep_clone(is_root: true)
19
+ each_with_object({}) do |(k, v), hsh|
20
+ hsh[k.deep_clone(is_root: false)] = v.deep_clone(is_root: false)
21
+ end
22
+ end
23
+ end
24
+
25
+ refine Array do
26
+ def deep_clone(is_root: true)
27
+ map { |e| e.deep_clone(is_root: false) }
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,19 @@
1
+ module Gemsupport
2
+ module DeepMerge
3
+ refine Hash do
4
+ def deep_merge(hsh)
5
+ merger = proc do |key, v1, v2|
6
+ v1.kind_of?(Hash) && v2.kind_of?(Hash) ? v1.merge(v2, &merger) : v2
7
+ end
8
+ self.merge(hsh, &merger)
9
+ end
10
+
11
+ def deep_merge!(hsh)
12
+ merger = proc do |key, v1, v2|
13
+ v1.kind_of?(Hash) && v2.kind_of?(Hash) ? v1.merge(v2, &merger) : v2
14
+ end
15
+ self.merge!(hsh, &merger)
16
+ end
17
+ end
18
+ end
19
+ end
@@ -0,0 +1,168 @@
1
+ # Extract from https://github.com/rails/rails/blob/4-1-stable/activesupport/lib/active_support/core_ext/hash/keys.rb
2
+ module Gemsupport
3
+ module HashKeys
4
+ refine Hash do
5
+ # Returns a new hash with all keys converted using the block operation.
6
+ #
7
+ # hash = { name: 'Rob', age: '28' }
8
+ #
9
+ # hash.transform_keys{ |key| key.to_s.upcase }
10
+ # # => {"NAME"=>"Rob", "AGE"=>"28"}
11
+ def transform_keys
12
+ result = {}
13
+ each_key do |key|
14
+ result[yield(key)] = self[key]
15
+ end
16
+ result
17
+ end
18
+
19
+ # Destructively convert all keys using the block operations.
20
+ # Same as transform_keys but modifies +self+.
21
+ def transform_keys!
22
+ keys.each do |key|
23
+ self[yield(key)] = delete(key)
24
+ end
25
+ self
26
+ end
27
+
28
+ # Returns a new hash with all keys converted to strings.
29
+ #
30
+ # hash = { name: 'Rob', age: '28' }
31
+ #
32
+ # hash.stringify_keys
33
+ # # => { "name" => "Rob", "age" => "28" }
34
+ def stringify_keys
35
+ transform_keys{ |key| key.to_s }
36
+ end
37
+
38
+ # Destructively convert all keys to strings. Same as
39
+ # +stringify_keys+, but modifies +self+.
40
+ def stringify_keys!
41
+ transform_keys!{ |key| key.to_s }
42
+ end
43
+
44
+ # Returns a new hash with all keys converted to symbols, as long as
45
+ # they respond to +to_sym+.
46
+ #
47
+ # hash = { 'name' => 'Rob', 'age' => '28' }
48
+ #
49
+ # hash.symbolize_keys
50
+ # # => { name: "Rob", age: "28" }
51
+ def symbolize_keys
52
+ transform_keys{ |key| key.to_sym rescue key }
53
+ end
54
+ alias_method :to_options, :symbolize_keys
55
+
56
+ # Destructively convert all keys to symbols, as long as they respond
57
+ # to +to_sym+. Same as +symbolize_keys+, but modifies +self+.
58
+ def symbolize_keys!
59
+ transform_keys!{ |key| key.to_sym rescue key }
60
+ end
61
+ alias_method :to_options!, :symbolize_keys!
62
+
63
+ # Validate all keys in a hash match <tt>*valid_keys</tt>, raising ArgumentError
64
+ # on a mismatch. Note that keys are NOT treated indifferently, meaning if you
65
+ # use strings for keys but assert symbols as keys, this will fail.
66
+ #
67
+ # { name: 'Rob', years: '28' }.assert_valid_keys(:name, :age) # => raises "ArgumentError: Unknown key: :years. Valid keys are: :name, :age"
68
+ # { name: 'Rob', age: '28' }.assert_valid_keys('name', 'age') # => raises "ArgumentError: Unknown key: :name. Valid keys are: 'name', 'age'"
69
+ # { name: 'Rob', age: '28' }.assert_valid_keys(:name, :age) # => passes, raises nothing
70
+ def assert_valid_keys(*valid_keys)
71
+ valid_keys.flatten!
72
+ each_key do |k|
73
+ unless valid_keys.include?(k)
74
+ raise ArgumentError.new("Unknown key: #{k.inspect}. Valid keys are: #{valid_keys.map(&:inspect).join(', ')}")
75
+ end
76
+ end
77
+ end
78
+
79
+ # Returns a new hash with all keys converted by the block operation.
80
+ # This includes the keys from the root hash and from all
81
+ # nested hashes and arrays.
82
+ #
83
+ # hash = { person: { name: 'Rob', age: '28' } }
84
+ #
85
+ # hash.deep_transform_keys{ |key| key.to_s.upcase }
86
+ # # => {"PERSON"=>{"NAME"=>"Rob", "AGE"=>"28"}}
87
+ def deep_transform_keys(&block)
88
+ _deep_transform_keys_in_object(self, &block)
89
+ end
90
+
91
+ # Destructively convert all keys by using the block operation.
92
+ # This includes the keys from the root hash and from all
93
+ # nested hashes and arrays.
94
+ def deep_transform_keys!(&block)
95
+ _deep_transform_keys_in_object!(self, &block)
96
+ end
97
+
98
+ # Returns a new hash with all keys converted to strings.
99
+ # This includes the keys from the root hash and from all
100
+ # nested hashes and arrays.
101
+ #
102
+ # hash = { person: { name: 'Rob', age: '28' } }
103
+ #
104
+ # hash.deep_stringify_keys
105
+ # # => {"person"=>{"name"=>"Rob", "age"=>"28"}}
106
+ def deep_stringify_keys
107
+ deep_transform_keys{ |key| key.to_s }
108
+ end
109
+
110
+ # Destructively convert all keys to strings.
111
+ # This includes the keys from the root hash and from all
112
+ # nested hashes and arrays.
113
+ def deep_stringify_keys!
114
+ deep_transform_keys!{ |key| key.to_s }
115
+ end
116
+
117
+ # Returns a new hash with all keys converted to symbols, as long as
118
+ # they respond to +to_sym+. This includes the keys from the root hash
119
+ # and from all nested hashes and arrays.
120
+ #
121
+ # hash = { 'person' => { 'name' => 'Rob', 'age' => '28' } }
122
+ #
123
+ # hash.deep_symbolize_keys
124
+ # # => {:person=>{:name=>"Rob", :age=>"28"}}
125
+ def deep_symbolize_keys
126
+ deep_transform_keys{ |key| key.to_sym rescue key }
127
+ end
128
+
129
+ # Destructively convert all keys to symbols, as long as they respond
130
+ # to +to_sym+. This includes the keys from the root hash and from all
131
+ # nested hashes and arrays.
132
+ def deep_symbolize_keys!
133
+ deep_transform_keys!{ |key| key.to_sym rescue key }
134
+ end
135
+
136
+ private
137
+
138
+ # support methods for deep transforming nested hashes and arrays
139
+ def _deep_transform_keys_in_object(object, &block)
140
+ case object
141
+ when Hash
142
+ object.each_with_object({}) do |(key, value), result|
143
+ result[yield(key)] = _deep_transform_keys_in_object(value, &block)
144
+ end
145
+ when Array
146
+ object.map {|e| _deep_transform_keys_in_object(e, &block) }
147
+ else
148
+ object
149
+ end
150
+ end
151
+
152
+ def _deep_transform_keys_in_object!(object, &block)
153
+ case object
154
+ when Hash
155
+ object.keys.each do |key|
156
+ value = object.delete(key)
157
+ object[yield(key)] = _deep_transform_keys_in_object!(value, &block)
158
+ end
159
+ object
160
+ when Array
161
+ object.map! {|e| _deep_transform_keys_in_object!(e, &block)}
162
+ else
163
+ object
164
+ end
165
+ end
166
+ end
167
+ end
168
+ end
@@ -0,0 +1,35 @@
1
+ module Gemsupport
2
+ module StringInteractions
3
+ refine String do
4
+ def underscore
5
+ gsub(/::/, '/')
6
+ .gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
7
+ .gsub(/([a-z\d])([A-Z])/, '\1_\2')
8
+ .tr('-', '_')
9
+ .downcase
10
+ end
11
+
12
+ def camelize
13
+ return self if self !~ /_/ && self =~ /[A-Z]+.*/
14
+ split('/').map do |e|
15
+ e.split('_').map { |w| w.capitalize }.join
16
+ end.join('::')
17
+ end
18
+
19
+ # Remove indentation spaces for multilines string
20
+ # From:
21
+ # | Anonymous Coward
22
+ # | - Community Guest
23
+ # To:
24
+ # |Anonymous Coward
25
+ # | - Community Guest
26
+ def unindent
27
+ gsub(/^#{scan(/^[ \t]+(?=\S)/).min}/, '')
28
+ end
29
+
30
+ def unindent!
31
+ replace(unindent)
32
+ end
33
+ end
34
+ end
35
+ end
@@ -1,3 +1,3 @@
1
1
  module Gemsupport
2
- VERSION = '0.4.2'
2
+ VERSION = '0.5.0'
3
3
  end
@@ -13,6 +13,8 @@ class EmptyFalse
13
13
  end
14
14
 
15
15
  describe 'blank' do
16
+ using Gemsupport::Blank
17
+
16
18
  context 'when it is a blank object' do
17
19
  [EmptyTrue.new, nil, false, '', ' ', " \n\t \r ", ' ', "\u00a0", [], {}].each do |blank_value|
18
20
  describe "#{blank_value.class}#blank?" do
@@ -1,6 +1,8 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Object do
4
+ using Gemsupport::DeepClone
5
+
4
6
  describe '#deep_clone' do
5
7
  context 'when deep clone action is impossible' do
6
8
  it 'raises an error' do
@@ -1,6 +1,8 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Hash do
4
+ using Gemsupport::DeepMerge
5
+
4
6
  let(:input_a) do
5
7
  { a: { b: { c: 3 } } }
6
8
  end
@@ -1,6 +1,8 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Hash do
4
+ using Gemsupport::HashKeys
5
+
4
6
  let(:simple) do
5
7
  {
6
8
  strings: { 'a' => 1, 'b' => 2 },
@@ -1,6 +1,8 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe 'String' do
4
+ using Gemsupport::StringInteractions
5
+
4
6
  describe '#underscore' do
5
7
  context 'when snake_case word' do
6
8
  it 'does nothing' do
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gemsupport
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.4.2
4
+ version: 0.5.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - mdouchement
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2015-11-02 00:00:00.000000000 Z
11
+ date: 2015-11-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: bundler
@@ -111,21 +111,21 @@ files:
111
111
  - gemsupport.gemspec
112
112
  - lib/gemsupport.rb
113
113
  - lib/gemsupport/console.rb
114
- - lib/gemsupport/core_ext.rb
115
- - lib/gemsupport/core_ext/blank.rb
116
- - lib/gemsupport/core_ext/hash.rb
117
- - lib/gemsupport/core_ext/hash_keys.rb
118
- - lib/gemsupport/core_ext/object_deep_clone.rb
119
- - lib/gemsupport/core_ext/string.rb
120
114
  - lib/gemsupport/error.rb
115
+ - lib/gemsupport/refinements.rb
116
+ - lib/gemsupport/refinements/blank.rb
117
+ - lib/gemsupport/refinements/deep_clone.rb
118
+ - lib/gemsupport/refinements/deep_merge.rb
119
+ - lib/gemsupport/refinements/hash_keys.rb
120
+ - lib/gemsupport/refinements/string_interactions.rb
121
121
  - lib/gemsupport/version.rb
122
122
  - spec/gemsupport/console_spec.rb
123
- - spec/gemsupport/core_ext/blank_spec.rb
124
- - spec/gemsupport/core_ext/hash_keys_spec.rb
125
- - spec/gemsupport/core_ext/hash_spec.rb
126
- - spec/gemsupport/core_ext/object_deep_clone_spec.rb
127
- - spec/gemsupport/core_ext/string_spec.rb
128
123
  - spec/gemsupport/error_spec.rb
124
+ - spec/gemsupport/refinements/blank_spec.rb
125
+ - spec/gemsupport/refinements/deep_clone_spec.rb
126
+ - spec/gemsupport/refinements/deep_merge_spec.rb
127
+ - spec/gemsupport/refinements/hash_keys_spec.rb
128
+ - spec/gemsupport/refinements/string_interactions_spec.rb
129
129
  - spec/spec_helper.rb
130
130
  homepage: https://github.com/mdouchement/gemsupport
131
131
  licenses:
@@ -139,7 +139,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
139
139
  requirements:
140
140
  - - ">="
141
141
  - !ruby/object:Gem::Version
142
- version: '0'
142
+ version: '2.0'
143
143
  required_rubygems_version: !ruby/object:Gem::Requirement
144
144
  requirements:
145
145
  - - ">="
@@ -1,5 +0,0 @@
1
- require 'gemsupport/core_ext/blank' unless defined?(ActiveSupport)
2
- require 'gemsupport/core_ext/string'
3
- require 'gemsupport/core_ext/hash_keys' unless defined?(ActiveSupport)
4
- require 'gemsupport/core_ext/hash'
5
- require 'gemsupport/core_ext/object_deep_clone'
@@ -1,130 +0,0 @@
1
- # https://raw.githubusercontent.com/rails/rails/4-1-stable/activesupport/lib/active_support/core_ext/object/blank.rb
2
- class Object
3
- # An object is blank if it's false, empty, or a whitespace string.
4
- # For example, '', ' ', +nil+, [], and {} are all blank.
5
- #
6
- # This simplifies
7
- #
8
- # address.nil? || address.empty?
9
- #
10
- # to
11
- #
12
- # address.blank?
13
- #
14
- # @return [true, false]
15
- def blank?
16
- respond_to?(:empty?) ? !!empty? : !self
17
- end
18
-
19
- # An object is present if it's not blank.
20
- #
21
- # @return [true, false]
22
- def present?
23
- !blank?
24
- end
25
-
26
- # Returns the receiver if it's present otherwise returns +nil+.
27
- # <tt>object.presence</tt> is equivalent to
28
- #
29
- # object.present? ? object : nil
30
- #
31
- # For example, something like
32
- #
33
- # state = params[:state] if params[:state].present?
34
- # country = params[:country] if params[:country].present?
35
- # region = state || country || 'US'
36
- #
37
- # becomes
38
- #
39
- # region = params[:state].presence || params[:country].presence || 'US'
40
- #
41
- # @return [Object]
42
- def presence
43
- self if present?
44
- end
45
- end
46
-
47
- class NilClass
48
- # +nil+ is blank:
49
- #
50
- # nil.blank? # => true
51
- #
52
- # @return [true]
53
- def blank?
54
- true
55
- end
56
- end
57
-
58
- class FalseClass
59
- # +false+ is blank:
60
- #
61
- # false.blank? # => true
62
- #
63
- # @return [true]
64
- def blank?
65
- true
66
- end
67
- end
68
-
69
- class TrueClass
70
- # +true+ is not blank:
71
- #
72
- # true.blank? # => false
73
- #
74
- # @return [false]
75
- def blank?
76
- false
77
- end
78
- end
79
-
80
- class Array
81
- # An array is blank if it's empty:
82
- #
83
- # [].blank? # => true
84
- # [1,2,3].blank? # => false
85
- #
86
- # @return [true, false]
87
- alias_method :blank?, :empty?
88
- end
89
-
90
- class Hash
91
- # A hash is blank if it's empty:
92
- #
93
- # {}.blank? # => true
94
- # { key: 'value' }.blank? # => false
95
- #
96
- # @return [true, false]
97
- alias_method :blank?, :empty?
98
- end
99
-
100
- class String
101
- BLANK_RE = /\A[[:space:]]*\z/
102
-
103
- # A string is blank if it's empty or contains whitespaces only:
104
- #
105
- # ''.blank? # => true
106
- # ' '.blank? # => true
107
- # "\t\n\r".blank? # => true
108
- # ' blah '.blank? # => false
109
- #
110
- # Unicode whitespace is supported:
111
- #
112
- # "\u00a0".blank? # => true
113
- #
114
- # @return [true, false]
115
- def blank?
116
- BLANK_RE === self
117
- end
118
- end
119
-
120
- class Numeric #:nodoc:
121
- # No number is blank:
122
- #
123
- # 1.blank? # => false
124
- # 0.blank? # => false
125
- #
126
- # @return [false]
127
- def blank?
128
- false
129
- end
130
- end
@@ -1,15 +0,0 @@
1
- Hash.class_eval do
2
- def deep_merge(hsh)
3
- merger = proc do |key, v1, v2|
4
- v1.kind_of?(Hash) && v2.kind_of?(Hash) ? v1.merge(v2, &merger) : v2
5
- end
6
- self.merge(hsh, &merger)
7
- end
8
-
9
- def deep_merge!(hsh)
10
- merger = proc do |key, v1, v2|
11
- v1.kind_of?(Hash) && v2.kind_of?(Hash) ? v1.merge(v2, &merger) : v2
12
- end
13
- self.merge!(hsh, &merger)
14
- end
15
- end
@@ -1,163 +0,0 @@
1
- # Extract from https://github.com/rails/rails/blob/4-1-stable/activesupport/lib/active_support/core_ext/hash/keys.rb
2
- class Hash
3
- # Returns a new hash with all keys converted using the block operation.
4
- #
5
- # hash = { name: 'Rob', age: '28' }
6
- #
7
- # hash.transform_keys{ |key| key.to_s.upcase }
8
- # # => {"NAME"=>"Rob", "AGE"=>"28"}
9
- def transform_keys
10
- result = {}
11
- each_key do |key|
12
- result[yield(key)] = self[key]
13
- end
14
- result
15
- end
16
-
17
- # Destructively convert all keys using the block operations.
18
- # Same as transform_keys but modifies +self+.
19
- def transform_keys!
20
- keys.each do |key|
21
- self[yield(key)] = delete(key)
22
- end
23
- self
24
- end
25
-
26
- # Returns a new hash with all keys converted to strings.
27
- #
28
- # hash = { name: 'Rob', age: '28' }
29
- #
30
- # hash.stringify_keys
31
- # # => { "name" => "Rob", "age" => "28" }
32
- def stringify_keys
33
- transform_keys{ |key| key.to_s }
34
- end
35
-
36
- # Destructively convert all keys to strings. Same as
37
- # +stringify_keys+, but modifies +self+.
38
- def stringify_keys!
39
- transform_keys!{ |key| key.to_s }
40
- end
41
-
42
- # Returns a new hash with all keys converted to symbols, as long as
43
- # they respond to +to_sym+.
44
- #
45
- # hash = { 'name' => 'Rob', 'age' => '28' }
46
- #
47
- # hash.symbolize_keys
48
- # # => { name: "Rob", age: "28" }
49
- def symbolize_keys
50
- transform_keys{ |key| key.to_sym rescue key }
51
- end
52
- alias_method :to_options, :symbolize_keys
53
-
54
- # Destructively convert all keys to symbols, as long as they respond
55
- # to +to_sym+. Same as +symbolize_keys+, but modifies +self+.
56
- def symbolize_keys!
57
- transform_keys!{ |key| key.to_sym rescue key }
58
- end
59
- alias_method :to_options!, :symbolize_keys!
60
-
61
- # Validate all keys in a hash match <tt>*valid_keys</tt>, raising ArgumentError
62
- # on a mismatch. Note that keys are NOT treated indifferently, meaning if you
63
- # use strings for keys but assert symbols as keys, this will fail.
64
- #
65
- # { name: 'Rob', years: '28' }.assert_valid_keys(:name, :age) # => raises "ArgumentError: Unknown key: :years. Valid keys are: :name, :age"
66
- # { name: 'Rob', age: '28' }.assert_valid_keys('name', 'age') # => raises "ArgumentError: Unknown key: :name. Valid keys are: 'name', 'age'"
67
- # { name: 'Rob', age: '28' }.assert_valid_keys(:name, :age) # => passes, raises nothing
68
- def assert_valid_keys(*valid_keys)
69
- valid_keys.flatten!
70
- each_key do |k|
71
- unless valid_keys.include?(k)
72
- raise ArgumentError.new("Unknown key: #{k.inspect}. Valid keys are: #{valid_keys.map(&:inspect).join(', ')}")
73
- end
74
- end
75
- end
76
-
77
- # Returns a new hash with all keys converted by the block operation.
78
- # This includes the keys from the root hash and from all
79
- # nested hashes and arrays.
80
- #
81
- # hash = { person: { name: 'Rob', age: '28' } }
82
- #
83
- # hash.deep_transform_keys{ |key| key.to_s.upcase }
84
- # # => {"PERSON"=>{"NAME"=>"Rob", "AGE"=>"28"}}
85
- def deep_transform_keys(&block)
86
- _deep_transform_keys_in_object(self, &block)
87
- end
88
-
89
- # Destructively convert all keys by using the block operation.
90
- # This includes the keys from the root hash and from all
91
- # nested hashes and arrays.
92
- def deep_transform_keys!(&block)
93
- _deep_transform_keys_in_object!(self, &block)
94
- end
95
-
96
- # Returns a new hash with all keys converted to strings.
97
- # This includes the keys from the root hash and from all
98
- # nested hashes and arrays.
99
- #
100
- # hash = { person: { name: 'Rob', age: '28' } }
101
- #
102
- # hash.deep_stringify_keys
103
- # # => {"person"=>{"name"=>"Rob", "age"=>"28"}}
104
- def deep_stringify_keys
105
- deep_transform_keys{ |key| key.to_s }
106
- end
107
-
108
- # Destructively convert all keys to strings.
109
- # This includes the keys from the root hash and from all
110
- # nested hashes and arrays.
111
- def deep_stringify_keys!
112
- deep_transform_keys!{ |key| key.to_s }
113
- end
114
-
115
- # Returns a new hash with all keys converted to symbols, as long as
116
- # they respond to +to_sym+. This includes the keys from the root hash
117
- # and from all nested hashes and arrays.
118
- #
119
- # hash = { 'person' => { 'name' => 'Rob', 'age' => '28' } }
120
- #
121
- # hash.deep_symbolize_keys
122
- # # => {:person=>{:name=>"Rob", :age=>"28"}}
123
- def deep_symbolize_keys
124
- deep_transform_keys{ |key| key.to_sym rescue key }
125
- end
126
-
127
- # Destructively convert all keys to symbols, as long as they respond
128
- # to +to_sym+. This includes the keys from the root hash and from all
129
- # nested hashes and arrays.
130
- def deep_symbolize_keys!
131
- deep_transform_keys!{ |key| key.to_sym rescue key }
132
- end
133
-
134
- private
135
- # support methods for deep transforming nested hashes and arrays
136
- def _deep_transform_keys_in_object(object, &block)
137
- case object
138
- when Hash
139
- object.each_with_object({}) do |(key, value), result|
140
- result[yield(key)] = _deep_transform_keys_in_object(value, &block)
141
- end
142
- when Array
143
- object.map {|e| _deep_transform_keys_in_object(e, &block) }
144
- else
145
- object
146
- end
147
- end
148
-
149
- def _deep_transform_keys_in_object!(object, &block)
150
- case object
151
- when Hash
152
- object.keys.each do |key|
153
- value = object.delete(key)
154
- object[yield(key)] = _deep_transform_keys_in_object!(value, &block)
155
- end
156
- object
157
- when Array
158
- object.map! {|e| _deep_transform_keys_in_object!(e, &block)}
159
- else
160
- object
161
- end
162
- end
163
- end
@@ -1,27 +0,0 @@
1
- Object.class_eval do
2
- def deep_clone(is_root: true)
3
- clone.tap do |deep_cloning_obj|
4
- deep_cloning_obj.instance_variables.each do |var|
5
- val = deep_cloning_obj.instance_variable_get(var)
6
- deep_cloning_obj.instance_variable_set(var, val.deep_clone(is_root: false))
7
- end
8
- end
9
- rescue TypeError
10
- return self unless is_root
11
- raise
12
- end
13
- end
14
-
15
- Hash.class_eval do
16
- def deep_clone(is_root: true)
17
- each_with_object({}) do |(k, v), hsh|
18
- hsh[k.deep_clone(is_root: false)] = v.deep_clone(is_root: false)
19
- end
20
- end
21
- end
22
-
23
- Array.class_eval do
24
- def deep_clone(is_root: true)
25
- map { |e| e.deep_clone(is_root: false) }
26
- end
27
- end
@@ -1,31 +0,0 @@
1
- String.class_eval do
2
- def underscore
3
- gsub(/::/, '/')
4
- .gsub(/([A-Z]+)([A-Z][a-z])/, '\1_\2')
5
- .gsub(/([a-z\d])([A-Z])/, '\1_\2')
6
- .tr('-', '_')
7
- .downcase
8
- end
9
-
10
- def camelize
11
- return self if self !~ /_/ && self =~ /[A-Z]+.*/
12
- split('/').map do |e|
13
- e.split('_').map { |w| w.capitalize }.join
14
- end.join('::')
15
- end
16
-
17
- # Remove indentation spaces for multilines string
18
- # From:
19
- # | Anonymous Coward
20
- # | - Community Guest
21
- # To:
22
- # |Anonymous Coward
23
- # | - Community Guest
24
- def unindent
25
- gsub(/^#{scan(/^[ \t]+(?=\S)/).min}/, '')
26
- end
27
-
28
- def unindent!
29
- replace(unindent)
30
- end
31
- end