Read more

Consul: Querying a power that might be nil

Henning Koch
January 29, 2013Software engineer at makandra GmbH

Consul Show archive.org snapshot 0.6.1+ gives your Power class a number of static methods that behave neutrally in case Power.current is nil. This allows you to create authorization-aware models that still work when there is no user at the end of a web browser, e.g. on the console, during tests or during batch processes.


Illustration UI/UX Design

UI/UX Design by makandra brand

We make sure that your target audience has the best possible experience with your digital product. You get:

  • Design tailored to your audience
  • Proven processes customized to your needs
  • An expert team of experienced designers
Read more Show archive.org snapshot

You will often want to access Power.current from another model, to e.g. iterate through the list of accessible users:

class UserReport

  def data
    Power.current.users.collect do |user|
      [user.name, user.email, user.income]
    end
  end

end

Good practice is for your model to not crash when Power.current is nil. This is the case when your model isn't
called as part of processing a browser request, e.g. on the console, during tests and during batch processes.
In such cases your model should simply skip authorization and assume that all users are accessible:

class UserReport

  def data
    accessible_users = Power.current.present? Power.current.users || User
    accessible_users.collect do |user|
      [user.name, user.email, user.income]
    end
  end

end

Because this pattern is so common, the Power class comes with a number of class methods you can use to either query
Power.current or, if it is not set, just assume that everything is accessible:

class UserReport

  def data
    Power.for_model(user).collect do |user|
      [user.name, user.email, user.income]
    end
  end

end

There is a long selection of class methods that behave neutrally in case Power.current is nil:

Call Equivalent
Power.for_model(Note) Power.current.present? ? Power.current.notes : Note
Power.for_model(:updatable, Note) Power.current.present? ? Power.current.updatable_notes : Note
Power.include_model?(Note) Power.current.present? ? Power.notes? : true
Power.include_model?(:updatable, Note) Power.current.present? ? Power.updatable_notes? : true
Power.include_model!(Note) Power.notes! if Power.current.present?
Power.include_model!(:updatable, Note) Power.updatable_notes! if Power.current.present?
Power.for_record(Note.last) Power.current.present? ? Power.current.notes : Note
Power.for_record(:updatable, Note.last) Power.current.present? ? Power.current.updatable_notes : Note
Power.include_record?(Note.last) Power.current.present? ? Power.note?(Note.last) : true
Power.include_record?(:updatable, Note.last) Power.current.present? ? Power.updatable_note?(Note.last?) : true
Power.include_record!(Note.last) Power.note!(Note.last) if Power.current.present?
Power.include_record!(:updatable, Note.last) Power.updatable_note!(Note.last) if Power.current.present?
Henning Koch
January 29, 2013Software engineer at makandra GmbH
Posted by Henning Koch to makandra dev (2013-01-29 15:10)