2011-01-08 5 views
2

Post.find_by_slug('some-slug', :case_sensitive => false), Post.find_by_title('some title', :case_sensitive => false) 할 수 있기를 원합니다.중복 코드없이 find_by_x 메서드에 case_sensitivity 옵션 추가

나는 다음과 같은 방법을 시도했지만, 중복 로직이 많이있다 :

def self.find_by_name(name, options = {}) 
    conditions = options[:case_sensitive] == false ? ['UPPER(name) = UPPER(?)', name] : ['name = ?', name] 
    first(:conditions => conditions) 
    end 

    def self.find_by_slug(slug, options = {}) 
    conditions = options[:case_sensitive] == false ? ['UPPER(slug) = UPPER(?)', slug] : ['slug = ?', slug] 
    first(:conditions => conditions) 
    end 

어떻게 중복 코드없이 모든 find_by_x 방법에 대한 :case_sensitive => false 옵션을받을 수 있나요?

답변

2

제게 이것은 method_missing을 사용할 수있는 좋은 기회입니다. 기본적으로 클래스에 이미 존재하지 않는 메서드를 수신하는 클래스 메서드를 구현합니다.

그것은 다음과 같이 보일 수 있습니다

def self.method_missing(method, *args, &block) 
    if method.to_s =~ /^find_by_(.*)$/ 
    condition = args.first 
    options = args.last 
    first(options[:case_sensitive] == false ? ["UPPER(#{$1}) = UPPER(?)", condition] : ["#{$1} = ?", condition]) 
    else 
    super 
    end 
end 

을 지금, 당신은 할 수 있어야한다 :

find_by_name('name', :case_sensitive => false) 
find_by_slug('slug', :case_sensitive => false) 
find_by_any_other_column('value', :case_sensitive => false) 
관련 문제