1 / 27

Building a Ruby on Rails application with DB2 Express-C 9

Building a Ruby on Rails application with DB2 Express-C 9. An introduction to a sweet and trendy Web framework: Rails Markham Oct 17, 2006 Antonio Cangiano Alex Pitigoi IBM Toronto Lab. Agenda. On Rails ? Model – View – Controller (MVC) aspects in Rails

tommyp
Download Presentation

Building a Ruby on Rails application with DB2 Express-C 9

An Image/Link below is provided (as is) to download presentation Download Policy: Content on the Website is provided to you AS IS for your information and personal use and may not be sold / licensed / shared on other websites without getting consent from its author. Content is provided to you AS IS for your information and personal use only. Download presentation by click this link. While downloading, if for some reason you are not able to download a presentation, the publisher may have deleted the file from their server. During download, if you can't get a presentation, the file might be deleted by the publisher.

E N D

Presentation Transcript


  1. Building a Ruby on Rails application with DB2 Express-C 9 An introduction to a sweet and trendy Web framework: Rails Markham Oct 17, 2006 Antonio Cangiano Alex Pitigoi IBM Toronto Lab

  2. Agenda • On Rails ? • Model – View – Controller (MVC) aspects in Rails • Object Relation Mapping (ORM) flavors in Rails • Schema evolution through Rails migrations • Using a scaffold to build a prototype • Test “contaminated” development environment • Deployment

  3. On Rails ? Moving smooth and guided. • Extracted from the 37signals’ project collaboration tool: Basecamp • Makes Web development easy through simple conventions, and the “Don’t Repeat Yourself” principle: • Examples: • order records are stored in an Orders table • http://localhost/order/list/100 is how you request to display the Order with ID = 100 (change list with delete and it gets removed) • View partials can be reused over many web pages. • Maintenance and deployment simplified by built-in plumbing: MVC, ORM, testing.

  4. Moving smooth on known tracks • J2EE on Struts versus Ruby on Rails • stack comparison • Controller: processes HTTP requests extracting parameters to be passed to Action • Model: retrieves and persists data encapsulating access and domain logic • View: renders and presents the model in an HTML format Apache Tomcat Servlet Container Webrick ActionServlet Controller DispatchServlet Action ActionForm JSP View RHTML ActionController Hibernate ActiveRecord Model Datastore Datastore

  5. MVC the Rails way • Controller (DispatchServlet) orchestrates the application: • extracts parameters and interacts with the Model through an ActionController subclass: • Example: http://localhost/item/delete/100 directs to ItemController (defined in item_controller.rb) and passes to the method delete the value 100 • invokes the View providing the rendering of the Model • ActionController and ActionView form the Action Pack: core requests processing and responses generation.

  6. MVC the Rails way • View: a combination of templates, partials and layouts using Ruby code tag libraries (similar to Java tag libraries): • Allows data display and input, but never handles incoming data • ActionView module provides templates rendering (HTML or XML): • .rxml templates render XML pages, while • .rhtml templates render HTML pages • writing a view = writing a template (i.e. HTML fragments are interwoven with Ruby code statements) • Controller instance variables and public methods accessible from templates (actions communicate data to templates)

  7. MVC the Rails way: • Model: ActiveRecordwrapping framework • ActiveRecord subclass wraps a row in a database table/view, encapsulates access/domain logic, and acts as the gatekeeper. • Wraps class hierarchies to relational tables through single table inheritance (a string column ‘TYPE’ is added to every table). • Wraps classic table relationships (one-to-one, one-to-many, many-to-many) through declarations in the model (belongs-to, has-one, has-many, has-and-belongs-to-many), and also supports: acts_as_tree, acts_as_list • Differs from other ORM implementations through its “convention over configuration” principle which implies a sensible set of defaults.

  8. ActiveRecord: implementing one-to-one • A one-to-one association (one-to-zero-or-one relationship): a foreign key in a table’s row references at most a single row in another table. • In Rails one just adds a has_one declaration to the Order model, and a belongs_to declaration to the Invoice model: class Invoice < ActiveRecord::Base belongs_to :order . . . end class Order < ActiveRecord::Base has_one :invoice . . . end

  9. ActiveRecord: implementing one-to-many • A one-to-many aggregation representing a collection: a given order’s line item rows contain a foreign key column referring back to order. • In Rails one just needs to add the has_many declaration in the parent object, while the child table declares the belongs_to for its parent: class LineItem < ActiveRecord::Base belongs_to :order . . . end class Order < ActiveRecord::Base has_many :line_items . . . end

  10. ActiveRecord: implementing many-to-many • A many-to-many association where each side of the relationship contains a collection of things on the other side. • In Rails one just needs to add the has_and_belongs_to_many declaration to both models: class Category< ActiveRecord::Base has_and_belongs_to_many :products . . . end class Product< ActiveRecord::Base has_and_belongs_to_many :categories . . . end

  11. ActiveRecord: implementing act-as-tree • An act-as-tree structure can be achieved by adding a single column (parent_id) to a table to act as a foreign key reference back to the same table (linking child rows to their parent row). • In Rails one just needs to declare such structure using an acts_as_tree declaration for a table which defines the parent_id column: create_table :categories, :force => true do |t| t.column :name, :string t.column :parent_id, :integer . . . end class Category < ActiveRecord::Base acts_as_tree :order => "name“ . . . end

  12. ActiveRecord: implementing act-as-list • An act-as-list structure defines a relation between a parent table and some children tables through a column recording position in the list and allowing: traversal, addition, removal, position change • In Rails one just needs to declare the belongs_to and has_many to define parent-child relation, and then add acts_as_list to define the list: class Parent < ActiveRecord::Base has_many :children, :order => :position . . . end class Child < ActiveRecord::Base belongs_to :parent acts_as_list :scope => :parent_id . . . end

  13. ORM the Rails way: ActiveRecord • Wrapping an object view of some data to certain tables in a relational database: • wraps tables to classes, rows to objects, and columns to object attributes • implicit ActiveRecord conventions (customizable): • table name is the plural form for the class name • database schema reflexion configures classes that wrap tables • instance attributes generally correspond to the table row data • tables associated with a class have an integer id primary key column • the database connection is abstracted while the details are delegated to a set of database-specific adapters

  14. ActiveRecord: the intermediator • Makes it easy to implement the basic operations on database tables: Create, Read, Update, Delete (CRUD) • Abstracts and generates dynamic SQL • where or like clause represented by :conditions parameter • Item.find(:all, :conditions => “item_type = ‘new‘” and "name like ?", pa+"%") • order clause represented by :order param • Item.find(:all, :order => “part_type, shipped_at DESC" ) • Similarly, it provides :limit, :offset, :joins, :select, :readonly, :from, :group, :lock • Built-in statistics: average, maximum, minimum, sum, count • Built-in common searches: find_by_<name>, find_all_by_<name>, etc.

  15. Migrations to eradicate evolution migraines • Rails encourages an agile, iterative style of development: • If a database schema constantly evolves (adding a new class/table, changing attributes/columns) it’s easy to sync the application’s code. • ActiveRecord::Migration interface abstracts data manipulation in a database table and allows reversible actions: • for creation: up() method • for removal: down() method • Migration == Ruby source file (also under version control) prefixed with the schema version ID (example: 022_add_email_column.rb) and implementing the 2 class methods: up and down • Warning: migrations do not currently feature transactional support (i.e. an atomic failure inside up() may not allow the migration to be reapplied or even rolled back)

  16. Migrate up and down at will • Example: class AddEmailColumnToCustomer < ActiveRecord::Migration def self.up • add_column :customers, :e_mail, :string end def self.down • remove_column :customers, :e_mail end end • While the above code is in available in 022_add_email.rb • to apply: $ rake db:migrate VERSION=22 • to roll-back: $ rake db:migrate VERSION=21

  17. Raise a scaffold, build the edifice • Scaffold: an ActionController feature to generate standardized actions for a class wrapping a table. • Static scaffold: • $ ruby script/generate scaffold product admin • Scaffoldgenerator takes the modelandcontrollernames and • renders standardized actions • code generated responds to requests for HTML or XML content. • provides a customizable scaffold.css stylesheet in public/stylesheets • Dynamic scaffold: • scaffold :productdeclaration does runtime code generation for immediate use in testing of a newly added model and controller • web_service_scaffold() :invoke provides the simplest execution for a web service method from a web page in development.

  18. From scaffold to prototype • $ ruby script/generate scaffold product admin dependency model skip app/models/product.rb identical test/unit/product_test.rb identical test/fixtures/products.yml create app/views/admin/_form.rhtml create app/views/admin/list.rhtml create app/views/admin/show.rhtml create app/views/admin/new.rhtml create app/views/admin/edit.rhtml overwrite app/controllers/admin_controller.rb? [Ynaq] y force app/controllers/admin_controller.rb overwrite test/functional/admin_controller_test.rb? [Ynaq] y force test/functional/admin_controller_test.rb identical app/helpers/admin_helper.rb create app/views/layouts/admin.rhtml create public/stylesheets/scaffold.css Source: Agile Web Development with Rails 2nd edition, Dave Thomas

  19. Test environment: tests pass, work done • Applying “tough love” on our beloved applications before they are even written: • Rails framework testing support baked into every project: new projects are created with a test subdirectory (and associated database) • By convention, Rails calls: • testing models: unit tests • testing a single action in a controller: functional tests • testing the flow through controllers: integration tests • Rails generate script creates the unit tests files for the models and the functional tests files for the controllers • testing starts from the data (unit test) and moves up closer to the user interaction (functional and integration)

  20. Assertion, test, case, suite… results • Assertion: a method call stating the expectations (i.e. the simplest assertion is the method assert(), expecting its argument to be true). • Unit Tests: collection of assertions that validate a model • Functional Tests: collection of assertions that validate a controller’s action (example: test_delete_item) • Fixtures: specification of the initial contents of a model(s) under test (test/fixtures directory). • Mocks: replacement for a known object simplifying the needing for some real complex resource (network connection), while ensuring more consistent and repeatable results.

  21. Deployment: is there an easy way? • Webrick: development server for the single-threaded Rails • production environments (highly concurrent) require a front-end server (i.e. Apache, Lighttpd, or Zeus), + proxy to distribute requests to Rails processes running on several of back-end machines: • FastCGI proxy can handle multiple sequential requests to Ruby interpreter and Rails framework (one per process) • Mongrel (Ruby-based web-server) can proxy directly and considered a better, more extensible and scalable solution • Deployment principles: • start early (as soon as few views already display) in order to identify any deployment issues • do it often (after any major commit) in order to have early feedback from management and customers • Capistrano (RubyGem utility) provides reliable and repeatable deployment for Rails applications on remote servers.

  22. Deployment: few real life lessons from James Duncan • Make use of Capistrano, it’s better then you would first think • Make use of before and after hooks for the various tasks in Capistrano, to avoid overloading the deploy task • Ruby versions change. Set RubyGems in a GEM_HOME (e.g. /usr/local/rubygems/) to be able to reuse while upgrading Ruby • Don't even consider running your Rails app in CGI mode. Too slow. • The SCGI support in Rails is not quite ready for primetime, better use Lighty (with built in FastCGI and SCGI support) • For RubyGems that need to do native compilation of code the libraries should be kept in bundles outside of RubyGems if there is a need to manage multiple variants of the _same_ version. • If you do use Apache httpd, your options are 1.3.x or 2.0.x. • Don't use Ruby 1.8.3 with Rails on Mac OS X Source: http://blog.duncandavidson.com/2005/12/real_lessons_fo.html

  23. Credits and References • Many thanks to all of those who wrote about Rails in books and blogs and articles: • David Heinemeier Hanson • Dave Thomas • James Duncan • Bruce Tate • Patrick Peak • Aaron Rustad • References: • Agile Web Development using Rails, 2nd edition • http://www.theserverside.com/tt/articles/article.tss?l=RailsHibernate • http://www-128.ibm.com/developerworks/java/library/j-cb03076/index.html • http://weblogs.java.net/blog/batate/archive/2006/01/we_should_learn.html • http://www-128.ibm.com/developerworks/web/library/wa-rubyonrails/

  24. “Show me the code!”: Rails development environment • Ruby Development Tools (RDT) plug-in for Eclipse • http://updatesite.rubypeople.org/release • RadRails: free opensource IDE for Ruby on Rails • built on the Eclipse Rich Client Platform as IDE feature • RadRails feature: http://radrails.sourceforge.net/update • Includes also: • RDT plug-in http://updatesite.rubypeople.org/release • Subclipse plug-in http://subclipse.tigris.org/update_1.0.x • download complete setup from http://www.radrails.org/ • Note: the lab workstations are already setup using the Starter Toolkit for DB2 on Rails: http://www.alphaworks.ibm.com/tech/db2onrails • Ruby, Rails, DB2 driver for Ruby, DB2 adapter for Rails, DB2 Express C

  25. Creating a Rails project on Linux (shell commands) • Creating a Rails Web application: • <ruby_path>/bin/rails /path/to/your/app [options] Example: $ rails myblog $ cd blog/ $ vi config/database.yml • development: adapter: ibm_db2 database: Blog_dev username: userID password: passwd schema: myschema $ ruby ./script/generate migration InitialSchema $ vi db/migrate 001_initial_schema.rb $ rake migrate $ ruby script/generate scaffold post

  26. Creating a Rails project on Windows • Rails perspective: • File / New … • Rails / Rails project • Defaults will generate also the Web application tree and the WEBrick test server Rails tutorials http://manuals.rubyonrails.com/

More Related