Yet Another Rails Newbie

June 26, 2006

It’s all brackets

Filed under: RubyOnRails — Richard @ 8:25 pm

I’ve been experimenting using the following code to retrieve HTML from various sites:

require 'open-uri'

class DemoController < ApplicationController
def index
open('http://www.google.co.uk/search?q=ruby') {
|html| render_text html.read()
}
end
end

If you try it, you’ll get the HTML for a Google results page. So far so good.
However, this is where I’m stuck. One site I’ve been trying to access passes a GUID in the querystring and it’s wrapped in curly brackets. So I updated the ‘open’ line to say:

open('http://www.google.co.uk/search?q={3F2504E0-4F89-11D3-9A-0C-03-05-E8-2C-33-01}') {then refreshed my browser; only to be presented with the following error:

URI::InvalidURIError in DemoController#index

bad URI(is not URI?): http://www.google.co.uk/search?q={3F2504E0-4F89-11D3-9A-0C-03-05-E8-2C-33-01}
RAILS_ROOT: /code/public/../config/..
/usr/local/lib/ruby/1.8/uri/common.rb:432:in `split'
/usr/local/lib/ruby/1.8/uri/common.rb:481:in `parse'
/usr/local/lib/ruby/1.8/open-uri.rb:85:in `open'
#{RAILS_ROOT}/app/controllers/demo_controller.rb:5:in `index'

From what I’ve read, curly brackets aren’t allowed in a Ruby URI (despite my browser being capable of using them). I’ve tried encoding them but then the page is called with the encoded version, which in my case, the site isn’t expecting and it doesn’t work.

What I’m looking for is a way to allow an ‘unsafe’ URI to be called. Does anyone know if that’s possible?

June 19, 2006

Ooh, that’s clever.

Filed under: RubyOnRails — hittingthebuffers @ 10:09 pm

While knocking together a new Rails app earlier I typed script/generate model Binding and expected the usual list of created files and directories. Instead I got this:


Po:~/rails/woms eifs$ script/generate model binding
The name 'Binding' is reserved by Ruby on Rails.
Please choose an alternative and run this generator again.

Suggestions:

Sense 1
binding -- (the capacity to attract and hold something)
=> attraction, attractiveness -- (the quality of arousing interest; being attractive or something that attracts; "her personality held a strange attraction for him")

Sense 2
binding -- (strip sewn over or along an edge for reinforcement or decoration)
=> sewing, stitchery -- (needlework that involves sewing; "she put her sewing back in the basket")

Sense 3
dressing, bandaging, binding -- (the act of applying a bandage)
=> medical care, medical aid -- (professional treatment for illness or injury)

Sense 4
binding, book binding, cover, back -- (the front and back covering of a book; "the book had a leather binding")
=> protective covering, protective cover, protection -- (a covering that is intend to protect from damage or injury; "they had no protection from the fallout"; "wax provided protection for the floors")

June 5, 2006

Migrate the way.

Filed under: ActiveRecord, RubyOnRails — Richard @ 10:13 pm

Yesterday I spent a couple of hours fathoming out how to use migration. I've read several articles and blogs saying that this is the best way to create your database tables in Rails, so thought I'd give it a go.

Firstly, the fact that it's possible to update your database schema, or rollback to a previous version seemed great. You simply type ruby script/generate migration SomeDescription and you have a file created in the db/migrate folder called something like 001_some_description.rb.

Then, next time you want to modify the database you type ruby script/generate migration AnotherDescription and another file called 002_another_description.rb would appear. So far so good.

But what happens if there's a problem in your migration code. For example, I accidentally had a field of type :booolean (with the extra 'o'). Then, when I ran rake migrate, there was a MySQL error and the migration stopped. Some of the migration had succeeded and one of the tables had been created, but the schema_info table which tracks which version is actually in the database still contained the previous version number. It seemed odd that if a migration fails, then it doesn't automatically call the self.down method to restore the database to the working version. Instead, I manually had to go into the MySQL command line, type UPDATE schema_info SET version = 2 (which was the version that failed) and then I could use rake migrate VERSION=1 to undo the partly updated tables. I was then able to correct my typo and re-rake the migration. Also noting that VERSION has to be in upper case which caught me out the first time I tried. I guess I could have manually undone the changes that Rails had made, but since I'd already defined these for the rollback, it seemed easier to use rake.

Another thing which I wasn't sure about was foreign keys. I'm a full time web developer and at work, whenever there are relationships, there are foreign keys. I was surprised to find that Rails doesn't have them! I knew about has_many and belongs_to – but these, to my surprise didn't enforce any data integrity. So I could have any value in one table that didn't exist in the id column of another. I wasn't happy about this. There had to be some way to stop this from happening. After many searches on Google, I found that it's possible to add validation to the model before data is inserted into the database:

class Site < ActiveRecord::Base
   belongs_to :category

   def validate
      errors.add_to_base "Error description" unless Category.exists?(category_id)
   end
end

Which did just what I wanted. Every row that was inserted into the sites table, would check that the category Id existed in categories and fail if it wasn't valid.

However, there's an even better way (as I see it at the moment). RedHill Consulting have created a Rails plugin (http://www.redhillconsulting.com.au/rails_plugins.html) which adds a foreign key to the database when you rake. All you have to do it run these two commands after making sure that SVN is installed on your computer (OSX users go here: http://www.codingmonkeys.de/mbo/):

script/plugin install svn://rubyforge.org//var/svn/redhillonrails/trunk/vendor/plugins/schema_defining

script/plugin install svn://rubyforge.org//var/svn/redhillonrails/trunk/vendor/plugins/foreign_key_migrations

Then, each time you migrate, the foreign keys are added to the database. I've only tried this using MySQL for now but from what I think I read, it should work for others too.

Discuss.

June 4, 2006

New Newbie

Filed under: Uncategorized — Richard @ 11:07 pm

Thanks to HittingTheBuffers who has let me post, I'll be adding my Rails findings and hopefully helping out anyone else who's just as stuck as me.

Blog at WordPress.com.