Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Rails concerns note #19

Open
hungle00 opened this issue Aug 13, 2024 · 0 comments
Open

Rails concerns note #19

hungle00 opened this issue Aug 13, 2024 · 0 comments
Labels
ruby About Ruby and Rails

Comments

@hungle00
Copy link
Owner

A Rails Concern is a module that extends the ActiveSupport::Concern module. Concerns allow us to include modules with methods (both instance and class) and constants into a class so that the including class can use them.

A concern provides two blocks:

  1. included
  • The code inside the included block is evaluated in the context of the including class.
  • You can write class macros (validations, associations, scopes, etc.) here, and any methods become instance methods of the including class.
  1. class_methods
  • The methods added inside this block become the class methods on the including class.
  • Instead of the class_methods block, you can create a nested module named ClassMethods.

For example, a concern named Taggable

module Taggable
  extend ActiveSupport::Concern

  included do

  end

  class_methods do

  end
end

To use this concern, you include the module as usual. For example, if the Post model wanted the visibility functionality, it would include the Taggable concern.

Justin Weiss has a great article that describes just how you can use Rails concern to refactor feature filter Product by attribute.

module Filterable
  extend ActiveSupport::Concern

  module ClassMethods
    def filter(filtering_params)
      results = self.where(nil)
      filtering_params.each do |key, value|
        results = results.public_send("filter_by_#{key}", value) if value.present?
      end
      results
    end
  end
end

In Product model:

class Product
  include Filterable
end

In controller that filter products by each attributes:

def index
  @products = Product.filter(params.slice(:status, :location, :starts_with))
end
@hungle00 hungle00 added the ruby About Ruby and Rails label Aug 13, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
ruby About Ruby and Rails
Projects
None yet
Development

No branches or pull requests

1 participant