How make utilities for models and controllers?

It's me again.

I need to abstract out some utilities that I want accessible to all controllers, AR models, and my own non-AR models.

Adding methods to application.rb doesn't do it -- which I think I understand because that's the top of the controller hierarchy, so models won't see controller methods. Plus, these should be easily transportable to any application, so cut & paste in application.rb would be lame anyway.

I understand Ruby's concept of modules & mixins, but I come from a language where 'require' just isn't used, so still getting used to that process.

So, if I create a module where does it go (wherever I want? typically in /lib/?), and is it necessary that every model & controller I want to use that with, I have to add a "require 'myModule'" line? There's no way to "load" it for universal usage?

Related...

I tried using request.remote_ip in a method in an AR model, and am getting a method undefined. I haven't really figured out when I need to use Class::Blah.method syntax for stuff. Is that what I need to do here? I tried poking around the RDocs for hints, but my guesses aren't working.

Thanks for being my "senior developer pairing buddy" :slight_smile:

-- gw

So, if I create a module where does it go (wherever I want? typically
in /lib/?), and is it necessary that every model & controller I want
to use that with, I have to add a "require 'myModule'" line? There's
no way to "load" it for universal usage?

not require. You want to include the module in the relevant clases, ie

class MyModel < AR::Base
  include Utilities
end

(rails would automatically require utilities.rb when it saw Utilities).

You could include such a module in both application.rb and AR::Base and wherever else they were useful. I would however query whether this is the best strategy - perhaps your utilities belong somewhere else, eg if some of your utilities are handy things to do with strings then you might be better off extending the String class.

Related...

I tried using request.remote_ip in a method in an AR model, and am
getting a method undefined. I haven't really figured out when I need
to use Class::Blah.method syntax for stuff. Is that what I need to do
here? I tried poking around the RDocs for hints, but my guesses
aren't working.

You can't do that. From the model (unless it was passed in to the model from the controller) there is no request object.

Fred

So, if I create a module where does it go (wherever I want? typically
in /lib/?), and is it necessary that every model & controller I want
to use that with, I have to add a "require 'myModule'" line? There's
no way to "load" it for universal usage?

not require. You want to include the module in the relevant clases, ie

class MyModel < AR::Base
include Utilities
end

(rails would automatically require utilities.rb when it saw Utilities).

You could include such a module in both application.rb and AR::Base and wherever else they were useful. I would however query whether this is the best strategy - perhaps your utilities belong somewhere else, eg if some of your utilities are handy things to do with strings then you might be better off extending the String class.

its a custom logging/debugging system to trace application steps and state, so I want to be able to trace details of what's happening inside controllers and models using the same central system. It doesn't really extend anything. It's my own system I want to be easy to drop into any app I work on.

There may be other systems to use, but if I do my own that I am accustomed to on other platforms that's one less new thing to have to worry about right now. It's tiny and easily pulled out if I come across a better way.

Related...

I tried using request.remote_ip in a method in an AR model, and am
getting a method undefined. I haven't really figured out when I need
to use Class::Blah.method syntax for stuff. Is that what I need to do
here? I tried poking around the RDocs for hints, but my guesses
aren't working.

You can't do that. From the model (unless it was passed in to the model from the controller) there is no request object.

Yep. Makes sense.

-- gw

Rails uses a built in logger that is very nice and easy to use. It is
almost identical to log4java. It's easy to use and supports various
logging levels. You can set / alter the default logging levels per
environment in the various environment files. Examples:

logger.debug "blah blah"
logger.info "a = #{a.inspect}"
logger.error "I just blew up"

You may still prefer to use yours, but this is built in to rails and
logger is automatically available in all of your models, controllers
and helpers. It is also very easy to create additional log files using
the same logger.

-Bill

its a custom logging/debugging system to trace application steps and
state, so I want to be able to trace details of what's happening
inside controllers and models using the same central system. It
doesn't really extend anything. It's my own system I want to be easy
to drop into any app I work on.

If it's truly to be used everywhere, you could always include your
module into Object

Fred