2013-04-18 11 views
5

W większości moich aplikacji mam metodę current_user. Aby uniknąć wyjątków w przypadkach, takich jak current_user.name, gdzie current_user jest nil, szyny udostępniają metodę try. Problem polega na tym, że muszę pamiętać, aby używać try wszędzie tam, gdzie current_user może być nil.Szyny: zastępowanie próby ze wzorcem obiektów zerowych

Chcę użyć wzorca obiektu zerowego, aby usunąć ten dodatkowy narzut.

class NullUser 
    def method_missing(method_name, *args) 
    nil 
    end 
end 

def current_user 
    return NullUser.new unless UserSession.find 
    @current_user ||= UserSession.find.user 
end 

To może zastąpić try w niektórych przypadkach:

current_user.try(:first_name)  #=> nil 
current_user.first_name   #=> nil 

ale nie z dalszych połączeń łańcuchowych:

current_user.profiles.first.name #=> undefined method... 

starałem się zwrócić obiekt zerowy:

class NullUser 
    def method_missing(method_name, *args) 
    self.class.new 
    end 
end 

current_user.try { |u| u.profiles.first.name } #=> nil 
current_user.profiles.first.name    #=> nil 

ale byłoby to nie w innych przypadkach:

current_user.is_admin?   #=> #<NullUser:0x96f4e98> 

Czy jest możliwe rozwiązanie tego problemu lub nie wszyscy muszą żyć z try?

+1

nie może zrozumieć, dlaczego wydają się te same stron między zalogowanych i anonimowych użytkowników. dlaczego nie jest odpowiednio podzielony? – apneadiving

Odpowiedz

7

Zostałbym przywieziony z NullUser, ale zmień jego nazwę na GuestUser, aby wszystko było wyraźniejsze. Dodatkowo powinieneś wykorzystać wszystkie ważne metody z poziomu swojej klasy użytkownika, np.

class GuestUser 
    def method_missing(method_name, *args) 
    nil 
    end 

    def is_admin? 
    false 
    end 

    # maybe even fields: 
    def name 
    "Guest" 
    end 

    # ... 
end 
Powiązane problemy