Maven, JRuby and Rails Migrations
20/07/2009
Here’s how I managed to get Rails Migrations working with a Maven build process, enabling me to leverage Migrations to maintain the RDBMS schema of a Java application.
Add JRuby and Database dependencies
Add the following dependencies to your pom.xml (adjust for whatever is latest version of jruby and whatever your database is).
1
2
3
4
5
6
7
8
9
10
<dependency>
<groupId> org.jruby</groupId>
<artifactId> jruby-complete</artifactId>
<version> 1.3.0RC1</version>
</dependency>
<dependency>
<groupId> oracle</groupId>
<artifactId> jdbc</artifactId>
<version> 11.1.0</version>
</dependency>
Add a goal to install required Ruby gems
To get Rails migrations running we’ll need the following gems:
activerecord
activerecord-jdbc-adapter
your database specific jdbc adapter
We’ll set up a profile to install these gems if they are missing (based on a approach used by Binil Thomas ):
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
<profiles>
<profile>
<id> first.time</id>
<activation>
<file>
<missing> ${user.home}/.gem/jruby/1.8/gems/activerecord-2.3.2</missing>
</file>
</activation>
<build>
<plugins>
<plugin>
<groupId> org.codehaus.mojo</groupId>
<artifactId> exec-maven-plugin</artifactId>
<executions>
<execution>
<id> install-active-record-gem</id>
<phase> initialize</phase>
<goals>
<goal> java</goal>
</goals>
<configuration>
<mainClass> org.jruby.Main</mainClass>
<arguments>
<argument> -S</argument>
<argument> gem</argument>
<argument> install</argument>
<argument> activerecord</argument>
<argument> activerecord-jdbc-adapter</argument>
<argument> activerecord-oracle_enhanced-adapter</argument>
<argument> --no-ri</argument>
<argument> --no-rdoc</argument>
<argument> --no-test</argument>
</arguments>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
</profiles>
Replace activerecord-oracle_enhanced-adapter
with the name of your chosen database’s jdbc adapter.
Add a goal to run the migration
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
<build>
<plugins>
<plugin>
<groupId> org.codehaus.mojo</groupId>
<artifactId> exec-maven-plugin</artifactId>
<executions>
<execution>
<id> run-migrate</id>
<phase> install</phase>
<goals>
<goal> java</goal>
</goals>
<configuration>
<mainClass> org.jruby.Main</mainClass>
<arguments>
<argument> -S</argument>
<argument> rake</argument>
<argument> -f</argument>
<argument> ${basedir}/Rakefile</argument>
</arguments>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
Create a Rakefile
You’ll need a Rakefile to carry out the migration, in my case I wanted to avoid depending on all of Rails so I just used the following:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
require 'active_record'
require 'yaml'
RAILS_ROOT = " #{ File . dirname(__FILE__)} " unless defined?(RAILS_ROOT )
task :default => :migrate
task :migrate => :environment do
ActiveRecord :: Migrator . migrate('db/migrate' , ENV [ "VERSION" ] ? ENV [ "VERSION" ]. to_i : nil )
end
task :environment do
ActiveRecord :: Base . establish_connection(YAML :: load(File . open(" #{ RAILS_ROOT } /config/database.yml" )))
ActiveRecord :: Base . logger = Logger . new(File . open('database.log' , 'a' ))
end
Write your migrations
Create your migrations in db/migrate
.
Apply database changes
Finally type:
to deploy your database changes.
The full POM
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
<project>
<modelVersion> 4.0.0</modelVersion>
<groupId> org.example</groupId>
<artifactId> schema</artifactId>
<name> Example POM for doing Rails Migrations</name>
<packaging> pom</packaging>
<dependencies>
<dependency>
<groupId> org.jruby</groupId>
<artifactId> jruby-complete</artifactId>
<version> 1.3.0RC1</version>
</dependency>
<dependency>
<groupId> oracle</groupId>
<artifactId> jdbc</artifactId>
<version> 11.2.0</version>
</dependency>
</dependencies>
<build>
<plugins>
<plugin>
<groupId> org.codehaus.mojo</groupId>
<artifactId> exec-maven-plugin</artifactId>
<executions>
<execution>
<id> run-migrate</id>
<phase> install</phase>
<goals>
<goal> java</goal>
</goals>
<configuration>
<mainClass> org.jruby.Main</mainClass>
<arguments>
<argument> -S</argument>
<argument> rake</argument>
<argument> -f</argument>
<argument> ${basedir}/Rakefile</argument>
</arguments>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
<profiles>
<profile>
<id> first.time</id>
<activation>
<file>
<missing> ${user.home}/.gem/jruby/1.8/gems/activerecord-2.3.2</missing>
</file>
</activation>
<build>
<plugins>
<plugin>
<groupId> org.codehaus.mojo</groupId>
<artifactId> exec-maven-plugin</artifactId>
<executions>
<execution>
<id> install-active-record-gem</id>
<phase> initialize</phase>
<goals>
<goal> java</goal>
</goals>
<configuration>
<mainClass> org.jruby.Main</mainClass>
<arguments>
<argument> -S</argument>
<argument> gem</argument>
<argument> install</argument>
<argument> activerecord</argument>
<argument> activerecord-jdbc-adapter</argument>
<argument> activerecord-oracle_enhanced-adapter</argument>
<argument> --no-ri</argument>
<argument> --no-rdoc</argument>
<argument> --no-test</argument>
</arguments>
</configuration>
</execution>
</executions>
</plugin>
</plugins>
</build>
</profile>
</profiles>
</project>