Assert statement in Objective C

Hi,
if you like to use assertions in your source code, but you miss this feature in ObjectiveC, give a look to this small class.
Assert.h

  1. #import <Foundation/Foundation.h>
  2. @interface Assert : NSObject {
  3. }
  4. +(void)that:(BOOL)expr;
  5. @end

Assert.m

  1. #import "Assert.h"
  2. @implementation Assert
  3. +(void)that:(BOOL)expr{
  4.  if (!expr) {
  5.   [NSException raise:@"Failed assertion." format:@"Failed assertion", nil];
  6.  }
  7. }
  8. @end

As you can see, there’s only one static method that you can use wherever you want.
In this snippet here’s an example how to use it.

  1. #import "Assert.h"
  2. -(void)doSomething{
  3.  [Assert that:(<your_assertion>)];
  4. }

Ruby on CentOS

In these days I’m trying to install Ruby on Rails on our CentOS production server. What I really don’t like very much about CentOS are its pretty outdated packages installable via yum. This time proved to be the same… it’s seems that the Ruby available on CentOS via yum is a version released during 2006.
In the first place I tried to compile Ruby from sources, but this proved a little too much messy for me. In the end I stumbled upon Ruby Enterprise Edition and I gave it a try.
What I liked most about it was that it worked perfectly just out of the box and that all Ruby files go inside a single directory, so it’s pretty easy to move from a version to another even if not using yum.
This is a brief tutorial about how to install Ruby Enterprise Edition on CentOS.

Get rid of any Ruby previously installed

First of all let’s remove any Ruby installation already present on our CentOS.
We can ask Yum to give us a list of Ruby related packages currently installed.

  1. yum list | grep installed | grep ruby

My server answered that way, but obviously yours can show other answers.

  1. ruby.i386 1.8.5-5.el5_3.7 installed
  2. ruby-devel.i386 1.8.5-5.el5_3.7 installed
  3. ruby-libs.i386 1.8.5-5.el5_3.7 installed
  4. ruby-mode.i386 1.8.5-5.el5_3.7 installed

Time to gently ask to Yum to remove all those Ruby packages.

  1. yum erase ruby
  2. yum erase ruby-devel
  3. yum erase ruby-libs
  4. yum erase ruby-mode

We can now start with the Enterprise Ruby installation.

Download and install Enterprise Ruby

There is really nothing deeply interesting here. Just download the sources, unpack them, compile them and set some useful links.

  1. mkdir -p ~/Temp/Sources
  2. cd ~/Temp/Sources
  3. wget http://rubyforge.org/frs/download.php/68719/ruby-enterprise-1.8.7-2010.01.tar.gz
  4. tar xzvf ruby-enterprise-1.8.7-2010.01.tar.gz
  5. ./ruby-enterprise-1.8.7-2010.01/installer

At the end we should have a working Ruby installation.
Let’s create some useful link.

  1. ln -s /opt/ruby-enterprise-1.8.7-2010.01/bin/rake /usr/bin/rake
  2. ln -s /opt/ruby-enterprise-1.8.7-2010.01/bin/gem /usr/bin/gem
  3. ln -s /opt/ruby-enterprise-1.8.7-2010.01/bin/rails /usr/bin/rails
  4. ln -s /opt/ruby-enterprise-1.8.7-2010.01/bin/ruby /usr/bin/ruby
  5. ln -s /opt/ruby-enterprise-1.8.7-2010.01/bin/irb /usr/bin/irb

Worth reading

Cristian Livadaru’s blog post about the topic.
Install the available Ruby via Yum
Enterprise Ruby download page

Database testing with Mono and NUnit

In these days I’m trying to rewrite an old application using Mono.
I’m currently a newbie about Mono and the .Net world, but I happily noticed that the Mono environment come with a bundled interface to NUnit, so I can keep on writing tests as I’m slowly but steadily getting used to.
After having put together a bunch of classes and relative and unit tests, it was time to write the first integration test. I needed to put the development database in a known state before running the test, so I came up with the following class, that I’d like to share with you.

  1. using System;
  2. using System.Collections;
  3. using NUnit.Framework;
  4. using System.IO;
  5. using System.Data;
  6. using System.Data.SqlClient;
  7. namespace TellItMailer{
  8.  public class TestDbSetup{
  9.   public void SetUpDbForTest(object test){
  10.    String path = test.GetType().FullName + ".sql";
  11.    path = path.Replace(this.GetType().Namespace + ".", "");
  12.    path = "/home/danidemi/workspace/TellItMailer/Tests/" + path;
  13.    //Read the script
  14.    String script = "";
  15.    using (StreamReader sr = File.OpenText(path)){
  16.     string s = "";
  17.                while ((s = sr.ReadLine()) != null){
  18.      script = script + s;
  19.                }
  20.           }
  21.  
  22.    string connectionString =
  23.     "Server=192.168.75.128\\SQLEXPRESS;" +
  24.     "Database=TellIt_test;" +
  25.              "User ID=user;" +
  26.              "Password=password;";
  27.  
  28.           IDbConnection dbcon;
  29.    using(dbcon = new SqlConnection(connectionString)){
  30.     dbcon.Open();
  31.            using (IDbCommand dbcmd = dbcon.CreateCommand()) {
  32.                dbcmd.CommandText = script;
  33.      dbcmd.ExecuteNonQuery();
  34.     }
  35.    }
  36.   }
  37.  
  38.  }
  39. }

It’s quite useful. Essentially this class loads a SQL script file whose name is the same of the test class, and execute it.
In this way you have for example a TestFeature.cs file alongside a TestFeature.sql file. Nice if your IDE shows files sorted alphabetically.
I found that the best place to use the class is inside the SetUp marked method. In this way the SQL script is run before each test. Doing it in a local development environment is not so bad, since the scripts are executed at high speed.

So, this is an example of how a test that uses TestDbSetup looks like.

  1. using System;
  2. using NUnit.Framework;
  3. using log4net;
  4. using log4net.Config;
  5. namespace TellItMailer {
  6.  [TestFixture()]
  7.  public class IntegrationTest {
  8.   [SetUp]
  9.   public void SetUp(){
  10.    new TestDbSetup().SetUpDbForTest(this);
  11.   }
  12.  
  13.   [Test]
  14.   public void TestCase(){
  15.    BasicConfigurator.Configure();
  16.   }
  17.  }
  18. }

Pretty useful, IMHO.

Obtain the root logger programmatically in log4net

If you use log4net, you could have the need to configure the loggers programamtically. The problem arise when you want access to the root logger, since the documentation does not explain well how to obtain it.
So, here’s a snippet that show how to do it. Don’t forget to imort the log4net namespaces.

  1. using log4net;
  2. using log4net.Core;
  3. using log4net.Appender;
  4. using log4net.Layout;
  5. using log4net.Repository.Hierarchy;
  6. using log4net.Config;
  1. Hierarchy h = (Hierarchy)log4net.LogManager.GetRepository();
  2. Logger rootLogger = h.Root;

Good environment variable values during iPhone development

Directly from GHUnit, a small note about which environment variables to set while developing for the iPhone.

Environment Variable:                 Default:  Set to:
NSDebugEnabled                           NO       YES
NSZombieEnabled                          NO       YES
NSDeallocateZombies                      NO       NO (or YES)
NSHangOnUncaughtException                NO       YES
NSAutoreleaseFreedObjectCheckEnabled     NO       YES

Actually, I keep forgetting them, so I hope this will be useful to me.

Here an example that shows how to set those environment variables.

Setting iPhone development variables in XCode