2013-03-21 1 views
2

나는 두 개의 매우 레일 애플 리케이션에 대한 내 루비 개체에 비슷한 방법이 있습니다. 나는 그들이 결합 될 수 있다는 것을 알고, 나는 단지 어떻게해야할지 모른다. (당신이 #try를 사용하지 않는, return unless 외에 가능한 NILS을 처리 할 수있는 더 아름다운 길을 찾을 수 있다면 추가 포인트.)Ruby : 비슷한 두 가지 방법을 하나에 결합 하시겠습니까?

def is_portal_admin?(resource) 
    return unless resource.user && resource.user.clinic_memberships.any? 
    memberships = resource.user.clinic_memberships.collect { |membership| membership.portal_admin? } 
    memberships.include?(true) 
    end 

    def is_staff_admin?(resource) 
    return unless resource.user && resource.user.clinic_memberships.any? 
    memberships = resource.user.clinic_memberships.collect { |membership| membership.staff_admin? } 
    memberships.include?(true) 
    end 
+0

메서드 호출의 동작 대신 심볼 또는 무언가로 사용 권한을 정의 해보십시오. 그런 다음 리소스 및 사용 권한 기호를 사용하는 단일 메서드 (is_admin_type)로 리팩토링 할 수 있습니다. –

답변

3

방법에 대해 :

def is_admin_of_type?(type, resource) 
    return unless resource.user && resource.user.clinic_memberships.any? && type 
    memberships = resource.user.clinic_memberships.collect { |membership| membership.send("#{type}_admin?") } 
    memberships.include?(true) 
end 

사람이 존재하지 않는 유형을 제공하는 경우

, it'l NoMethodError을 던져주십시오. 또한 더 많은 관리 유형을 추가하면 앞으로 호환됩니다.

+0

나는'def is_admin_of_type? '과 같이 갈 것이지만 그 외는 +1 –

+0

@AlexWayne : 감사합니다. 나는 그것을 바꿀 것이다. – Linuxios

2

collectinclude? 메커니즘 대신 any?을 사용하면됩니다. clinic_memberships이 항상 배열을 반환하면 (예 : has_many 연관 인 경우) 확인하지 않아도됩니다.

def has_membership?(resource, &block) 
    return unless resource.user 
    resource.user.clinic_memberships.any?(&block) 
end 

는 다음 입력하지 않으면 지점, 전무가 반환되면, 그렇게

has_memberhsip?(resource){|m| m.portal_admin?} 
+0

고급 솔루션 – Intrepidd

0
def is_admin?(resource, kind) 
    if resource.user && resource.user.clinic_memberships.any? 
    !!resource.user.clinic_memberships.detect { |membership| membership.send("#{kind}_admin?") } 
    end 
end 

에 해당

has_membership?(resource, &:portal_admin?) 

처럼 호출 할 수 있습니다 위와 같은 귀하의 조건부는 명시 적 수익과 동일한 결과를 산출합니다 ...

두 번째 매개 변수를 추가하고 staff 또는 : portal (또는 "staff"또는 "portal")을 전달하십시오. "send"를 사용하면 런타임에 "staff_admin"으로 eval됩니다. 또는 "portal_admin?"

collect + include 대신 detect를 사용합니까? 적어도 하나가 발견되면 객체를 반환하고 !! double은 true/false 결과로 바꾸기 위해 무효화됩니다.

저는 개인적으로 resource.user.clinic_memberships.any 이후로 개인적으로 이렇게 할 것입니다. 그렇지 않으면

실제로 clinic_memberships이 전무 것을 방지하려는 경우
def is_admin?(resource, kind) 
    !!resource.user.clinic_memberships.detect { |membership| membership.send("#{kind}_admin?") } if resource.user 
end 

, 당신은 ".ANY를?"조건부 년 하반기 필요하지만, 드롭 수행 : 사물의 웅대 한 계획의 이론에 불과 어떤 테스트를해도 오류가 있습니까? 에 대하여.

0
def is_portal_admin?(resource) 
    is_admin_of_type?(resource, :portal) 
end 

def is_staff_admin?(resource) 
    is_admin_of_type?(resource, :staff) 
end 

def is_admin_of_type?(resource, type) 
    if (user = resource.user) 
    user.clinic_memberships.any? { |ms| ms.send("#{type}_admin?") } 
    end 
end 
  • memberships이 있는지 확인하기 위해 중복입니다.
  • conditinal 뒤에 || false을 추가하여 method?이 부울을 반환하는지 확인할 수 있습니다.
  • is_admin_of_type?을 비공개로 설정할 수 있습니다.
관련 문제