Friday, March 5, 2010

Ruby 1.9.1 on Windows with Rails, MS SQL Server and Cucumber

 

Cucumber: For future reference, and time-saving, here is what we did.

 

 

Why wolud anybody use Ruby on Windows? With Microsoft SQL Server?

At the company where I work we decided to generate db integration tests. We need database model rock solid for new release we are planing soon. Our old db test system was based on pure SQL, and was working fine. but model itself got complex and SQL is far from what user wants to do and wants to see. We realized that we need test that is very close to what non-tech user is actually talking about, 

I did a small research and found Cucumber, and after a few tweaks we got excellent results.
For future reference, and time-saving, here is what we did.

In Ruby slang we "created rails project connecting activerecord with legacy database on MS SQL Server, using Cucumber for testing"

Let's go: Download Ruby 1.9.1 and install gems 

You can install from installer, but I'll start from plain 7zip file: 

http://rubyforge.org/frs/download.php/69039/ruby-1.9.1-p378-i386-mingw32.7z

Unzip it to C:\Ruby191, and make that dir accessible to all users. This is where all ruby files and gems will be located. 

Add C:\Ruby191\bin to your PATH. After that try these two commands: 

ruby --version
gem -v

If you get versions (1.9.x and 1.3.x), you are ready to start with basic gems:

gem install --no-rdoc --no-ri rails 
gem install --no-rdoc --no-ri database_cleaner factory_girl rspec rspec-rails cucumber cucumber-rails

You can now create a rails app, but be patient. We need to set a few more things.

Tricky part 1: Connecting to MS SQL Server from Ruby 1.9.1 

gem install --no-rdoc --no-ri activerecord-sqlserver-adapter

This will do on 1.8.6 and 1.8.7. But it is not enough for 1.9.1

For 1.9.1 to work you need to download this file (thanks to Cosimo Guglielmucci):

http://web.tiscali.it/mamva/ruby19-odbc-mswin32.zip

And unzip it to the C:\Ruby19\lib\ruby\1.9.1\i386-mingw32\ folder.

Now you can create a rails app, and connect it to MS SQL, but we still need to set a few more things.

Tricky part 2: RSpec on Windows and Ruby 1.9.1

RSpec gem relays on test-unit 1.2.3, but it will fail to load it if there is a newer one installed. 
Solution is simple. First find out which test-unit you have installed: 

gem list test-unit 

if there is no test-unit 1.2.3 or there are more versions installed: 

gem uninstall test-unit 
gem install test-unit -v 1.2.3

Tricky part 3: Cucumber on Windows and Ruby 1.9.1

Cucumber got it's name as "all green -> you are done", and it relays on colored console output. 

On windows that means that cucumber depends on win32console gem.
That gem fails on Ruby 1.9.1. But there is a soulution (thanks to Luis Lavena)

gem install win32console --prerelease

This command will install win32console beta version which works on 1.9.1 

If your console codepage is not 1252, you will have incorect output - eg. incredible "missing 'a' problem
Solution is to chenge your console code page: 

chcp 1252

Cucumber will also remember where it stopped with testing, but it saves path with backslashes on windows, and that backslash can trigger hard to spot errors (missing files, etc...). If you encounter such error just delete rerun.txt file in root of your project. 

Solution for this is to set enviroment variable: 

SET CUCUMBER_FORWARD_SLASH_PATHS=true 

 

Since Cucumber need enviroment variables and chcp, the best thing to do is to create batch file in root of your project:

 

191.bat

SET Path=%PATH%;C:\Ruby19\bin;

SET HOME=%HOMEDRIVE%%HOMEPATH%

SET GEM_BIN=C:\ruby19\bin 

SET CUCUMBER_OUTPUT_ENCODING=cp1252

SET CUCUMBER_FORWARD_SLASH_PATHS=true

 

 

 

 

chcp 1252

ruby --version

 

 

This will make Ruby and Cucumber happy. Open console, cd to your project and call 191.bat. 
In fact, I have 186.bat and 187.bat; each with its own gems. 

Create your rails project 

We are using rails since it ties activerecord, rspec and cucumber very nice. With lots of examples.
Please note that we are not making a website. Of course nothing stops you to do exacly that. 
Here is short command line tutorial: 

rails dbtest
cd dbtest
ruby script/generate cucumber

Database connection is set in config/database.yml It should look like this:

 

development:
  adapter: sqlserver
  dsn: WingsTest

test: &TEST
  adapter: sqlserver
  dsn: WingsTest

production:
  adapter: sqlserver
  dsn: WingsTest

cucumber:
  <<: *TEST

 

I created ODBC DSN  (Control Panel->Administrative Tools->ODBC) for my database connection.
Note that I'am using only one db, and you should use three if you are creating a website.

Tricky part 4: Legacy MS SQL Server database on Rails

First thing to notice is that activerecord expects lowercase table and field names. 
And our db is all uppercase. 

Fastest solution was to patch activerecord-sqlserver-adapter. Only thing changed was to insert LOWER(FIELD_NAME) in a few places where adapter fetches tablenames and field names metadata from SQL Server. The only file changed was:

C:\Ruby19\lib\ruby\gems\1.9.1\gems\activerecord-sqlserver-adapter-2.3.4\lib\active_record\connection_adapters\sqlserver_adapter.rb 

My patch is public. I forked activerecord-sqlserver-adapter on GitHub made change and published back my changes. You can get them from:

http://github.com/dmajkic/2000-2005-adapter

If you have legacy database, that is CaSE INsenSItiVE, you are welcome to use my fork.


Then I generated schema.rb with

rake db:schema:dump

If your connection is ok, you will get schema.rb file with all your tables.

Afther that we added activerecord model or two just to get started with cucumber.

That's it . 

If you are going to use Ruby for website development, you will need to follow more tutorials and go with installing more gems.

As for us, we now have a Cucumber "stage" set, and we are adding steps and scenarios as needed. 

Posted via web from dmajkic's posterous