The code was not much to look at. We mostly rspec’d a few methods and learned that just because you ‘def to_s’ doesn’t mean the implicit string conversion uses it!
I think the real issue we uncovered was that the implicit string conversion produces escaped string and calling #to_s produces unescaped strings.
Ruby Gems we used to setup the environment.
heredocs — we talked about how to produce heredocs You can either use multi-line double-quoted, or <<-eot
text = <<-eot
This is the heredoc text
It can even include evaluations #{Time.now} !!
eot
More about heredocs : http://blog.jayfields.com/2006/12/ruby-multiline-strings-here-doc-or.html
A windows-implementation of textmate : http://www.e-texteditor.com/
The Ruby Way — Hal Fulton
http://www.google.com/url?sa=t&source=web&ct=res&cd=1&ved=0CAwQFjAA&url=http%3A%2F%2Fwww.amazon.com%2FRuby-Way-Second-Techniques-Programming%2Fdp%2F0672328844&ei=OuLwSsj_PIa1tgf59N26Cw&usg=AFQjCNHhpmT3C35Xiianfordqb21_DsWIA&sig2=Pb631QnepV_sAD8wmRuPTA
The Rails Way — Obie Fernandez
http://www.google.com/url?sa=t&source=web&ct=res&cd=3&ved=0CBYQFjAC&url=http%3A%2F%2Fwww.amazon.com%2FRails-Way-Obie-Fernandez%2Fdp%2F0321445619&ei=V-LwSunCEYeVtgfWib26Cw&usg=AFQjCNGpPcvEJDxIOGEwWZZIp9HXnbPC0A&sig2=0ofdwEJfrMOm7U3bR7c5OQ
The Rails Way Blog therailsway.com
Enumerable Module
In this chapter, I’ll discuss the adapter initialization; how Rails 2.x reads from database.yml and launches the database initialization.
Here is a condensation of the Rails boot process from Rails Guts. As Mike Gunderloy suggests, it will be really helpful to have a blank rails app open with
rake gems:freeze
invoked :
Rails::Initializer.run do |config|
configuration = Configuration.new
(that’s Rails::Configuration in railties/lib/initializer.rb)
self.database_configuration_file = default_database_configuration_file
def default_database_configuration_file File.join(root_path, 'config', 'database.yml') end
def initialize_database if configuration.frameworks.include?(:active_record) ActiveRecord::Base.configurations = configuration.database_configuration ActiveRecord::Base.establish_connection end end
def database_configuration require 'erb' YAML::load(ERB.new(IO.read(database_configuration_file)).result) end
gem "activerecord-#{spec[:adapter]}-adapter"
and execute the adapter-method (which is expected to be def’d from the adapter’s gem) :
adapter_method = "#{spec[:adapter]}_connection"
The adapter-method is the entry-point of our new adapter, so in my next post I’ll pick-apart the #establish_connection process and prepare for our multi-connection pooling adapter’s version.
Well, I don’t know how many parts this will have… so lets just say 5 until I re-edit the introduction.
Thomas Edison told us how to invent. So let’s get to it. The Adapter we’ll build will assist in handling the problem of database-failover in Rails 2.3.2 applications
Seamless Database Pool gem provides us with a template to follow. The SDP is focused purely on connection logic. The true db adapter is used within the pool connections. Our Adapter, like SDP, will simply serve as a proxy to handle the event when an ActiveRecord method (#select, #create, #update, #delete) encounters a DatabaseConnectionError.
Ok, we’re going to have to work for it this time. Event though we have SDP as a template, there is A LOT of logic in there that is really not useful to us. SDP is a load-balancing pool based upon a weighted one-write/many-read database cluster / replication group.
Ahh, the real meat of our cookout.
In my next post, we’ll start with #1 Configure Master + Slavees in database.yml
I recently completed configuration of continuous-integration between two servers.
Here’s the steps and notes that I have for the move.
The system of servers/services comes together like this :
Git and Redmine run on server ‘redmine-server’, which is a CentOS 5 Intel box. OpenSSH is installed, Redmine runs on Ruby 1.8.7, yum package install.
User on this server is ‘git’
Cerberus runs on an OSX box named ‘ci-server’, Leopard.
Ruby on this box is installed using ruby-switcher, with 1.8.7p173 and 1.9.1p129r23412.
My customization of that ruby-switcher is here ruby_switcher.sh.
User on this server is ‘cerberus’
The Git repository lives on a different server, so SSH is employed to protect passwords-cleartext over the wire.
There is an additional constraint in that Git hooks are “non-interactive”, so ssh keys must be configured to not challenge. There are [security implications] to this. The option I have chosen is passwordless “backup keys” for specific purposes.
git@redmine-server $ ssh-keygen -t rsa -C git_ci_server@redmine_server Generating public/private rsa key pair. Enter file in which to save the key (/home/git/.ssh/id_rsa): \ .ssh/id_rsa_git_ci_server Enter passphrase (empty for no passphrase): Enter same passphrase again: Your identification has been saved in .ssh/id_rsa_git_ci_server. Your public key has been saved in .ssh/id_rsa_git_ci_server.pub. The key fingerprint is: 42:62:16:4c:00:74:7c:a9:96:90:5a:75:5d:08:c5:f9 git_ci_server@redmine_server
Move the key to the target server ci-server
[git@redmine-server]$ scp .ssh/id_rsa_git_ci_server.pub \ cerberus@ci-server:id_rsa_git_ci_server.redmine-server
Password:
id_rsa_git_ci_server.pub 100% 410 0.4KB/s 00:00
[git@redmine-server]$ ssh deployer@web-ci Password:
Last login: Mon Jun 15 09:20:00 2009 from redmine-server [cerberus@ci-server]$ cat id_rsa_git_ci_server.redmine-server ssh-rsa AAAAB3NzaC1yc2EAAAABIwAAAQEAtOVHRlhLmUI/9XglQs6u9F1reUwAq2U0clJI2l j5kAX5XkVW7FoiiGo4BfAqP3j69ynMBnLx/eUtcYcxHUKZfikwQbXnUdAUd8mIXoNhOfVZ/gqr i0yS0XHpkGU2lJve3soqEIyYu2gxf5QPP18ibJeyFZ5QRTPUATfi1c6Pb12tsr4O9H+b5T08cU ejvQP5ISyYH3ysPZwLQ3d1Ods9ZItm7h9/eoZQxgXpVLxUkQ3NO+JoktKlruGajTRgm5xP7NBd gUZsC2vs84/mW64RWSzbl8fA5oKUhKQIDt7QSOGx2UVGYAoarFGTsvps5g9WnXTJ37XRT+ORHI cpmO90mQ== git_ci_server@redmine_server [cerberus@ci-server]$ cat id_rsa_git_ci_server.redmine-server >> .ssh/authorized_keys [cerberus@ci-server]$ exit
From ‘man ssh’ :
-i identity_file
Selects a file from which the identity (private key) for RSA or DSA authentication is read. The default is
~/.ssh/identity for protocol version 1, and ~/.ssh/id_rsa and ~/.ssh/id_dsa for protocol version 2. Identity files
may also be specified on a per-host basis in the configuration file. It is possible to have multiple -i options
(and multiple identities specified in configuration files).
This Git server does not have ssh-agent running, so using -i will cause the indicated file to be the only identity used in the ssh session.
Now test the login using the backup-key switch of ’ssh’
[git@redmine-server]$ ssh -i .ssh/id_rsa_git_ci_server cerberus@ci-server Last login: Mon Jun 15 10:53:38 2009 from redmine-server [cerberus@ci-server]$
The backup-key switch will be used in the Git post-receive hook for executing Cerberus build upon Git Push
Simple. Use ssh to call a build script on ci-server, which we’ll build after the break…
#!/bin/sh # # An example hook script for the post-receive event # # This script is run after receive-pack has accepted a pack and the # repository has been updated. It is passed arguments in through stdin # in the form # <oldrev> <newrev> <refname> # For example: # aa453216d1b3e49e7f6f98441fa56946ddcd6a20 68f7abf4e6f922807889f52bc043ecd31b79f814 refs/heads/master # # see contrib/hooks/ for an sample, or uncomment the next line (on debian) # ssh -i ~/.ssh/id_rsa_git_ci_server cerberus@ci-server \ bin/cerberus-build racc-webapp
NOTE: the use of the -i switch
This hook is applied to each repository that will be monitored by Cerberus Continuous Integration. It must be made executable so Git will execute it!
[git@redmine-server]$ cp post-receieve repos/my_app/.git/hooks/post-receive [git@redmine-server]$ chmod +x repos/my_app/.git/hooks/post-receive
Using the ruby-switcher, install the ruby of your choice (’install_ruby_187p173′). The use it (’use_ruby_187′).
Install cerberus gem (note we are using local gem storage to accomodate ruby-switcher):
[cerberus@ci-server]$ gem install cerberus
Configure cerberus globals, especially email server config (for SMTP send).
I also configured the builder/rake to handle new migrations (Rails 2.3) and Rspec (rake spec)
[cerberus@ci-server]$ cat .cerberus/config.yml
publisher:
# active: mail jabber rss campfire
mail:
address: smtp.test.com
port: 25
domain: test.com
authentication: :none
sender: Cerberus CI <cerberus@test.com>
# address: smtp.gmail.com
# port: 587
# domain: gmail.com
# authentication: plain
# user_name: someuser
# password: somepassword
# on_event: all
# jabber:
# jid: somemailbox@gmail.com/cerberus
# password: somepassword
# twitter:
# login: twitter_username
# password: twitter_password
# irc:
# nick: cerb
# server: irc.freenode.net
# channel: cerberus
# campfire:
# url: http://someemail:password@cerberustool.campfirenow.com/room/51660
# rss:
# file: /usr/www/rss.xml
builder:
rake:
task: db:migrate spec
#changeset_url: POINT_TO_YOUR_TRAC/changeset/
#hook:
# rcov:
# on_event: successful, setup #by default - run hook for any state
# action: 'export CERBERUS_HOME=/home/anatol && sudo chown www-data -R /home/anatol/cerberus && rcov' #Add here any hook you want
Configure the cerberus project. Note how the config points back to the repository
[cerberus@ci-server]$ cerberus add git@redmine-server:my_app/.git \ APPLICATION_NAME=my-app SCM=git
Edit the configuration of the project to add project-level mailing addresses. The BUILD WILL FAIL WITHOUT THIS!!!
[cerberus@ci-server]$ cat .cerberus/config/my-app.yml
---
publisher:
mail:
recipients: someuser@test.com
scm:
url: git@redmine-server:repos/my_app/.git
type: git
An initial build ‘cerberus build my-app’ is required to set the sources. This one will likely fail, as it is necessary to configure non-SCM files like ‘database.yml’.
You should receive email from “Cerberus CI” declaring your failure.
You have completed config. Now FIX YOUR BROKEN CHECKIN FTW!!
I could go into great detail… but I’m beat. Creating the dev environment from the ground up was a lot of work. I also needed to get some project details under way.
Here is what I needed to get Features and Specs to load up the library properly
Create a cucumber.yml. This is necessary to set the default profile, which I wanted to get a little more pretty printing during the cucumber command.
In a step definition (grid_steps.rb), I needed the $LOAD_PATH to point to the lib, so I added the following to the top of support/env.rb
$:.unshift File.expand_path(File.dirname(__FILE__) + "/../../lib")
Also support RSpec expectations/matchers within the steps, so
require 'spec/expectations'
Update the $LOAD_PATH here from a different location in the tree than features, from ./spec
$:.unshift File.expand_path(File.dirname(__FILE__) + "/../lib")
In order to get cucumber integrated with autotest, add this to cucumber.yml
autotest: --format pretty features autotest-all: --format pretty features
Also autospec requires an environment switch, which I have added to ./bashrc for convenience
export AUTOFEATURE=true
With all the prettyness set up with cucumber and RSpec, we now have a new color in the Red-Green cycle.
Cucumber Features’ Given/When/Then lines are displayed in Amber until each is properly trapped by a defined Given/When/Then in a steps definition file (./features/step_definitions/*.rb).
RSpec specs are displayed in amber if the spec is not defined (name only) like this
it "this spec is not defined yet"
Well, that’s about all I can handle for now.
I will make an attempt to trap the Amber-Red-Green cycle in git commits during my work tomorrow.
Here’s the entirement development environment for TicTacToe. This was actually rebuilt for this project as I deleted my last dev environment (A VirtualBox instance) during a system-repair process (wipe-drive-reinstall of Vista
This week I am starting a Tic Tac Toe Kata in response to a programming exercise by a future employer. (Wave to you!)
Here are my rules for performance of the kata:
And here is the kata:
What we have in mind is a simple Tic-Tac-Toe program.
At the least this program should:
We would like you to use Ruby as the programming language. (My Pleasure!)
So, in my next posting I’ll be into project setup, prerequisites, and the first story or two.
Update 3/17/09: Add RDoc to expected deliverables.
Yo All Followers.
This blog has had downtime and lost data due to my hosting provider’s server move and my own error in choosing a custom DNS config within my virtually-hosted node.
What does that mean to you?
I hope you all like to follow me again. More Ruby goodness up and coming.
Regards,
Pete the Ruby Evangelist.
Well, Jamie Cansdale has been getting heat over time from M$ over TestDriven.Net, formerly NUnitAddin.
M$ turned up the heat over the last week, and seemingly put it to HIGH yesterday.
Ian Ringrose simplified the discussion :
“Is it safe for me as a developer without a large legal department to work with Microsoft technology? “
FransBouma says : “Nail on the head.”
Yes… Nail on the head.
I’m debating between moving my career in one of two ways :
Study ruby on rails, leave Microsoft development, move my career in a new direction. I feel immediate happiness in this endeavor.
Study Microsoft Certified Professional Developer (MCPD) / .NET 2.0. Give in to “the state”, admit that a governmentally structured certification machine also has a thriving job market. Join a Microsoft Consulting Firm full time and be a valuable contributor to their technologies.
Updated: 20 June 2007 12:35:00. This rounds out the pro/con list to more clearly present my perspective on what direction to take my career.