ruby-next-core 0.9.0 → 0.10.2

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.
Files changed (57) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +42 -0
  3. data/README.md +20 -6
  4. data/lib/.rbnext/2.3/ruby-next/commands/core_ext.rb +167 -0
  5. data/lib/.rbnext/2.3/ruby-next/commands/nextify.rb +198 -0
  6. data/lib/.rbnext/2.3/ruby-next/language/eval.rb +66 -0
  7. data/lib/.rbnext/2.3/ruby-next/language/rewriters/base.rb +121 -0
  8. data/lib/.rbnext/2.3/ruby-next/language/rewriters/endless_range.rb +63 -0
  9. data/lib/.rbnext/2.3/ruby-next/language/rewriters/pattern_matching.rb +944 -0
  10. data/lib/.rbnext/2.3/ruby-next/language/rewriters/right_hand_assignment.rb +107 -0
  11. data/lib/.rbnext/2.3/ruby-next/utils.rb +65 -0
  12. data/lib/ruby-next.rb +8 -6
  13. data/lib/ruby-next/cli.rb +2 -2
  14. data/lib/ruby-next/commands/core_ext.rb +1 -1
  15. data/lib/ruby-next/commands/nextify.rb +41 -10
  16. data/lib/ruby-next/core.rb +27 -21
  17. data/lib/ruby-next/core/array/deconstruct.rb +9 -9
  18. data/lib/ruby-next/core/array/difference_union_intersection.rb +12 -12
  19. data/lib/ruby-next/core/constants/no_matching_pattern_error.rb +3 -3
  20. data/lib/ruby-next/core/enumerable/filter.rb +8 -8
  21. data/lib/ruby-next/core/enumerable/filter_map.rb +25 -25
  22. data/lib/ruby-next/core/enumerable/tally.rb +7 -7
  23. data/lib/ruby-next/core/enumerator/produce.rb +12 -12
  24. data/lib/ruby-next/core/hash/deconstruct_keys.rb +9 -9
  25. data/lib/ruby-next/core/hash/except.rb +11 -0
  26. data/lib/ruby-next/core/hash/merge.rb +8 -8
  27. data/lib/ruby-next/core/kernel/then.rb +2 -2
  28. data/lib/ruby-next/core/proc/compose.rb +11 -11
  29. data/lib/ruby-next/core/string/split.rb +6 -6
  30. data/lib/ruby-next/core/struct/deconstruct.rb +2 -2
  31. data/lib/ruby-next/core/struct/deconstruct_keys.rb +17 -17
  32. data/lib/ruby-next/core/symbol/end_with.rb +4 -4
  33. data/lib/ruby-next/core/symbol/start_with.rb +4 -4
  34. data/lib/ruby-next/core/time/ceil.rb +6 -6
  35. data/lib/ruby-next/core/time/floor.rb +4 -4
  36. data/lib/ruby-next/core/unboundmethod/bind_call.rb +4 -4
  37. data/lib/ruby-next/core_ext.rb +1 -1
  38. data/lib/ruby-next/language.rb +30 -6
  39. data/lib/ruby-next/language/proposed.rb +3 -0
  40. data/lib/ruby-next/language/rewriters/args_forward.rb +24 -20
  41. data/lib/ruby-next/language/rewriters/base.rb +1 -1
  42. data/lib/ruby-next/language/rewriters/endless_method.rb +26 -3
  43. data/lib/ruby-next/language/rewriters/endless_range.rb +1 -0
  44. data/lib/ruby-next/language/rewriters/find_pattern.rb +44 -0
  45. data/lib/ruby-next/language/rewriters/method_reference.rb +2 -1
  46. data/lib/ruby-next/language/rewriters/numbered_params.rb +1 -0
  47. data/lib/ruby-next/language/rewriters/pattern_matching.rb +103 -12
  48. data/lib/ruby-next/language/rewriters/right_hand_assignment.rb +74 -11
  49. data/lib/ruby-next/language/rewriters/safe_navigation.rb +87 -0
  50. data/lib/ruby-next/language/rewriters/shorthand_hash.rb +47 -0
  51. data/lib/ruby-next/language/rewriters/squiggly_heredoc.rb +36 -0
  52. data/lib/ruby-next/logging.rb +1 -1
  53. data/lib/ruby-next/rubocop.rb +15 -9
  54. data/lib/ruby-next/setup_self.rb +22 -0
  55. data/lib/ruby-next/version.rb +1 -1
  56. data/lib/uby-next.rb +8 -4
  57. metadata +21 -7
@@ -1,25 +1,25 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Array, method: :union, version: "2.6" do
4
- <<~RUBY
5
- def union(*others)
6
- others.reduce(Array.new(self).uniq) { |acc, arr| acc | arr }
7
- end
4
+ <<-RUBY
5
+ def union(*others)
6
+ others.reduce(Array.new(self).uniq) { |acc, arr| acc | arr }
7
+ end
8
8
  RUBY
9
9
  end
10
10
 
11
11
  RubyNext::Core.patch Array, method: :difference, version: "2.6" do
12
- <<~RUBY
13
- def difference(*others)
14
- others.reduce(Array.new(self)) { |acc, arr| acc - arr }
15
- end
12
+ <<-RUBY
13
+ def difference(*others)
14
+ others.reduce(Array.new(self)) { |acc, arr| acc - arr }
15
+ end
16
16
  RUBY
17
17
  end
18
18
 
19
19
  RubyNext::Core.patch Array, method: :intersection, version: "2.7" do
20
- <<~RUBY
21
- def intersection(*others)
22
- others.reduce(Array.new(self)) { |acc, arr| acc & arr }
23
- end
20
+ <<-RUBY
21
+ def intersection(*others)
22
+ others.reduce(Array.new(self)) { |acc, arr| acc & arr }
23
+ end
24
24
  RUBY
25
25
  end
@@ -10,8 +10,8 @@ RubyNext::Core.patch Object,
10
10
  # we only use the contents in `ruby-next core_ext`.
11
11
  supported: true,
12
12
  location: [__FILE__, __LINE__ + 2] do
13
- <<~RUBY
14
- class NoMatchingPatternError < RuntimeError
15
- end
13
+ <<-RUBY
14
+ class NoMatchingPatternError < RuntimeError
15
+ end
16
16
  RUBY
17
17
  end
@@ -1,8 +1,8 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Enumerable, method: :filter, version: "2.6" do
4
- <<~RUBY
5
- alias filter select
4
+ <<-RUBY
5
+ alias filter select
6
6
  RUBY
7
7
  end
8
8
 
@@ -11,15 +11,15 @@ end
11
11
  #
12
12
  # Also, Array also have `filter!`
13
13
  RubyNext::Core.patch Array, method: :filter!, version: "2.6" do
14
- <<~RUBY
15
- alias filter select
16
- alias filter! select!
14
+ <<-RUBY
15
+ alias filter select
16
+ alias filter! select!
17
17
  RUBY
18
18
  end
19
19
 
20
20
  RubyNext::Core.patch Hash, method: :filter!, version: "2.6" do
21
- <<~RUBY
22
- alias filter select
23
- alias filter! select!
21
+ <<-RUBY
22
+ alias filter select
23
+ alias filter! select!
24
24
  RUBY
25
25
  end
@@ -3,36 +3,36 @@
3
3
  # Refine Array seprately, 'cause refining modules is vulnerable to prepend:
4
4
  # - https://bugs.ruby-lang.org/issues/13446
5
5
  RubyNext::Core.patch Enumerable, method: :filter_map, version: "2.7", refineable: [Enumerable, Array] do
6
- <<~RUBY
7
- def filter_map
8
- if block_given?
9
- result = []
10
- each do |element|
11
- res = yield element
12
- result << res if res
13
- end
14
- result
15
- else
16
- Enumerator.new do |yielder|
17
- result = []
18
- each do |element|
19
- res = yielder.yield element
20
- result << res if res
21
- end
22
- result
23
- end
6
+ <<-RUBY
7
+ def filter_map
8
+ if block_given?
9
+ result = []
10
+ each do |element|
11
+ res = yield element
12
+ result << res if res
13
+ end
14
+ result
15
+ else
16
+ Enumerator.new do |yielder|
17
+ result = []
18
+ each do |element|
19
+ res = yielder.yield element
20
+ result << res if res
24
21
  end
22
+ result
25
23
  end
24
+ end
25
+ end
26
26
  RUBY
27
27
  end
28
28
 
29
29
  RubyNext::Core.patch Enumerator::Lazy, method: :filter_map, version: "2.7" do
30
- <<~RUBY
31
- def filter_map
32
- Enumerator::Lazy.new(self) do |yielder, *values|
33
- result = yield(*values)
34
- yielder << result if result
35
- end
36
- end
30
+ <<-RUBY
31
+ def filter_map
32
+ Enumerator::Lazy.new(self) do |yielder, *values|
33
+ result = yield(*values)
34
+ yielder << result if result
35
+ end
36
+ end
37
37
  RUBY
38
38
  end
@@ -3,12 +3,12 @@
3
3
  # Refine Array seprately, 'cause refining modules is vulnerable to prepend:
4
4
  # - https://bugs.ruby-lang.org/issues/13446
5
5
  RubyNext::Core.patch Enumerable, method: :tally, version: "2.7", refineable: [Enumerable, Array] do
6
- <<~RUBY
7
- def tally
8
- each_with_object({}) do |v, acc|
9
- acc[v] ||= 0
10
- acc[v] += 1
11
- end
12
- end
6
+ <<-RUBY
7
+ def tally
8
+ each_with_object({}) do |v, acc|
9
+ acc[v] ||= 0
10
+ acc[v] += 1
11
+ end
12
+ end
13
13
  RUBY
14
14
  end
@@ -1,20 +1,20 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Enumerator.singleton_class, method: :produce, singleton: Enumerator, version: "2.7" do
4
- <<~'RUBY'
5
- # Based on https://github.com/zverok/enumerator_generate
6
- def produce(*rest, &block)
7
- raise ArgumentError, "wrong number of arguments (given #{rest.size}, expected 0..1)" if rest.size > 1
8
- raise ArgumentError, "No block given" unless block
4
+ <<-'RUBY'
5
+ # Based on https://github.com/zverok/enumerator_generate
6
+ def produce(*rest, &block)
7
+ raise ArgumentError, "wrong number of arguments (given #{rest.size}, expected 0..1)" if rest.size > 1
8
+ raise ArgumentError, "No block given" unless block
9
9
 
10
- Enumerator.new(Float::INFINITY) do |y|
11
- val = rest.empty? ? yield() : rest.pop
10
+ Enumerator.new(Float::INFINITY) do |y|
11
+ val = rest.empty? ? yield() : rest.pop
12
12
 
13
- loop do
14
- y << val
15
- val = yield(val)
16
- end
17
- end
13
+ loop do
14
+ y << val
15
+ val = yield(val)
18
16
  end
17
+ end
18
+ end
19
19
  RUBY
20
20
  end
@@ -1,21 +1,21 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Hash, method: :deconstruct_keys, version: "2.7" do
4
- <<~RUBY
5
- def deconstruct_keys(_)
6
- self
7
- end
4
+ <<-RUBY
5
+ def deconstruct_keys(_)
6
+ self
7
+ end
8
8
  RUBY
9
9
  end
10
10
 
11
11
  # We need to hack `respond_to?` in Ruby 2.5, since it's not working with refinements
12
12
  if Gem::Version.new(RUBY_VERSION) < Gem::Version.new("2.6")
13
13
  RubyNext::Core.patch refineable: Hash, name: "HashRespondToDeconstructKeys", method: :deconstruct_keys, version: "2.7" do
14
- <<~RUBY
15
- def respond_to?(mid, *)
16
- return true if mid == :deconstruct_keys
17
- super
18
- end
14
+ <<-RUBY
15
+ def respond_to?(mid, *)
16
+ return true if mid == :deconstruct_keys
17
+ super
18
+ end
19
19
  RUBY
20
20
  end
21
21
  end
@@ -0,0 +1,11 @@
1
+ # frozen_string_literal: true
2
+
3
+ RubyNext::Core.patch Hash, method: :except, version: "3.0" do
4
+ <<-RUBY
5
+ def except(*keys)
6
+ self.dup.tap do |new_hash|
7
+ keys.each { |k| new_hash.delete(k) }
8
+ end
9
+ end
10
+ RUBY
11
+ end
@@ -1,14 +1,14 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Hash, method: :merge, version: "2.6", supported: {}.method(:merge).arity < 0, core_ext: :prepend do
4
- <<~RUBY
5
- def merge(*others)
6
- return super if others.size == 1
7
- return dup if others.size == 0
4
+ <<-RUBY
5
+ def merge(*others)
6
+ return super if others.size == 1
7
+ return dup if others.size == 0
8
8
 
9
- merge(others.shift).tap do |new_h|
10
- others.each { |h| new_h.merge!(h) }
11
- end
12
- end
9
+ merge(others.shift).tap do |new_h|
10
+ others.each { |h| new_h.merge!(h) }
11
+ end
12
+ end
13
13
  RUBY
14
14
  end
@@ -4,7 +4,7 @@
4
4
  # - https://bugs.ruby-lang.org/issues/13446
5
5
  # - Rails added `Kernel.prepend` in 6.1: https://github.com/rails/rails/commit/3124007bd674dcdc9c3b5c6b2964dfb7a1a0733c
6
6
  RubyNext::Core.patch Kernel, method: :then, version: "2.6", refineable: Object do
7
- <<~RUBY
8
- alias then yield_self
7
+ <<-RUBY
8
+ alias then yield_self
9
9
  RUBY
10
10
  end
@@ -2,18 +2,18 @@
2
2
 
3
3
  # rubocop:disable Style/LambdaCall
4
4
  RubyNext::Core.patch Proc, name: "ProcCompose", method: :<<, version: "2.6" do
5
- <<~RUBY
6
- def <<(other)
7
- raise TypeError, "callable object is expected" unless other.respond_to?(:call)
8
- this = self
9
- proc { |*args, &block| this.(other.(*args, &block)) }
10
- end
5
+ <<-RUBY
6
+ def <<(other)
7
+ raise TypeError, "callable object is expected" unless other.respond_to?(:call)
8
+ this = self
9
+ proc { |*args, &block| this.(other.(*args, &block)) }
10
+ end
11
11
 
12
- def >>(other)
13
- raise TypeError, "callable object is expected" unless other.respond_to?(:call)
14
- this = self
15
- proc { |*args, &block| other.(this.(*args, &block)) }
16
- end
12
+ def >>(other)
13
+ raise TypeError, "callable object is expected" unless other.respond_to?(:call)
14
+ this = self
15
+ proc { |*args, &block| other.(this.(*args, &block)) }
16
+ end
17
17
  RUBY
18
18
  end
19
19
  # rubocop:enable Style/LambdaCall
@@ -1,11 +1,11 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch String, method: :split, version: "2.6", supported: ("a b".split(" ", &proc {}) == "a b"), core_ext: :prepend do
4
- <<~RUBY
5
- def split(*args, &block)
6
- return super unless block_given?
7
- super.each { |el| yield el }
8
- self
9
- end
4
+ <<-RUBY
5
+ def split(*args, &block)
6
+ return super unless block_given?
7
+ super.each { |el| yield el }
8
+ self
9
+ end
10
10
  RUBY
11
11
  end
@@ -1,7 +1,7 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Struct, method: :deconstruct, version: "2.7" do
4
- <<~'RUBY'
5
- alias deconstruct to_a
4
+ <<-RUBY
5
+ alias deconstruct to_a
6
6
  RUBY
7
7
  end
@@ -2,31 +2,31 @@
2
2
 
3
3
  # Source: https://github.com/ruby/ruby/blob/b76a21aa45fff75909a66f8b20fc5856705f7862/struct.c#L953-L980
4
4
  RubyNext::Core.patch Struct, method: :deconstruct_keys, version: "2.7" do
5
- <<~'RUBY'
6
- def deconstruct_keys(keys)
7
- raise TypeError, "wrong argument type #{keys.class} (expected Array or nil)" if keys && !keys.is_a?(Array)
5
+ <<-'RUBY'
6
+ def deconstruct_keys(keys)
7
+ raise TypeError, "wrong argument type #{keys.class} (expected Array or nil)" if keys && !keys.is_a?(Array)
8
8
 
9
- return to_h unless keys
9
+ return to_h unless keys
10
10
 
11
- keys.each_with_object({}) do |k, acc|
12
- # if k is Symbol and not a member of a Struct return {}
13
- next if (Symbol === k || String === k) && !members.include?(k.to_sym)
14
- # if k is Integer check that index is not ouf of bounds
15
- next if Integer === k && k > size - 1
16
- acc[k] = self[k]
17
- end
18
- end
11
+ keys.each_with_object({}) do |k, acc|
12
+ # if k is Symbol and not a member of a Struct return {}
13
+ next if (Symbol === k || String === k) && !members.include?(k.to_sym)
14
+ # if k is Integer check that index is not ouf of bounds
15
+ next if Integer === k && k > size - 1
16
+ acc[k] = self[k]
17
+ end
18
+ end
19
19
  RUBY
20
20
  end
21
21
 
22
22
  # We need to hack `respond_to?` in Ruby 2.5, since it's not working with refinements
23
23
  if Gem::Version.new(RUBY_VERSION) < Gem::Version.new("2.6")
24
24
  RubyNext::Core.patch refineable: Struct, name: "StructRespondToDeconstruct", method: :deconstruct_keys, version: "2.7" do
25
- <<~RUBY
26
- def respond_to?(mid, *)
27
- return true if mid == :deconstruct_keys || mid == :deconstruct
28
- super
29
- end
25
+ <<-RUBY
26
+ def respond_to?(mid, *)
27
+ return true if mid == :deconstruct_keys || mid == :deconstruct
28
+ super
29
+ end
30
30
  RUBY
31
31
  end
32
32
  end
@@ -1,9 +1,9 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Symbol, method: :end_with?, version: "2.7" do
4
- <<~RUBY
5
- def end_with?(*prefixes)
6
- to_s.end_with?(*prefixes)
7
- end
4
+ <<-RUBY
5
+ def end_with?(*prefixes)
6
+ to_s.end_with?(*prefixes)
7
+ end
8
8
  RUBY
9
9
  end
@@ -1,9 +1,9 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Symbol, method: :start_with?, version: "2.7" do
4
- <<~RUBY
5
- def start_with?(*prefixes)
6
- to_s.start_with?(*prefixes)
7
- end
4
+ <<-RUBY
5
+ def start_with?(*prefixes)
6
+ to_s.start_with?(*prefixes)
7
+ end
8
8
  RUBY
9
9
  end
@@ -1,11 +1,11 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Time, method: :ceil, version: "2.7" do
4
- <<~'RUBY'
5
- def ceil(den = 0)
6
- sceil = (subsec * 10**den).ceil.to_r / 10**den
7
- change = sceil - subsec
8
- self + change
9
- end
4
+ <<-RUBY
5
+ def ceil(den = 0)
6
+ sceil = (subsec * 10**den).ceil.to_r / 10**den
7
+ change = sceil - subsec
8
+ self + change
9
+ end
10
10
  RUBY
11
11
  end
@@ -1,9 +1,9 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  RubyNext::Core.patch Time, method: :floor, version: "2.7" do
4
- <<~'RUBY'
5
- def floor(den = 0)
6
- self - (subsec % (10**-den))
7
- end
4
+ <<-RUBY
5
+ def floor(den = 0)
6
+ self - (subsec % (10**-den))
7
+ end
8
8
  RUBY
9
9
  end