[Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Previous Topic Next Topic
 
classic Classic list List threaded Threaded
10 messages Options
Reply | Threaded
Open this post in threaded view
|

[Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Alberto Almagro
These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }

But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

Cheers,
Alberto Almagro

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Rafael Mendonça França
If you think that method would be useful there is no reason why it should be Rails specific. Please send a feature request to the Ruby issue tracker here https://bugs.ruby-lang.org/.

Rafael França

On May 11, 2018, 13:10 -0400, Alberto Almagro <[hidden email]>, wrote:
These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }

But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

Cheers,
Alberto Almagro

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Alberto Almagro
Hi Rafael,

I'm glad to see you here. The reason I see its place here at first is because I think its use case fits better with the framework than with the language. When thinking on the Ruby language I would expect more to deal with collections which contain objets like String, Integer, and the likes, while in Ruby on Rails you are much likely to have related collections because of Active Record navigations that require this kind of map chaining.

Cheers,
Alberto Almagro

El viernes, 11 de mayo de 2018, 20:01:27 (UTC+2), Rafael Mendonça França escribió:
If you think that method would be useful there is no reason why it should be Rails specific. Please send a feature request to the Ruby issue tracker here <a href="https://bugs.ruby-lang.org/" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fbugs.ruby-lang.org%2F\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNHD-TdICxbMpOj54SFVFL4TS6Ynrw&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fbugs.ruby-lang.org%2F\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNHD-TdICxbMpOj54SFVFL4TS6Ynrw&#39;;return true;">https://bugs.ruby-lang.org/.

Rafael França

On May 11, 2018, 13:10 -0400, Alberto Almagro <<a href="javascript:" target="_blank" gdf-obfuscated-mailto="f7OgEzbFAAAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">alberto...@...>, wrote:
These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }

But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at <a href="https://ruby-doc.org/core-2.5.0/Array.html#method-i-dig" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FArray.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNExGRDK-moLSmNqnFtQLE3kusZckw&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FArray.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNExGRDK-moLSmNqnFtQLE3kusZckw&#39;;return true;">Array#dig or <a href="https://ruby-doc.org/core-2.5.0/Hash.html#method-i-dig" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FHash.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNEE6C8shOl0jIy-_cbFPgixYniS2Q&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FHash.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNEE6C8shOl0jIy-_cbFPgixYniS2Q&#39;;return true;">Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

Cheers,
Alberto Almagro

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="f7OgEzbFAAAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">rubyonrails-co...@googlegroups.com.
To post to this group, send email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="f7OgEzbFAAAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">rubyonra...@googlegroups.com.
Visit this group at <a href="https://groups.google.com/group/rubyonrails-core" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://groups.google.com/group/rubyonrails-core&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/group/rubyonrails-core&#39;;return true;">https://groups.google.com/group/rubyonrails-core.
For more options, visit <a href="https://groups.google.com/d/optout" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;">https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Anthony Bailey
On reading my first thought was "can you do that by defining to_proc on Array".

A brief play suggests one can:

class Array
  def to_proc
    Proc.new { |arg| self.inject(arg) { |memo, f| f.to_proc.call(memo) } }
  end
end

Example using primitives:

% [1, 2, 3].map &[:succ, :odd?, :to_s, :length]
=> [5, 4, 5]

Your example would I guess become

% orders.map &[:order_option, :item, :title]

Seems OK?

 --Anthony.

On 11/05/18 19:20, Alberto Almagro wrote:
Hi Rafael,

I'm glad to see you here. The reason I see its place here at first is because I think its use case fits better with the framework than with the language. When thinking on the Ruby language I would expect more to deal with collections which contain objets like String, Integer, and the likes, while in Ruby on Rails you are much likely to have related collections because of Active Record navigations that require this kind of map chaining.

Cheers,
Alberto Almagro

El viernes, 11 de mayo de 2018, 20:01:27 (UTC+2), Rafael Mendonça França escribió:
If you think that method would be useful there is no reason why it should be Rails specific. Please send a feature request to the Ruby issue tracker here <a href="https://bugs.ruby-lang.org/" target="_blank" rel="nofollow" onmousedown="this.href='https://www.google.com/url?q\x3dhttps%3A%2F%2Fbugs.ruby-lang.org%2F\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNHD-TdICxbMpOj54SFVFL4TS6Ynrw';return true;" onclick="this.href='https://www.google.com/url?q\x3dhttps%3A%2F%2Fbugs.ruby-lang.org%2F\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNHD-TdICxbMpOj54SFVFL4TS6Ynrw';return true;" moz-do-not-send="true">https://bugs.ruby-lang.org/.

Rafael França

On May 11, 2018, 13:10 -0400, Alberto Almagro <<a href="javascript:" target="_blank" gdf-obfuscated-mailto="f7OgEzbFAAAJ" rel="nofollow" onmousedown="this.href='javascript:';return true;" onclick="this.href='javascript:';return true;" moz-do-not-send="true">alberto...@...>, wrote:
These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }

But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at <a href="https://ruby-doc.org/core-2.5.0/Array.html#method-i-dig" target="_blank" rel="nofollow" onmousedown="this.href='https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FArray.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNExGRDK-moLSmNqnFtQLE3kusZckw';return true;" onclick="this.href='https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FArray.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNExGRDK-moLSmNqnFtQLE3kusZckw';return true;" moz-do-not-send="true">Array#dig or <a href="https://ruby-doc.org/core-2.5.0/Hash.html#method-i-dig" target="_blank" rel="nofollow" onmousedown="this.href='https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FHash.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNEE6C8shOl0jIy-_cbFPgixYniS2Q';return true;" onclick="this.href='https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FHash.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNEE6C8shOl0jIy-_cbFPgixYniS2Q';return true;" moz-do-not-send="true">Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

Cheers,
Alberto Almagro
--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="f7OgEzbFAAAJ" rel="nofollow" onmousedown="this.href='javascript:';return true;" onclick="this.href='javascript:';return true;" moz-do-not-send="true">rubyonrails-co...@googlegroups.com.
To post to this group, send email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="f7OgEzbFAAAJ" rel="nofollow" onmousedown="this.href='javascript:';return true;" onclick="this.href='javascript:';return true;" moz-do-not-send="true">rubyonra...@googlegroups.com.
Visit this group at <a href="https://groups.google.com/group/rubyonrails-core" target="_blank" rel="nofollow" onmousedown="this.href='https://groups.google.com/group/rubyonrails-core';return true;" onclick="this.href='https://groups.google.com/group/rubyonrails-core';return true;" moz-do-not-send="true">https://groups.google.com/group/rubyonrails-core.
For more options, visit <a href="https://groups.google.com/d/optout" target="_blank" rel="nofollow" onmousedown="this.href='https://groups.google.com/d/optout';return true;" onclick="this.href='https://groups.google.com/d/optout';return true;" moz-do-not-send="true">https://groups.google.com/d/optout.
--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.


--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Alberto Almagro
Hi Anthony,

thanks for your response. Great that you mention this. Yes I have seen other Rubyists on the internet proposing a similar solution, but for me it feels like a workaround, which could work in some cases, but it's not ideal. My main objection for that is that it implies defining to_proc, not only for Array, but for Enumerable, and you may need to define the method for other purposes. For example, I have also seen other people defining Array#to_proc using the first position of the provided array to hold the method that will be sent to the collection object and the remaining positions for the attributes that would be then passed to the method.

In the other hand, having the ability to pass more than one Symbol to the map method only implies extending that method capabilities, thus limiting the scope of the change to the method that we want to extend.

Cheers,
Alberto Almagro

El viernes, 11 de mayo de 2018, 22:10:49 (UTC+2), Anthony Bailey escribió:
On reading my first thought was "can you do that by defining to_proc on Array".

A brief play suggests one can:

class Array
  def to_proc
    Proc.new { |arg| self.inject(arg) { |memo, f| f.to_proc.call(memo) } }
  end
end

Example using primitives:

% [1, 2, 3].map &[:succ, :odd?, :to_s, :length]
=> [5, 4, 5]

Your example would I guess become

% orders.map &[:order_option, :item, :title]

Seems OK?

 --Anthony.

On 11/05/18 19:20, Alberto Almagro wrote:
Hi Rafael,

I'm glad to see you here. The reason I see its place here at first is because I think its use case fits better with the framework than with the language. When thinking on the Ruby language I would expect more to deal with collections which contain objets like String, Integer, and the likes, while in Ruby on Rails you are much likely to have related collections because of Active Record navigations that require this kind of map chaining.

Cheers,
Alberto Almagro

El viernes, 11 de mayo de 2018, 20:01:27 (UTC+2), Rafael Mendonça França escribió:
If you think that method would be useful there is no reason why it should be Rails specific. Please send a feature request to the Ruby issue tracker here <a href="https://bugs.ruby-lang.org/" rel="nofollow" target="_blank" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fbugs.ruby-lang.org%2F\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNHD-TdICxbMpOj54SFVFL4TS6Ynrw&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fbugs.ruby-lang.org%2F\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNHD-TdICxbMpOj54SFVFL4TS6Ynrw&#39;;return true;">https://bugs.ruby-lang.org/.

Rafael França

On May 11, 2018, 13:10 -0400, Alberto Almagro <[hidden email]>, wrote:
These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }

But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at <a href="https://ruby-doc.org/core-2.5.0/Array.html#method-i-dig" rel="nofollow" target="_blank" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FArray.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNExGRDK-moLSmNqnFtQLE3kusZckw&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FArray.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNExGRDK-moLSmNqnFtQLE3kusZckw&#39;;return true;">Array#dig or <a href="https://ruby-doc.org/core-2.5.0/Hash.html#method-i-dig" rel="nofollow" target="_blank" onmousedown="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FHash.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNEE6C8shOl0jIy-_cbFPgixYniS2Q&#39;;return true;" onclick="this.href=&#39;https://www.google.com/url?q\x3dhttps%3A%2F%2Fruby-doc.org%2Fcore-2.5.0%2FHash.html%23method-i-dig\x26sa\x3dD\x26sntz\x3d1\x26usg\x3dAFQjCNEE6C8shOl0jIy-_cbFPgixYniS2Q&#39;;return true;">Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

Cheers,
Alberto Almagro
--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to rubyonrails-co...@googlegroups.com.
To post to this group, send email to [hidden email].
Visit this group at <a href="https://groups.google.com/group/rubyonrails-core" rel="nofollow" target="_blank" onmousedown="this.href=&#39;https://groups.google.com/group/rubyonrails-core&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/group/rubyonrails-core&#39;;return true;">https://groups.google.com/group/rubyonrails-core.
For more options, visit <a href="https://groups.google.com/d/optout" rel="nofollow" target="_blank" onmousedown="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;">https://groups.google.com/d/optout.
--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="3_4aakXMAAAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">rubyonrails-co...@googlegroups.com.
To post to this group, send email to <a href="javascript:" target="_blank" gdf-obfuscated-mailto="3_4aakXMAAAJ" rel="nofollow" onmousedown="this.href=&#39;javascript:&#39;;return true;" onclick="this.href=&#39;javascript:&#39;;return true;">rubyonra...@googlegroups.com.
Visit this group at <a href="https://groups.google.com/group/rubyonrails-core" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://groups.google.com/group/rubyonrails-core&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/group/rubyonrails-core&#39;;return true;">https://groups.google.com/group/rubyonrails-core.
For more options, visit <a href="https://groups.google.com/d/optout" target="_blank" rel="nofollow" onmousedown="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;" onclick="this.href=&#39;https://groups.google.com/d/optout&#39;;return true;">https://groups.google.com/d/optout.


--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Matt Jones-15
In reply to this post by Alberto Almagro

On May 11, 2018, at 1:10 PM, Alberto Almagro <[hidden email]> wrote:

These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }
Very small nitpick: the code above (which tolerates `nil`) isn’t equivalent to the chained map (which doesn’t). But anyways...


But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

This reminds me of the Elixir function `get_in` and the associated functions in `Elixir.Access`. I’m not sure if any of the existing methods would make sense to extend with the behavior, though:

* `dig` is called on a collection and returns one element with many levels of nesting
* `pluck` is called on a collection and returns a collection, but only at one level of nesting
* the proposed function is called on a collection and returns a collection, with many levels of nesting

Neither function can guarantee that its arguments are scalars (or even that they aren’t Procs, for that matter) so extending them is tricky. Probably better to pick a new name.

You might also consider “Proc#*” from Facets:


I haven’t tried it, but in principle this should work if the operator precedence goes correctly:

    orders.map(&:order_options * &:item * &:title)

—Matt Jones

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Abdel Latif
Hi, 
I am new to Ruby, can you please give me an example of the orders collection ?
Thanks.

On Wed, May 16, 2018 at 9:45 AM, Matt Jones <[hidden email]> wrote:

On May 11, 2018, at 1:10 PM, Alberto Almagro <[hidden email]> wrote:

These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }
Very small nitpick: the code above (which tolerates `nil`) isn’t equivalent to the chained map (which doesn’t). But anyways...


But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

This reminds me of the Elixir function `get_in` and the associated functions in `Elixir.Access`. I’m not sure if any of the existing methods would make sense to extend with the behavior, though:

* `dig` is called on a collection and returns one element with many levels of nesting
* `pluck` is called on a collection and returns a collection, but only at one level of nesting
* the proposed function is called on a collection and returns a collection, with many levels of nesting

Neither function can guarantee that its arguments are scalars (or even that they aren’t Procs, for that matter) so extending them is tricky. Probably better to pick a new name.

You might also consider “Proc#*” from Facets:


I haven’t tried it, but in principle this should work if the operator precedence goes correctly:

    orders.map(&:order_options * &:item * &:title)

—Matt Jones

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Alberto Almagro
In reply to this post by Matt Jones-15
Hi Matt,

thanks a lot for all your points and suggestions. 

Having thought about naming, I'm also starting to think that picking a new name would be better. At least it would have the same mental effect as when you compare `dig` vs `[ ]` methods, `dig` predisposes you to think on nested access.

Cheers,
Alberto

2018-05-16 15:45 GMT+02:00 Matt Jones <[hidden email]>:

On May 11, 2018, at 1:10 PM, Alberto Almagro <[hidden email]> wrote:

These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }
Very small nitpick: the code above (which tolerates `nil`) isn’t equivalent to the chained map (which doesn’t). But anyways...


But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

This reminds me of the Elixir function `get_in` and the associated functions in `Elixir.Access`. I’m not sure if any of the existing methods would make sense to extend with the behavior, though:

* `dig` is called on a collection and returns one element with many levels of nesting
* `pluck` is called on a collection and returns a collection, but only at one level of nesting
* the proposed function is called on a collection and returns a collection, with many levels of nesting

Neither function can guarantee that its arguments are scalars (or even that they aren’t Procs, for that matter) so extending them is tricky. Probably better to pick a new name.

You might also consider “Proc#*” from Facets:


I haven’t tried it, but in principle this should work if the operator precedence goes correctly:

    orders.map(&:order_options * &:item * &:title)

—Matt Jones

--
You received this message because you are subscribed to a topic in the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/rubyonrails-core/22K3pcKEZZU/unsubscribe.
To unsubscribe from this group and all its topics, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Alberto Almagro
In reply to this post by Abdel Latif
Hi Abdel,

sorry for the confusion, I guess I didn't explain myself properly. `orders` would be a collection composed by instances of Order model. For example, imagine you do `Order.last(5)` to get the last 5 orders. I hope this clarifies the example.

Cheers,
Alberto

2018-05-16 18:50 GMT+02:00 Abdel Latif <[hidden email]>:
Hi, 
I am new to Ruby, can you please give me an example of the orders collection ?
Thanks.

On Wed, May 16, 2018 at 9:45 AM, Matt Jones <[hidden email]> wrote:

On May 11, 2018, at 1:10 PM, Alberto Almagro <[hidden email]> wrote:

These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }
Very small nitpick: the code above (which tolerates `nil`) isn’t equivalent to the chained map (which doesn’t). But anyways...


But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

This reminds me of the Elixir function `get_in` and the associated functions in `Elixir.Access`. I’m not sure if any of the existing methods would make sense to extend with the behavior, though:

* `dig` is called on a collection and returns one element with many levels of nesting
* `pluck` is called on a collection and returns a collection, but only at one level of nesting
* the proposed function is called on a collection and returns a collection, with many levels of nesting

Neither function can guarantee that its arguments are scalars (or even that they aren’t Procs, for that matter) so extending them is tricky. Probably better to pick a new name.

You might also consider “Proc#*” from Facets:


I haven’t tried it, but in principle this should work if the operator precedence goes correctly:

    orders.map(&:order_options * &:item * &:title)

—Matt Jones

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to a topic in the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/rubyonrails-core/22K3pcKEZZU/unsubscribe.
To unsubscribe from this group and all its topics, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.
Reply | Threaded
Open this post in threaded view
|

Re: [Feature] Symbol to_proc coercions: Enumerable#map can take several symbols

Alberto Almagro
From the answers I got, I guess this isn't a desired feature at the moment.

Anyway, thanks to everyone involved!

El vie., 18 may. 2018 a las 17:53, Alberto Almagro (<[hidden email]>) escribió:
Hi Abdel,

sorry for the confusion, I guess I didn't explain myself properly. `orders` would be a collection composed by instances of Order model. For example, imagine you do `Order.last(5)` to get the last 5 orders. I hope this clarifies the example.

Cheers,
Alberto

2018-05-16 18:50 GMT+02:00 Abdel Latif <[hidden email]>:
Hi, 
I am new to Ruby, can you please give me an example of the orders collection ?
Thanks.

On Wed, May 16, 2018 at 9:45 AM, Matt Jones <[hidden email]> wrote:

On May 11, 2018, at 1:10 PM, Alberto Almagro <[hidden email]> wrote:

These days I have been comparing records in my daily job lots of times, which made me think about a better way to retrieve and compare them. When I want to navigate through several relations in a collection I often see myself writing code like the following:

Given orders as a collection of Order:
> orders.map(&:order_option).map(&:item).map(&:title)
=> ['Foo', 'Bar', 'Baz']

That is, chaining maps with Symbol to Proc coercions one after each other. Sharing my thoughts with my company's architect we came up with the alternative:
> orders.map { |order| order&.order_option&.item&.title }
Very small nitpick: the code above (which tolerates `nil`) isn’t equivalent to the chained map (which doesn’t). But anyways...


But we agreed that the notation was awful and didn't improve what we had before. With this, I proposed what I think it is more like what we would expect Ruby to have. I would like to add a notation similar to the one we can find at Array#dig or Hash#dig in the following manner:
> orders.map(&:order_option, &:item, &:title)
The method doesn't necessarily need to be named map or collect, we can agree on a different name for it if you want. Please share your thoughts with me. If you like this, I would be very happy to write a PR to include it in Rails.

This reminds me of the Elixir function `get_in` and the associated functions in `Elixir.Access`. I’m not sure if any of the existing methods would make sense to extend with the behavior, though:

* `dig` is called on a collection and returns one element with many levels of nesting
* `pluck` is called on a collection and returns a collection, but only at one level of nesting
* the proposed function is called on a collection and returns a collection, with many levels of nesting

Neither function can guarantee that its arguments are scalars (or even that they aren’t Procs, for that matter) so extending them is tricky. Probably better to pick a new name.

You might also consider “Proc#*” from Facets:


I haven’t tried it, but in principle this should work if the operator precedence goes correctly:

    orders.map(&:order_options * &:item * &:title)

—Matt Jones

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.

--
You received this message because you are subscribed to a topic in the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this topic, visit https://groups.google.com/d/topic/rubyonrails-core/22K3pcKEZZU/unsubscribe.
To unsubscribe from this group and all its topics, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.



--
Alberto Almagro
Senior Ruby on Rails engineer | www.albertoalmagro.com

--
You received this message because you are subscribed to the Google Groups "Ruby on Rails: Core" group.
To unsubscribe from this group and stop receiving emails from it, send an email to [hidden email].
To post to this group, send email to [hidden email].
Visit this group at https://groups.google.com/group/rubyonrails-core.
For more options, visit https://groups.google.com/d/optout.