Montag, 22. Februar 2010

So einfach vergeht einem die Lust am Schreiben

Da sich bei Twitter gerade mal wieder gewisse Tendenzen anbahnen, muss ich dahingehend mir mal meinen Frust von der Seele schreiben.

Während meine Studiums musste ich immer wieder umfangreichere Dokumente anfertigen: Berichte, Dokumentationen, Hausarbeiten. All diese Dokumente hatten einen gewissen Qualitätsanspruch. So sollten sie natürlich ein Inhaltsverzeichnis haben, eine Seitennummerierung, ggf. ein Deckblatt, vielleicht auch noch ein Quellen- und/oder Abbildungsverzeichnis. Eigentlich kein Problem für eine moderne Textverarbeitung, sollte man meinen. Leider aber ist es das doch. Ich habe das Schreiben solcher Dokumente immer gehasst.

Begonnen hat meine "Textverarbeitungskarriere" natürlich mit dem Klassiker, Microsoft Word. 1989 (!) verwendete ich schon Microsoft Word 4 unter MS-DOS 3.2 auf einem 8086. Das Programm ließ sich flott bedienen, ich konnte meine Texte für die Schule damals problemlos verfassen. Weiter ging es mit Word 6.0 unter Windows. Die nachfolgenden Office-Versionen nahm ich alle mit: Office 95, 97, 2000, XP, 2003. Bei meinem Wechsel zum Mac im Jahre 2005 versuchte ich eine Weile, die vorinstallierte Trial des MS Office 2004 for Mac zu verwenden. Zufrieden war ich aber nie, weswegen ich OpenOffice.org und iWork eine Chance gab. Das OpenOffice.org war mir eindeutig zu langsam, iWork wurde das Programm der Wahl, wenn auch Pages nicht so ganz mit dem Funktionsumfang von Word oder Writer mithalten kann. Und genau deswegen versuchte ich immer wieder, mit dem OpenOffice.org Writer, gelegentlich sogar mit Microsoft Word, umfangreiche, komplexe Dokumente zu setzen. Es ist ein Graus. Ich meine, ich gebe Schulungen in Word, ich kenne das Programm ziemlich gut, eine flüssige Arbeit, sofern es nicht nur um das Verfassen von Briefen geht, ist aus meiner Sicht nicht möglich. Zu viele Inkonsistenzen, Abstürze, verlorene Informationen. Ich persönlich finde das neue UI des Office 2007 nicht schlecht, viele Anwender fühlen sich aber von Microsoft vor den Kopf gestossen, was der Verwendung des OpenOffice.org in der Wirtschaft einen ziemlichen Boost gegeben hat.

Vor einigen Monaten nahm ich mir dann ein Herz. Ich installierte eine LaTeX-Distribution auf meinem Mac und startete TextMate. Das erste Dokument startete ich mit einer Vorlage, die TextMate mir anbot, um erst mal einen Einstieg zu finden. Und ich war begeistert. Wer HTML lesen und schreiben kann, der kann quasi auch LaTeX, die Konzepte sind verflucht ähnlich. Und der Textsatz. Ich fand das Schriftbild, das Word und Konsorten produzieren schon immer furchtbar hässlich. LaTeX macht das so viel besser, der Text ist gut lesbar, sieht wunderschön aus. Und das Beste: ich muss mich nicht händisch um das Setzen von Inhaltsverzeichnissen, Seitenzahlen, etc. kümmern. Hat man erst einmal eine Vorlage geschaffen, muss man sich nie (!) wieder um solche Elemente kümmern. Die Einarbeitungszeit ist natürlich abhängig vom technischen Verständnis des Anwenders, die typische Sekretärin, ohne den Berufsstand verunglimpfen zu wollen, mag damit anfangs überfordert sein, technisch versiertere Menschen hingegen dürften binnen weniger Stunden mit dem System klar kommen.

LaTeX führt eine sehr strikte Trennung zwischen Inhalt und (Text-)Satz durch, die anfangs gewöhnungsbedürftig ist. Ein vernünftiger Texteditor unterstützt einen aber in der Arbeit und nimmt einem vieles ab. Windows-Nutzer sollten also bitte nicht auf das Notepad zurückgreifen, damit dürfte einem ziemlich schnell der Spaß vergehen. Unter Mac OS kann ich ganz klar eine Empfehlung für TextMate aussprechen, unter Linux (Gnome) empfiehlt sich Gedit und unter Windows sollte man vermutlich zum NotePad++ greifen.

Jedem meiner Leser, der immer wieder mit dem Verfassen komplexer Dokumente betraut wird, kann ich die Einarbeitung in LaTeX nur empfehlen. Eine gute Quelle für den Einstieg ist meiner Meinung nach http://latex.mschroeder.net/. Solltet ihr nur Briefe schreiben müssen, kann ich die Verwendung von LaTeX weder empfehlen noch davon abraten. Der schönere Textsatz allein dürfte aber Grund genug für die Einarbeitung in dieses System sein.

Posted via email from ulfklose's posterous

Sonntag, 7. Februar 2010

Rails-Applikationen mit nginx und Thin

Wer Rails-Applikationen deployen möchte, wird vermutlich als erstes auf die Kombination Apache + Phusion Passenger stossen. So ging es auch mir. Praktisch insofern, da auf fast jedem Webserver ohnehin ein Apache läuft und der Passenger in Windeseile installiert ist. Beim Passenger handelt es sich um ein Apache-Modul (mod_rails), die Konfiguration in einem vHost ist ein Dreizeiler. Also eigentlich alles toll... wenn da nicht die Geschwindigkeit wäre. Wenn der Passenger erst mal läuft, ist die Geschwindigkeit durchaus als gut zu bewerten, aber wehe, wenn die fragliche Rails-Applikation eine Weile nicht mehr benutzt wurde. Dann werden die Passenger-Instanzen meiner Beobachtung nach nämlich vollständig abgeschossen und müssen neu gestartet werden, wenn doch wieder auf die Applikation zugegriffen wird. Auf meinem Server (AMD Athlon64 X2 5.600+, 4 GB RAM, 2 x 400 GB HDD im RAID-1; drei virtuelle Maschinen) dauert das mitunter ca. 20 - 30 Sekunden und macht in dieser Zeit die komplette VM unbenutzbar, andere Webseiten werden also nicht mehr ausgeliefert, der SSH-Daemon reagiert nicht.

Seit ich angefangen habe, mich mit Rails zu beschäftigen, lese ich einige Blogs von Firmen, die sich "hauptberuflich" mit Rails auf die eine oder andere Art und Weise beschäftigen. Dazu gehören unter anderem amerikanische Unternehmen wie Engine Yard [1], Rackspace[2] und GitHub[3]. In Deutschland ist Rails leider noch immer nicht so recht angekommen, die Anzahl wirklich interessanter, innovativer Unternehmen in diesem Bereich hält sich also stark in Grenzen. Die soeben genannten Unternehmen betreiben entweder für sich selbst oder im Kundenauftrag große Rails-Installationen und können sich solche Probleme, wie die im vorherigen Absatz geschilderten, absolut nicht erlauben. Insbesondere Engine Yard und GitHub betreiben viel Social Networking und haben sehr aktive gepflegte Blogs. Und in diesen bin ich auf so einige interessante Informationen gestossen, unter anderem auch mein Problem betreffend.

Wenn man eine Applikation in Rails entwickelt, verwendet man während der Entwicklungsphase der Einfachheit halber einen sehr rudimentären kleinen Webserver namens WEBrick. Er tut das, was er tun soll, startet schnell, eignet sich für den Produktbetrieb aufgrund fehlender Sicherheitsfeatures und ziemlich mauer Performance nur bedingt. Alternativ kann man Mongrel nutzen. Auch dieser ist fest mit Rails verbunden, bietet aber deutlich mehr Performance als WEBrick. Mongrel existiert auch in einer speziellen Cluster-Version. Mit Clustering ist hiermit gar nicht mal das verteilte Rechnen auf verschiedenen Systemen gemeint, sondern nur die Tatsache, dass mehrere Instanzen gestartet werden können. Dies ist ein im Rails-Bereich meinen Informationen nach ein übliches Setup. Es ist einfach aufzusetzen und Mongrel genügt für die meisten Zwecke. Aber Mongrel ist nun mal kein Apache und steht diesem in seinen Konfigurationsmöglichkeiten massiv nach. Einen reinen Mongrel-Cluster zu betreiben scheint also auch kein probates Mittel zu sein.

Nach dem Studium einiger Blog-Artikel entschied ich mich dann für den Toolstack, um den es hier gehen soll: nginx und Thin. nginx[4] als voll-funktionalen Webserver mit wenig Ressourcenhunger und Thin[5] als Application Server. Thin beschreibt sich selbst als die optimale Kombination aus dem Mongrel parser, Event Machine (einer Netzwerk-I/O-Bibliothek) und Rack (Minimal-Interface zwischen Webserver und Ruby-Applikation). Dieser Toolstack begeistert mich noch immer, ob er das auch unter wirklicher Last tun würde, kann ich (noch) nicht sagen, ich werde dann berichten.

Nun zur Installation.

Der erste Schritt sollte die Installation des entsprechenden Gems (und eines zugehörigen) sein. Mittels

sudo gem install thin; sudo gem install eventmachine --source http://code.macournoyer.com

installieren wir Thin. Um zu testen, ob alles in Ordnung ist, nehmen wir einen Verzeichniswechsel in zu unserer Rails-Applikation vor und tippen

thin start

ein. Es sollten ein paar Statusmeldungen ausgegeben werden, danach könnt ihr über http://domain.tld:3000 eure Rails-Applikation aufrufen. Sollte Thin nicht starten, was bei mir der Fall war, müsst ihr Thin noch zu eurer PATH-Variable hinzufügen. Thin liegt auf meinem Server (Ubuntu 9.04 Server) im Verzeichnis

/var/lib/gems/1.8/bin

Stellt sicher, dass dieser Eintrag als allererster in der PATH-Variable steht. Ich habe zu diesem Zweck meiner ~/.bashrc einfach am Ende folgende Zeile hinzugefügt:

export PATH=/var/lib/gems/1.8/bin:$PATH

Da das aber nicht das ist, was wir wollen, installieren wir nun nginx. Ich habe mich dafür entschieden, die aktuelle Stable aus dem Source Code zu kompilieren. Ein Blick auf http://nginx.org/en/download.html zeigt uns alle verfügbaren Versionen. Ich arbeite aktuell mit Version 0.7.65. Nach dem Download mittels

wget http://nginx.org/download/nginx-0.7.65.tar.gz

entpacken wir das Archiv mit

tar xvfz nginx-0.7.65.tar.gz

in das aktuelle Verzeichnis. In dieses Verzeichnis wird nun gewechselt. Ich habe meinen nginx mit den folgenden Optionen kompiliert:

 
./configure \
--prefix=/usr \
--conf-path=/etc/nginx/nginx.conf \
--http-log-path=/var/log/nginx/access_log \
--error-log-path=/var/log/nginx/error_log \
--pid-path=/var/run/nginx.pid \
--http-client-body-temp-path=/var/tmp/nginx/client \
--http-proxy-temp-path=/var/tmp/nginx/proxy \
--http-fastcgi-temp-path=/var/tmp/nginx/fastcgi \
--with-md5-asm --with-md5=/usr/include \
--with-sha1-asm \
--with-sha1=/usr/include \
--with-http_realip_module \
--with-http_ssl_module \
--with-http_stub_status_module

Der abschließende Build und die Installation erledigen wir so:

make && make install

Nun geben wir noch

sudo thin install && sudo /usr/sbin/update-rc.d -f thin defaults

um Thin automatisch starten zu lassen.

Weiter geht es mit der Konfiguration.

Konfigurieren wir als erstes Thin für den Live-Betrieb:

sudo thin config -C /etc/thin/railsapp.yml -c /var/www/railsapp --servers 2 --socket /var/run/thin/railsapp.sock -e production

Dieser Einzeiler legt im Verzeichnis /etc/thin/ eine Konfigurationsdatei im YAML-Format mit dem Namen railsapp.yml an. In dieser Datei wird festgehalten, wie Thin arbeiten soll. In diesem konkreten Falle wird, was sehr empfehlenswert ist, eine Socket- anstelle einer TCP/IP-Verbindung verwendet. Es werden zwei Serverinstanzen gestartet, die parallel laufen. ACHTUNG! Wer hier die Zahl zu hoch wählt, macht es seinem Server ganz schnell ganz schwer. Also vorsichtig erhöhen und nur, wenn es unbedingt nötig ist. Bemerkt man einen Flaschenhals, kann man hier natürlich rumschrauben. Das Hauptverzeichnis der Rails-Anwendung ist in diesem Falle /var/www/railsapp und die Sockets werden in /var/run/thin/ angelegt. Der letzte Schalter legt noch die Rails-Environment fest, hier wird also das Production Environment genutzt.

Die Konfiguration von nginx ist recht simpel. Meine /etc/nginx/nginx.conf sieht wie folgt aus:

  
user www-data;
worker_processes 2;
error_log /var/log/nginx/error.log;
pid /var/run/nginx.pid;
events {
worker_connections 1024;
# multi_accept on;
}
http {
include /etc/nginx/mime.types;
access_log /var/log/nginx/access.log;
sendfile on;
#tcp_nopush on;
#keepalive_timeout 0;
keepalive_timeout 65;
tcp_nodelay on;
gzip on;
gzip_disable "MSIE [1-6]\.(?!.*SV1)";
include /etc/nginx/conf.d/*.conf;
include /etc/nginx/sites-enabled/*;
}

Als Systembenutzer setzt dieses Setup einen Benutzer mit dem Namen www-data voraus. Außerdem werden zwei Worker-Prozesse gestartet. Wer in seiner Rails-Anwendung eine Benutzerverwaltung einsetze, sollte natürlich auf https anstelle von http setzen. Wie man einen https-Container mit nginx einrichtet, werde ich gesondert an dieser Stelle beschreiben.

Im Verzeichnis /etc/nginx/sites-available legen wir nun einen vHost-Container für unsere Rails-Anwendung an. Dieser sollte einen sprechenden Namen als Dateinamen erhalten, also bspw. railsapp.domain.tld. Bei mir sieht der Inhalt wie folgt aus:

  
upstream railsapp {
server unix:/var/run/thin/railsapp.0.sock;
server unix:/var/run/thin/railsapp.1.sock;
}
server {
listen 80;
server_name railsapp.domain.tld;
access_log /var/www/railsapp/log/access.log;
error_log /var/www/railsapp/log/error.log;
root /var/www/railsapp/public/;
index index.html;
location / {
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header Host $http_host;
proxy_redirect off;
if (-f $request_filename/index.html) {
rewrite (.*) $1/index.html break;
}
if (-f $request_filename.html) {
rewrite (.*) $1.html break;
}
if (!-f $request_filename) {
proxy_pass http://railsapp;
break;
}
}
}

Mittels

ln -s /etc/nginx/sites-available/railsapp.domain.tld /etc/nginx/sites-enabled/railsapp.domain.tld

legen wir einen Symlink in das Verzeichnis sites-enabled an. In diesem befinden sich alle vHost-Container, die nginx bedienen soll.

Nun starten wir noch nginx und Thin neu

sudo /etc/init.d/nginx restart; sudo /etc/init.d/thin restart

Gebt Thin ein paar Sekunden, um wirklich antworten zu können. Danach sollte eure Rails-Anwendung über Port 80 ausgeliefert werden.

Sollte ich beim Erstellen dieser Anleitung einen Fehler gemacht haben, lasst es mich bitte wissen, möchte ja keine falschen Informationen im Netz publizieren.

[1] http://www.engineyard.com/
[2] http://www.rackspace.com/
[3] https://github.com/
[4] http://wiki.nginx.org/Main
[5] http://code.macournoyer.com/thin/

Posted via email from ulfklose's posterous

Mittwoch, 3. Februar 2010

Git und der Mac

Ich arbeite nun schon geraume Zeit, ungefähr ein halbes Jahr, mit Git. Wissen vielleicht einige schon, da ich, ebenfalls vor einer Weile, eine Installationsanleitung für den eigenen Git-Server publiziert habe.

Nun möchte ich aber ein paar Worte der Client-Seite widmen, in meinem Falle also der Verwendung von Git unter Mac OS X. Wirkliche Probleme gibt es dabei nicht, nur einige "nice-to-knows", die ich an dieser Stelle kurz zusammenfassen möchte. Sollte einem meiner Leser noch etwas fehlen, so möge er es über die Kommentare hinzufügen ;-). Danke schon mal.

1. Installation

Den Installer habe ich bei Google code gefunden: http://code.google.com/p/git-osx-installer/. Damit ist die Installation ein Klacks. Auf meinem System mit Mac OS 10.6 Snow Leopard musste ich aber noch einen kleinen Hack anwenden, damit auch tatsächlich die aktuelle Version aus diesem Installer verwendet wird. Das liegt daran, dass Mac OS, wie jedes andere UNIX auch, die PATH-Variable linear durchsucht und den ersten Treffer verwendet. Auf meinem System war es nun leider so, dass ich eine alte Version von Git unter /usr/local/bin liegen hatte, die neue Version aber unter /usr/local/git/bin liegt. Verwendet hat Mac OS immer die alte Version, da die PATH-Variable den Pfad zur neueren Git-Version als erstes auflistete.

Um das Problem zu beheben, habe ich die Datei

/etc/profiles

editiert (sudo nano /etc/profiles), die die globale PATH-Variable beinhaltet. Bei mir sieht die entsprechende Zeile wie folgt aus:

export PATH=/usr/bin:/bin:/usr/sbin:/sbin:/usr/local/git/bin:/usr/local/bin:/usr/texbin:/usr/X11/bin

Somit sucht Mac OS nun zuerst nach der aktuellen Version. Andere Mac-OS-Installer von Git mögen die Binarys von Git woanders ablegen, der korrespondierende Pfad müsste dann entsprechend angepasst werden.

2. Konfiguration

Eine weitergehende Konfiguration von Git ist eigentlich nicht erforderlich, als sinnvoll haben sich aber einige Variablen herausgestellt. Folgende Kommandos habe ich für meine Git-Konfiguration verwendet:

2.1 Benutzerkonfiguration

git config --global user.name "Vorname Nachname"
git config --global user.email "user@domain.tld"

Diese Kommandos setzen die entsprechenden Git-Einstellungen global für den Systembenutzer. Diese sind somit für alle Repositorys eures Systembenutzers gültig. Abgelegt werden die Einstellungen in der Datei ~/.gitconfig. Um die Einstellungen spezifisch für ein Repository zu überschreiben, könnt ihr folgende Befehle verwenden:

git config user.name "Vorname Nachname"
git config user.email "user@domain.tld"

Diese Einstellungen werden in der Datei .git/config in eurem Repository-Verzeichnis abgelegt und sind somit auch nur für das jeweilige Repository gültig.

Es ist durchaus sinnvoll, diese Variablen zu setzen, da nur so gewährleistet ist, dass eure Commits eindeutig euch zugeordnet werden können. Diese Einstellungen können im Übrigen unabhängig von eventuellen Benutzern auf eurem Git-Server gesetzt werden.

2.2 Konfiguration der Ausgabe

Um die Ausgaben von Git farbig zu gestalten, müsst ihr folgendes eintippen:

git config --global color.ui "auto"

Auch hier gilt wieder, dass der Schalter --global die Einstellungen global setzt.

2.3 Weitere Einstellungen

Um Git für die Verwendung von Multi-Core-CPUs zu konfigurieren, folgenden Befehl eingeben:

git config --global pack.threads "0"

Um Apples opendiff für die Anzeige von diffs zu verwenden:

git config --global merge.tool opendiff
git config --global merge.summary true

.DS_Store-Dateien vom Repository ausschliessen:

git config --global core.excludesfile ~/.gitignore
echo ".DS_Store" >>~/.gitignore

Textmate als Standard-Editor setzen:

git config --global core.editor "mate -w"

2.4 Github-spezifische Einstellungen

Damit die geniale Social-Coding-Plattform GitHub (https://github.com) euren Benutzer korrekt erkennt, müssen zwei weitere Einstellungen gesetzt werden:

git config --global github.user
git config --global github.token

Eure entsprechenden Daten findet ihr unter https://github.com/account.

2.5 Textmate-Bundle

Für die Textmate-User unter euch gibt es im Übrigen ein Git-Bundle, welches wie folgt installiert werden kann:

mkdir -p ~/Library/Application\ Support/TextMate/Bundles
cd !$
git clone git://github.com/jcf/git-tmbundle Git.tmbundle
osascript -e 'tell app "TextMate" to reload bundles'

In Textmate müsst ihr nun noch die Shell-Variable TM_GIT erstellen. Diese muss (in meinem Falle) auf /usr/local/git/bin zeigen.

Wie gesagt, sollte irgendwo noch etwas wichtiges fehlen, lasst es mich bitte über die Kommentare wissen.

Posted via email from ulfklose's posterous