« November 2008 | Main | March 2009 »

February 2009 Archives

February 17, 2009

instant jruby & derby enviroment für eine RoR Anwendung

Als angestammter Java-Entwickler geht es mir oftmals schwer von der Hand, einer Ruby on Rails (RoR) Anwendung mit relativ wenig Auffand eine brauchbare Laufzeit-Umgebung zu bieten.
Normalerweise sollte das OS (MacOS 10.5.6) alles Brauchbare bieten. So ist oftmals ein Rails installiert und auch das (standardmäßig genutzte) SQlite 3 ist vorhanden.

Dennoch sind es oftmals Plugins (spezielle Rails Version / spezielle gems), welche einen zusätzlichen Aufwand benötigen.
Nicht zu vergessen, dass RoR nicht auf allen Systemen vorinstalliert ist und dementsprechend ein interessierter Entwicklung von einem Out-of-the-Box Erlebnis weit entfernt ist.
Sehen wir den Tatsachen ins Auge... die Wahrscheinlichkeit eine installierte JVM vorzufinden ist (noch?) deutlich höher, als eine Lauffähige Ruby-Installation.
Was liegt also näher, als die benötigte Umgebung auf Java fußen zu lassen.

Hierzu werden verwendet:

* jRuby in Version 1.1.5 (http://jruby.codehaus.org)
* Derby-DB in Version 10.4.2.0 (http://db.apache.org/derby)
* weiterhin wird eine installierte JVM (>1.5) vorrausgesetzt

Alles weitere wird mit Hilfe von shell-Scripten bewerkstelligt. Wobei momentan nur Unix-Scripte benutzt werden. Eine Portierung auf Windows sollte aber nur eine Sache von Minuten sein.

Es liegt eine RoR-Anwendung in einem Entwicklungs-Status vor. Diese wurde bisher in einem Netbeans-Enviroment mit einer SQlite-DB betrieben.

Das Verzeichnis ist folgendermaßen aufgebaut:

ROOT
|
|- microblog (dies ist unsere RoR-Anwendung)
|
|- derby (derby-installtion - es werden jeweils das bin und lib Verzeichnis benötigt)
| |-bin
| |-lib
|
|- jruby (jruby-installtion - es werden jeweils das bin und lib Verzeichnis benötigt)
| |-bin
| |-lib
|

Das Hauptproblem besteht darin, dass alle benötigten gems in das entsprechende Unterverzeichnis installiert werden müssen.
Weiterhin muss die Derby-DB mit dem entsprechenden Rake-Task auf mit der aktuellen Schema-Datei instanziiert werden.
Zuletzt sollen die vorhandenen User-Daten in die Derby-DB eingefügt werden.

Punkt 1)
Anpassen der database.yml
Wir nutzen weiterhin eine jdbc-Connection. Allerdings ändert sich der Treiber auf den der Derby-DB:

database.yml


development:
adapter: jdbc
driver: org.apache.derby.jdbc.ClientDriver
url: jdbc:derby://localhost/microblog_development;create=true
encoding: utf8
pool: 5
username: microblog
password: microblog
host: localhost

Punkt 2)
Export der alten DB-Daten:
Wir benutzen hierzu das Tool sqlitebrowser (http://sqlitebrowser.sourceforge.net) und erzeugen uns so einen SQL-Dump der alten SQLite-DB. Wir benutzen hierbei nur die SQL-Inserts für den User-Import. Diese speichern wir in die Datei:

microblog/db/microblog.sql

Punkt 3)
Für den Import erstellen wir einen Rake-Task:

microblog/lib/tasks/sql-import.rake


namespace :microblog do
desc 'Import old SQL Data'
task :sqlimport => :environment do
dbConn = ActiveRecord::Base.establish_connection :development
sql = File.open("db/microblog.sql").read
sql.split(';').each do |sql_statement|
dbConn.connection.execute(sql_statement)
end
puts "imported user data '#{Time.now}' "
end
end

Punkt 4)
Erstellen des Setup-Scriptes:
Folgende Schritte sind notwendig:

1. setzen aller benötiger Verzeichnisse
2. installieren aller benötigter gems
3. starten des Derby-DB-Servers
4. Rake db:migrate
5. import der alten Daten
6. beenden des Derby-DB-Servers

Das Script sieht wie folgt aus:

jruby-setup.sh


#!/bin/sh

BASE_DIR=`pwd`
CP=".:$BASE_DIR/jruby/lib/*:$BASE_DIR/derby/lib/derbyclient.jar"
JAVA_OPTS="-Djdbc.drivers=org.apache.derby.jdbc.EmbeddedDriver"
JRUBY="$BASE_DIR/jruby/bin/jruby"

DERBY_HOME=`cd derby && pwd`
export DERBY_HOME=$DERBY_HOME
cd $BASE_DIR

echo "setting up jgems..."
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem update --system
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem install jruby-openssl --no-rdoc --no-ri
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem install -v=2.2.2 rails --no-rdoc --no-ri
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem install activerecord-jdbc-adapter activerecord-jdbcderby-adapter --no-rdoc --no-ri

echo "starting derby..."
$BASE_DIR/derby/bin/startNetworkServer &

echo "setting up derby..."
cd microblog
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/rake db:migrate
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/rake microblog:sqlimport
cd $BASE_DIR

echo "stopping derby..."
$BASE_DIR/derby/bin/stopNetworkServer &

Es ist zu erwähnen, dass es notwendig ist, jeweils auf die entsprechende jRuby-Installation zu verweisen.
Weiterhin benötigt jRuby den entsprechenden derbyClientDriver, welcher in die (von jRuby später verwendete) JAVA_OPTS-Variabel eingetragen wird.
Ebenfalls musst der Classpath soweit angepasst werden, dass sowohl jRuby, als auch Derby über die notwendigen Bibliotheken verfügen.
Als letztes ist noch erwähnenswert, dass die beiden Rake-Tasks jeweils aus dem App-Verzeichnis ausgeführt werden.

Punkt 5)
Das Start-Script.
Letzendlich sind auch zum eigentlichen Betrieb des Servers Anpassungen notwendig, da auch hier die jRuby-Instanz mit den verwendeten gems benutzt werden sollen.
Das Script sieht wie folgt aus:

run.sh


#!/bin/sh
BASE_DIR=`pwd`
CP=".:$BASE_DIR/jruby/lib/*:$BASE_DIR/derby/lib/derbyclient.jar"
JAVA_OPTS="-Djdbc.drivers=org.apache.derby.jdbc.EmbeddedDriver"
JRUBY="$BASE_DIR/jruby/bin/jruby"
export BASE_DIR=$BASE_DIR
export JRUBY=$JRUBY

DERBY_HOME=`cd derby && pwd`
export DERBY_HOME=$DERBY_HOME
cd $BASE_DIR


echo "starting derby..."
$BASE_DIR/derby/bin/startNetworkServer &

echo "setting up derby..."
cd microblog
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/rake db:migrate

echo "starting microblog"
$BASE_DIR/jruby/bin/jruby $BASE_DIR/microblog/script/server

echo "stopping derby..."
$BASE_DIR/derby/bin/stopNetworkServer &

Es entspricht also einer abgespeckten Variante des Setup-Scriptes. Hierbei wird auch immer ein db:migrate aufgerufen, für den Fall, dass sich die DB-Struktur in der Zwischenzeit geändert haben sollte.

Punkt 6)
Auslieferung ;-).
Derby und jRuby belegen knapp 80 MB sodass es notwendig ist, die Dateigröße für den Transport zu verringern.
Zuallererst sollten die benötigten gems am besten immer online bezogen werden, sodass man hier ein paar MB sparen kann.
Weiterhin benutzen wir Jar um die vorhandenen Dateien auf ein 13 MB-Archiv zu packen.

Die veränderten Scripte sehen wie folgt aus:

Zuerst das Script, welches die vorhandenen Dateien packt:

pack.sh


#!/bin/sh
find . -name '*.DS_Store' -type f -delete
jar -cvf statusQ-runtime.jar derby/ jruby/ run.sh pack.sh microblog/db/microblog.sql microblog/lib/tasks/sql-import.rake
rm -R jruby
rm -R derby
rm run.sh
rm microblog/db/microblog.sql
rm microblog/lib/tasks/sql-import.rake
rm pack.sh

Und nun das geänderte jruby-setup.sh Script, welches vor dem eigentlichen Setup noch für das Entpacken aller Dateien verantwortlich ist:

jruby-setup.sh


#!/bin/sh
jar -xvf statusQ-runtime.jar
rm -R META-INF
chmod +x run.sh
chmod +x setup.sh
chmod +x pack.sh
chmod +x jruby/bin/jruby
chmod +x derby/bin/startNetworkServer
chmod +x derby/bin/stopNetworkServer

BASE_DIR=`pwd`
CP=".:$BASE_DIR/jruby/lib/*:$BASE_DIR/derby/lib/derbyclient.jar"
JAVA_OPTS="-Djdbc.drivers=org.apache.derby.jdbc.EmbeddedDriver"
JRUBY="$BASE_DIR/jruby/bin/jruby"

DERBY_HOME=`cd derby && pwd`
export DERBY_HOME=$DERBY_HOME
cd $BASE_DIR

echo "setting up jgems..."
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem update --system
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem install jruby-openssl --no-rdoc --no-ri
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem install -v=2.2.2 rails --no-rdoc --no-ri
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/jgem install activerecord-jdbc-adapter activerecord-jdbcderby-adapter --no-rdoc --no-ri

echo "starting derby..."
$BASE_DIR/derby/bin/startNetworkServer &

echo "setting up derby..."
cd microblog
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/rake db:migrate
$BASE_DIR/jruby/bin/jruby $BASE_DIR/jruby/bin/rake microblog:sqlimport
cd $BASE_DIR

echo "stopping derby..."
$BASE_DIR/derby/bin/stopNetworkServer &

Als nächstes sollte die Scripte auf Windows portiert werden.
Weiterhin wäre es interessant, die Derby/jRuby Binaries jeweils direkt online zu beziehen.

Das Problem mit der Abstraktion der Arbeit

Aus aktuellem Anlass möchte ich mich hier einem Thema widmen, welches möglicherweise jeden betrifft. Es geht um die Tatsache, dass man um sich herum Projekte und Arbeit sucht, welche sich über die Zeit ansammelt und mit der Zeit liegen bleibt. Es gibt viele Theorien und Methoden, wie man dieser Situation begegnen soll. Meistens geht es um - mehr oder weniger - hippe Methoden mit noch trendigeren Namen (z.B. GettingThingsDone). Sucht man nach dem Thema Arbeitsmethoden oder Zeitmanagement, finden sich ganze Bücherregale mit Titeln, unterschiedlicher Ausrichtung.

Dennoch habe ich mir persönlich die Frage gestellt, wieso man viele Dinge anfängt, nach einiger Zeit zurückblickt und zu dem Ergebnis kommt, dass man doch zum aktuellen Zeitpunkt weit von einem (dem) gesteckten Ziel entfernt ist, welches man eigentlich hat erreichen wollen. Ich spreche hier nicht von den typischen Kandidaten wie "Ich sollte mal wieder den Keller aufräumen", oder auch "Irgendwie sollte ich mal wieder die Steuern machen :-(". Es geht mir hier um die vielen kleineren und größeren Projekte, die man sich (und hin und wieder auch zusammen anderen Mitmenschen) vor langer Zeit gestellt hat und die trotz vieler Möglichkeiten daniederliegen und meist über das erste Planungsstadium nicht hinweg gekommen sind.

Ich möchte nachfolgend ein paar Punkte nenne, die ich an mir selber (als quasi Betroffener), hin und wieder aber auch bei anderen (als unbeteiligter Beobachter), bemerkt habe:


1. Titelgebend und meiner Meinung nach einer der seltsamsten Gründe - Abstrahierung des Probemes:
Ich habe lange Zeit überlegt, ob Abstrahierung überhaupt der richtige Begriff ist. Letztendlich ist damit gemeint, dass man ab einem gewissen Punkt erkennt, dass man das gesetzte Ziel rein theoretisch sicher und zu 100% erreichen kann. Dies mag zum einen Daraus resultieren, dass man in dem Arbeitsumfeld schon einiges an Erfahrung gesammelt hat, zum anderen auch daran, dass man im Beruf oder in anderen Situationen schon schwierigere/komplexere Dinge gelöst hat. So werden viele Aufgaben vor sich her geschoben und im Team werden simple, unerfreuliche, langweilige, aber notwendige Aufgaben an Unerfahrende Helfer abgeschoben, weil das eigene Genie sich für höheres berufen fühlt. Während man selber also nur mit dem Kopf die Dinge löst und selber fest der Meinung ist, dass die Verwirklichung der eigenen Ideen nur noch Detailfragen aufwerfen wird, wird man hinterher von dem langsamen Fortschritt und einer fehlerhaften Basis überrascht werden.
2. Das "Ich mache lieber alles selbst, weil es sonst falsch ist, oder zu lange dauert" - Problem.
3. "Keine Zeit - das mache ich dann mal, wenn ich (Frei-)Zeit habe" / "sobald X eintritt, mache ich das mal"
4. "Lasst uns die Wikipedia nachbauen"
5. "Das sieht so simpel aus - das kann ich auch"

February 23, 2009

sophisticated Backups mit Rsync Part II

Version 3.1 Features:
  • Logs werden nun gzip komprimiert
  • wöchentliche Backups aus der vorherigen Woche werden tar.gz komprimiert
Download startbackup-3.1.sh
Blogged with the Flock Browser

About February 2009

This page contains all entries posted to Philipps paper equivalent Blog in February 2009. They are listed from oldest to newest.

November 2008 is the previous archive.

March 2009 is the next archive.

Many more can be found on the main index page or by looking through the archives.

Powered by
Movable Type 3.31