Model-less Rails?

Hi,

I'm looking into using RoR to develop a front end for an existing system - one which is accessible via JSON-RPC. As such, there won't be any data management performed directly by the web application itself, all would be done via these RPC calls.

Is this possible? I assume that it is, so the next question is whether it's appropriate or not to chop off the model part of Rails. From tutorials and the like Rails seems quite dependent on convention (and even boasts of this). Will I get into trouble later on, or will decoupling the model part be more trouble than it's worth?

Thanks,

Shak

You are most likely going to have models. Those models are your business objects. In your case you're not going to be talking to a database, so the conventional "model" that is backed by a database will not be needed.

However, a Model in Rails can just be a simple Ruby class. Typically you'd have data models that did the RPC calls, so that the controllers interacted with them. The models then do the RPC calls to your backend, keeping each piece of code separated and easy to test. For example, say you were making a new front-end to Twitter. A skeleton model might look like this:

class Twitter

  def initialize(user, password)      @user = user      @password = password   end

   # returns timeline for the user    def posts    end

   # creates a new post    def post(message)      ....    end

private

end

Heck, you might even break this down farther and have a Post model, which you'd use to hold the Post you retrieved from Twitter, or even to have the Post class handle the creation of posts.

class Post   attr_accessor :message, :username, :posted_at end

The basic idea here is that you'd use models to encapsulate your logic, and controllers just to route requests around and show views. So, you'll have "models". just not ActiveRecord models.

you can have a look at the active_record_base_without_table plugin…

Shak wrote:

I'm looking into using RoR to develop a front end for an existing system - one which is accessible via JSON-RPC. As such, there won't be any data management performed directly by the web application itself, all would be done via these RPC calls.

Models are thin wrappers on external entities. Rails offers ActiveRecord as the One True Best external object to wrap. That's the convention.

To bypass the convention, simply do not use script/generate model. Just write the .rb file you want in app/models, put a class inside with the same name, and make it use whatever external entities you want to link to. All the rest of Rails will work the same...

I'm assuming you are meaning you don't want ActiveRecord models. If thats' the case, then yes it is possible. In fact, I currently do that in a couple apps that access objects through XML RPC calls. Here is how I do it, which will give you validations on errors.

class ModelWithoutDatabase end

Thanks for all the replies guys! Just what I wanted to her.

Is there a list of what methods my new models must implement in order to work well with the rest of Rails? Or does your ModelWithoutDatabase cover it all (via the include)?

The cool thing about this is that I can still call Model.valid? and use the validation stuff of ActiveRecord. Then I have my RPC objects that are Models inherit from the class above so:

class Contact < ModelWithoutDatabase def method1 rpc calls end

def method2 rpc calls end end

I hope that helps.

It does, thanks!

Shak

Yes that will work. I’ve been working on something very similar for an opensocial container, where I use models not tied to a database. I use something similar to this, although I also overrite save so you can validate on save.

http://svn.viney.net.nz/things/rails/plugins/active_record_base_without_table/

Also, the built in json serializer has really bad performance, especially in it’s association handling. I used the json gem and wrote my own code for serializing associations.

Chris

Chris,

I've been trying to use the active_record_base_without_table and it seems to work okay, until I try to dynamically create the model objects. At the moment I assign variables like so:

obj.instance_variable_set("@#{varname}", val)

However it seems that ActiveRecords don't hold values in variables, but in an attribute hash. This seems to get set like so:

obj.method_missing("@#{varname}=", [val], nil)

But this doesn't seem to work at all.

Is there a way of programatically assigning values to ActiveRecord columns?

Shak

But this doesn't seem to work at all.

Is there a way of programatically assigning values to ActiveRecord columns?

You need to call the accessor methods.

Fred

Thanks for the heads up, I managed to figure it out. However I'm now starting to think that using AR (without tables) is more trouble than its worth for non-trivial models - is it possible to define relationships if there's no tables to refer to?

For example, if the RPC returns a Post with a list of Comments, how would I write a table-less Post model which puts the Comments in the right place, and then doesn't let Rails go off and try to complete the model anyway?

Shak