Saturday, September 8, 2012

Rails behaviour of form_for serving from a custom ruby class, (rails2 and rails3 differentiates)

Hi,

It has been so long writing a post and for a change this time it not my laziness but had been really occupied from office front.

Anyhow, here is one strange thing that I found with "form_for" in Rails2 and Rails3.
In Rails2, if we have a class in ruby (not derived from Activerecord::Base) some thing like the one below..

class SomeRubyClass

  attr_accessor :file_name, :file_data, :class_name, :error

  def initialize(file_name, file_data, class_name, error)
    @file_name = file_name
    @file_data = file_data
    @class_name = class_name
    @error = error
  end

  def self.first
    #Some code, which will give an object
  end
end


We can use form_for with it something like this

class SomeController < ApplicationController
  def index
    @some_ruby_class = SomeRubyClass.new("file_name", "file_data", "class_name", "error")
  end

  def create
    @some_ruby_class = SomeRubyClass.first
    @some_ruby_class.class_name = params[:some_ruby_class][:class_name]
    @some_ruby_class.file_name = params[:some_ruby_class][:file_name]
  
    #some more code
    redirect_to :back
  end
end

<% form_for @some_ruby_class, :url => {:action => :create} do |f| %>
    <%= f.text_field :class_name %>
    <%= f.text_field :file_name %>
    <%= f.submit 'Update' %> 
<% end %>

and we can do manipulation as per the need.
But in Rails3 this thing is not supported with form_for
It gives exception like...
undefined method `model_name' for SomeRubyClass:Class' 
and to make it work we have to add these lines 
1. extend ActiveModel::Naming
2. add to_key instance method which must return an array

so added it and result is something like this
class SomeRubyClass
  extend ActiveModel::Naming

  attr_accessor :file_name, :file_data, :class_name, :error

  def initialize(file_name, file_data, class_name, error)
    @file_name = file_name
    @file_data = file_data
    @class_name = class_name
    @error = error
  end

  def self.first
    #Some code, which will give an object
  end

  def to_key
    ["some_key", "some_value"]
  end

end

and it works! Now question arises, Rails3 is imposing me to use ActiveModel (which was initially meant to provide ActiveRecord base type facilities like validation etc.) for simple things like form_for why?? am I missing something here.

No comments:

Post a Comment

Sky diving! What it feels like.

Writing a new post after almost a year :) Penning it down here.. so that can relive that moment when i did the jump from 10000 feet up in...