Calculate the minimum/maximum from an enumerable's extracted elements

```
payments = [Payment.new(5), Payment.new(15), Payment.new(10)]
payments.minimum(:price) # => 5
payments.maximum(:price) # => 20
```
This commit is contained in:
Ayrton De Craene 2021-02-11 11:15:10 +01:00
parent 1efa175b3b
commit 2526938b32
4 changed files with 78 additions and 0 deletions

View File

@ -100,6 +100,15 @@ class TestController < ActionController::Base
end
end
def conditional_hello_with_array_of_records
record = Struct.new(:updated_at, :cache_key).new(Time.now.utc.beginning_of_day, "foo/123")
old_record = Struct.new(:updated_at, :cache_key).new(Time.now.utc.beginning_of_day.yesterday, "bar/123")
if stale?([record, old_record])
render action: "hello_world"
end
end
def dynamic_render
render params[:id] # => String, AC::Params
end
@ -522,6 +531,34 @@ class LastModifiedRenderTest < ActionController::TestCase
assert_equal @last_modified, @response.headers["Last-Modified"]
end
def test_responds_with_last_modified_with_array_of_records
get :conditional_hello_with_array_of_records
assert_equal @last_modified, @response.headers["Last-Modified"]
end
def test_request_not_modified_with_array_of_records
@request.if_modified_since = @last_modified
get :conditional_hello_with_array_of_records
assert_equal 304, @response.status.to_i
assert_predicate @response.body, :blank?
assert_equal @last_modified, @response.headers["Last-Modified"]
end
def test_request_not_modified_but_etag_differs_with_array_of_records
@request.if_modified_since = @last_modified
@request.if_none_match = '"234"'
get :conditional_hello_with_array_of_records
assert_response :success
end
def test_request_modified_with_array_of_records
@request.if_modified_since = "Thu, 16 Jul 2008 00:00:00 GMT"
get :conditional_hello_with_array_of_records
assert_equal 200, @response.status.to_i
assert_predicate @response.body, :present?
assert_equal @last_modified, @response.headers["Last-Modified"]
end
def test_responds_with_last_modified_with_collection_of_records
get :conditional_hello_with_collection_of_records
assert_equal @last_modified, @response.headers["Last-Modified"]

View File

@ -1,3 +1,18 @@
* Add `Enumerable#maximum` and `Enumerable#minimum` to easily calculate the maximum or minimum from extracted
elements of an enumerable.
```ruby
payments = [Payment.new(5), Payment.new(15), Payment.new(10)]
payments.minimum(:price) # => 5
payments.maximum(:price) # => 20
```
This also allows passing enumerables to `fresh_when` and `stale?` in Action Controller.
See PR [#41404](https://github.com/rails/rails/pull/41404) for an example.
*Ayrton De Craene*
* `ActiveSupport::Cache::MemCacheStore` now accepts an explicit `nil` for its `addresses` argument.
```ruby

View File

@ -16,6 +16,22 @@ module Enumerable
# :startdoc:
# Calculates the minimum from the extracted elements.
#
# payments = [Payment.new(5), Payment.new(15), Payment.new(10)]
# payments.minimum(:price) # => 5
def minimum(key)
map(&key).min
end
# Calculates the maximum from the extracted elements.
#
# payments = [Payment.new(5), Payment.new(15), Payment.new(10)]
# payments.maximum(:price) # => 15
def maximum(key)
map(&key).max
end
# Calculates a sum from the elements.
#
# payments.sum { |p| p.price * p.tax_rate }

View File

@ -29,6 +29,16 @@ class EnumerableTests < ActiveSupport::TestCase
assert_equal(e, v, msg)
end
def test_minimum
payments = GenericEnumerable.new([ Payment.new(5), Payment.new(15), Payment.new(10) ])
assert_equal 5, payments.minimum(:price)
end
def test_maximum
payments = GenericEnumerable.new([ Payment.new(5), Payment.new(15), Payment.new(10) ])
assert_equal 15, payments.maximum(:price)
end
def test_sums
enum = GenericEnumerable.new([5, 15, 10])
assert_equal 30, enum.sum