A tool for rendering ORM-schemas and records to JSON for use with javascript code.
Pull request Compare This branch is 26 commits ahead of extjs:master.
Fetching latest commit…
Cannot retrieve the latest commit at this time.
Failed to load latest commit information.
lib When a fieldset doesn't exist, try the :default Mar 24, 2015
shoulda_macros Updated the Shoulda Macro to work with the new achitecture Apr 21, 2010
test Fix issue when executing sencha_fieldset :foo, where :foo doesn't exi… Feb 5, 2015
Gemfile rename project to sencha-model May 31, 2011
Gemfile.lock When a fieldset doesn't exist, try the :default Mar 24, 2015
LICENSE rename project to sencha-model May 31, 2011
README.rdoc fixed typo: ExtJS::Model -> Sencha::Model Jan 6, 2012
Rakefile rename project to sencha-model May 31, 2011



A simple Model mixin with adapters for various ORM frameworks such as ActiveRecord, DataMapper and MongoMapper. Sencha::Model was originally created as part of the gem extjs-mvc to assist with auto-generating ExtJS Stores (Ext.data.Store). However, it can be useful for a variety of Javascript frameworks for rendering data on the client.


% gem install sencha-model

or add the following line to your Rails Gemfile:

require 'sencha-model'

then run

bundle install

An ORM Model mixin: Sencha::Model

sencha-model contains Model mixin named Sencha::Model which works for three popular ORM frameworks, ActiveRecord, DataMapper and MongoMapper. The API for each framework is identical and an adapter can be created for just about any ORM in about an hour.

Simply include the mixin into your model. Use the class-method sencha_fields to specify those fields with will be used to render a record to Hash for later JSON-encoding.

class User < ActiveRecord::Base
  include Sencha::Model

  sencha_fields :exclude => [:password, :password_confirmation]

  # OR 
  sencha_fields :name, :description

  # OR
  sencha_fields :only => [:name, :description] # actually the same as above

  # OR
  sencha_fields :additional => [:computed] # includes all database columns and an additional computed field

  # OR define a column as a Hash
  sencha_fields :description, :name => {"sortDir" => "ASC"}, :created_at => {"dateFormat" => "c"}

  # OR render associations, association-fields will have their "mapping" property set automatically
  sencha_fields :name, :description, :company => [:name, :description]

  def computed
    name.blank? ? login : name

After including the model mixin Sencha::Model, try typing the following in irb console:

>> User.sencha_schema
=> { :idProperty=>"id", :fields=>[
     {:type=>'int', :allowBlank=>true, :name=>"id"},
     {:type=>'string', :allowBlank=>false, :name=>"first", :defaultValue => nil},
     {:type=>'string', :allowBlank=>false, :name=>"last", :defaultValue => nil},
     {:type=>'string', :allowBlank=>false, :name=>"email", :defaultValue => nil}

An auto-generated schema. These field-names were originally designed to be consumed by an Ext.data.Store from the Ext JS Framework. TODO: make the field-names configurable.

You can also define different sets of fields for different representations of your model.

E.g. with the following definition:

class User < ActiveRecord::Base
  include Sencha::Model

  sencha_fieldset :grid, [
    :name, :description, {:company => [:name, :description]}

  sencha_fieldset :combo, [:full_name]

  # computed field
  def full_name
    "#{first_name} #{name}"

You can get store configs for both representations with




And the corresponding data for the representations with




A Testing Mixin: Sencha::TestMacros

The sencha Gem includes a small set of testing macros to help unit-test models. Using this macro requires the 'Shoulda' gem from thoughtbot


In individual model unit tests:

class ModelTest < ActiveSupport::TestCase
  should_have_sencha_fields_for_fieldset :fieldset_name, [:name, :email, :city]
  #other tests

Note on Patches/Pull Requests

  • Fork the project.

  • Make your feature addition or bug fix.

  • Add tests for it. This is important so I don't break it in a future version unintentionally.

  • Commit, do not mess with rakefile, version, or history. (if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)

  • Send me a pull request. Bonus points for topic branches.


Copyright © 2009-2012 Chris Scott. See LICENSE for details.