Rails Installation Festival

Wolltest du schon immer mal Rails ausprobieren, aber bist irgendwie nie dazugekommen das ganze überhaupt zu installieren? Dafür gibts eine Lösung, geh einfach am Mittwoch, 26. November, an den RailsHock, dort kannst du dich mit anderen Neulingen und Alten Hasen austauschen.

Mehr dazu bei Georg, dem Chef des ganzen.

Ach ja, noch etwas mehr Werbung: Rails 2.2 ist erschienen.

2 comments »

Eu falo português

InfoQ wird seit wenigen Wochen von einem brasilianischen Team ins portugiesische übersetzt, und auch mein neuster Beitrag ist schon übersetzt:

Nach Chinesisch und Japanisch nun also die vierte Sprache, in der man InfoQ lesen kann, womit die Weltherrschaft kurz bevorsteht. :-)

2 comments »

XSel, dict.leo.org und KDialog vereint

Mein Bruder hat mir von diesem sehr praktischen Progrämmchen namens XSel erzählt, welches die X-Selektion verändern kann.

Damit lassen sich lustige Dinge anstellen:

require 'open-uri'
require 'hpricot'
require 'iconv'

word = `xsel`.split(" ").first

exit 1 unless word =~ /\w+/

doc = Hpricot(open("http://dict.leo.org/ [...] search=#{word}"))

translation = doc/"table[@id=results]"

translation.search("img").remove

translation.search("a") { |a| a.swap(a.innerHTML) }

(translation.search("tr")[20..-1] || []).each { |e| e.swap("") }

translation = Iconv.conv("UTF-8", "ISO-8859-1", translation.to_s)

translation.gsub!("'", "&#x#{?'.to_s(16)};")

`kdialog --passivepopup '#{translation}'`

(die Leo-URL musste ich aus Layoutründen hier kürzen)

Ok, was macht das? Es holt sich das erste Wort aus der X-Selektion und holt sich dafür die Uebersetzung von dict.leo.org. Danach noch etwas Kosmetik am HTML, Encoding verändern, Anzahl Einträge beschränken, böses Zeichen ersetzen und dann mit kdialog –passivepopup darstellen. Das Ergebnis sieht dann so aus:

Das Script habe ich mir auf die ThinkVantage-Taste gelegt, per Selektion und Knopfdruck kriege ich jetzt als die Uebersetzungen direkt auf den Bildschirm.

Wer lust hat, kann mit dem Leo-Script machen was er will, gewidmet sei es meinem gleichnamigen Kollegen, auch wenn es ihm wahrscheinlich nicht viel nützt.

No comment »

Ruby Quine

Ich hab mich mal an einem Quine in Ruby versucht:

def print a
  puts a, "print %s(#{a})"
end
print %s(def print a
  puts a, "print %s(#{a})"
end)


Ist zwar nicht das kürzeste, aber dafür lesbar.

Sonst noch jemand? Fürs ausprobieren empfehle ich: ruby q.rb | diff -u q.rb -

Bonusfrage: Welches Buch lese ich im Moment wohl? :-)

No comment »

Weg mit Java?

Ich bin mal wieder etwas im Rückstand mit Computer (das IEEE Magazin) lesen, und ehrlich gesagt blättere ich es meistens einfach durch. Ab und zu findet man aber auch sehr interessante Dinge, wie in der Juli Ausgabe unter dem Titel In Praise of Scripting: Real Programming Pragmatism:

To me, Java-based CS1 is the single greatest mistake in the history of computing curricula. Students should learn to love their own possibilities before they learn to loathe other people’s restrictions.

Students who learn to script early are empowered throughout their college years, especially in the crucial Unix and Web environments. Those who learn Java and C++ first are stifled by enterprise-sized correctness. Early programmers must learn to be creative and inventive, and they need programming tools that support exploration rather than production.

Recht hat er!

Interessant ist auch, welche Sprachen er verwenden würde:

What scripting language could be used for CS1? [..] an emerging consensus in the scripting community holds that Python is the right solution for freshman programming. Ruby would also be a defensible choice.
Python and Ruby have the enviable properties that almost no one dislikes them, and almost everyone respects them.

Also los, kippen wir Java aus Programmieren 1 und 2. Aber wohin damit? Vielleicht zusammen mit C++ ins Programmieren 3? Oder vielleicht nach Ruby zuerst C++ lernen, denn wenn man C++ und Ruby verstanden hat, sollte Java eigentlich kein Problem mehr sein. Oder?

4 comments »

SMS senden leicht gemacht (Orange)

Gibt es was mühsameres, als die unsäglichen Browser-SMS-Versende-Dienste unserer Mobilfunkanbieter? Naja, wahrscheinlich gibt es schlimmeres, aber verbessern kann man es ja trotzdem. Das Ziel ist, möglichst einfach SMS zu versenden, also schreiben wir doch ein Script, welches als Parameter Nummer und Text entgegennimmt und versendet.

Ist eigentlich ganz einfach, Mechanize mimt einen Browser und macht genau das, was auch ein Mensch tun würde, also anmelden, Formularfelder ausfüllen und abschicken:

#!/usr/bin/ruby
require 'mechanize'

username = 'mirkostocker'
password = 'XXXXXXXXXXXX'
number   = ARGV.shift
message  = ARGV * " "

if message.length > 144 || message.length < 1
  $stderr.puts "Nachricht zu lang oder zu kurz.."
  exit 1
end

def find_form_with_field(page, fieldname)
  page.forms.each do |form|
    if form.fields.find{|f| f.name == fieldname}
      yield form
    end
  end
end

WWW::Mechanize.new do |agent|

  agent.get('https://www.orange.ch/footer/login') do |page|

    find_form_with_field(page, 'username') do |f|
      f.username = username
      f.password = password
      f.submit
    end
  end

  agent.get('https://www.orange.ch/myorange/sms') do |page|

    find_form_with_field(page, 'messageInput') do |f|
      f.destinationNumberInput = number
      f.messageInput = message
      f.wui_target_id = 'sendButton'
      f.wui_event_id = 'onclick'
      f.submit
    end
  end
end


find_form_with_field musste ich schreiben, da die Formulare keine Namen besitzen, und fragt mich nicht, weshalb ich wui_target_id und wui_event_id setzen muss, im echten Browser wird das per Javascript gemacht und ist anscheinend wichtig. Hat auch gleich die Projektdauer um 50% verlängert, auf rund 1.5 Stunden.

So, und wer kümmert sich um die Swisscom und Sunrise?

Guido: Wie du siehst habe ich einen netten Weg gefunden, bunten Code zu bloggen, der beste Editor der Welt hat nämlich eine TOhtml Funktion.

6 comments »

Imap-Feeder: RSS und Atom Feeds nach IMAP

Imap-Feeder ist ein Programm, welches eine Reihe von Feeds abklappert und die Einträge als E-Mails auf einem IMAP Server ablegt.

Warum?

Mein Problem, das ich lösen wollte war, dass ich meine Feeds an mehreren Orten lesen will (also am Arbeitsplatz, am PC zu Hause und auf mindestens einem Laptop), das ist aber ziemlich mühsam weil man von Hand die bereits gelesenen Einträge verwalten muss. Und bei rund 50 Feeds ist das ziemlich nervig.

“Browser-basierte Feedreader” höre ich es schon rufen. Sorry, aber ist für mich keine Alternative. Ich kann mich mit Browser-basierten Anwendungen einfach nicht anfreunden – bin wohl von KDE zu sehr verwöhnt was Desktop-Applikationen und Interoperabilität anbelangt. Ausserdem bin ich nicht immer Online (jaja, Google Gears..).

Die Lösung: IMAP

Eigentlich gibt es ja schon eine sehr bewährte Technologie um Mail-ähnliche Daten aufzubewahren: IMAP. Von beliebig vielen Clients kann ich auf meinen IMAP Account zugreifen, und mit Cached- oder Offline-IMAP stehen die Daten auch immer zur Verfügung. Der Unterschied zwischen einer E-Mail und einem Eintrag in einem Feed sind eigentlich auch nicht so gross: Beide besitzen einen Betreff und einen Inhalt; bei Feeds kommt teilweise noch ein Autor sowie ein Timestamp dazu.

Vorteile

  • Mehrere Clients können ohne Probleme zugreiffen, wenns sein muss kann man immer noch einen Webmail-Client nutzen.
  • Einträge können wie E-Mails behandelt werden, man kann sie also mit speziellen Tags versehen, an andere Leute weiterleiten, archivieren, verschieben, durchsuchen und so weiter.
  • Man (oder zumindest ich als Entwickler) habe die volle Kontrolle, in welcher Form die Einträge abgelegt werden. Dadurch lassen sich eine Erweiterungen realisieren, wie beispielsweise:
    • Aenderungen an bereits vorhandenen Einträgen: Neu hinzufügen oder ignorieren?
    • Filtern von Einträgen, wenn man blog.misto.ch nicht mag und trotzdem den Planet-HSR abonnieren möchte.
    • Minderwertige Feeds aufwerten: Man könnte durch einen CSS oder XPath-Ausrucke beispielsweise die News von heise.de scrapen und direkt als Body einfügen.
    • … (nehme gerne neue Ideen entgegen).

Nachteile

Es gibt auch Nachteile, man braucht natürlich einen Server, welcher das imap-feeder Skript regelmässig laufen lässt.

Imap-Feeder

Momentan sind noch nicht alle oben genannten Features implementiert, auch gibt es keine HTML-Mails: der HTML-Code von Feeds wird mit ein paar simplen Regeln in Text umgewandelt. Mein Beitrag zu GitHub sieht dann so aus:

Ich hätte noch Einladungen für GitHub[1] zu vergeben (FCFS), falls jemand eine will. Einfach mit einer E-Mail-Adresse bei mir melden.

Wer mer über GitHub erfahren will, kann ja mal hier[2] weiterlesen.

[1] http://github.com/
[2] http://www.infoq.com/news/2008/03/github-git-repository-hosting

http://blog.misto.ch/archives/551

Die Links werden alle gesammelt und am Schluss dargestellt, um den Lesefluss nicht zu stören.

Das ganze ist in Ruby geschrieben und kann von der offiziellen Website bezogen werden. Installation und Einrichtung sind eigentlich ziemlich simpel.

Zukunft

Als nächstes werde ich wohl noch einige der oben genannten Features implementieren oder vervollständigen; HTML-Mails könnten durchaus praktisch sein für Einträge mit Bildern.

5 comments »

Truly Beautiful Code [updated]

In einer Sitzung heute kamen wir auf das Thema Beautiful Code zu sprechen, und natürlich auch auf das gleichnamige Buch. Bei InfoQ-Kollege Stefan Tilkov habe ich gerade ein wirklich schönes Stück Ruby-Code gesehen:

fib = Hash.new{ |h, n| n < 2 ? h[n] = n : h[n] = h[n - 1] + h[n - 2] }
puts fib[15]

Nicht wahr?

Update, 23. Mai

Ok, ich hätte vielleicht etwas mehr erklären sollen was da genau abgeht. Dazu kann man das ganze etwas schöner schreiben:

fib = Hash.new{ |h, n| h[n] = h[n - 1] + h[n - 2] }
fib[0] = 0
fib[1] = 1
puts fib[15]

Hash.new nimmt einen Block entgegen, welcher jeweils aufgerufen wird, wenn ein Element nicht im Hash vorhanden ist. Wenn also fib[15] evaluiert wird, kommt unser Block zum Zug, welcher dann das aktuelle Element bestimmt, wobei das ganze wieder von vorne beginnt, und zum Schluss im Hash ablegt. Schön daran ist, dass jede Zahl nur einmal berechnet wird, Memoization kriegt man also fast umsonst.

No comment »

Ich kann Chinesisch und Japanisch!

Könnte man zumindest meinen, wenn man sich folgende Artikel anschaut:

Japanisch:

Chinesisch:

Tja, schön wärs, ich verstehe leider kein Wort..

5 comments »

Gelesen: Practical Ruby Projects

Im WK hat man ja üblicherweise genug Zeit totzuschlagen, trotzdem hat es in den bisherigen drei Wochen bloss für ein Buch gereicht, nämlich Practical Ruby Projects, Ideas for the Eclectic Programmer.

In acht Kapitel wird jeweils ein (eigentlich erstaunlich umfangreiches) Programm geschrieben. Dabei geht es vom rundenbasierten Strategiespiel mit GUI über genetische Algorithmen bis zum Lisp-Interpreter.

Sehr interessant fand ich den Münz-Simulator, ein Programm, welches anhand von typischen Wechselgeldsituationen und Münzsystemen erprobt, welche Werte in Münzen vorhanden sein müssten, um immer möglichst wenig Wechselgeld herumzutragen. Cool, nicht? In einem System mit 4 verschiedenen Münzen wären 1, 3, 13 und 31 optimal um das Gewicht zu reduzieren. Mit drei Münzen wären 1, 7 und 24 oder 1, 13 und 18 nicht schlecht. Netter Nebeneffekt: Die Leute könnten wieder Kopfrechnen :) . Die Problemstellung wird schrittweise angegangen und mit dem Leser zusammen erarbeitet. Dabei werden auch verschiedene Probleme und Lösungen gezeigt, wie beispielsweise Memoization für den Brute-Force Algorithmus.

Das Buch hat mir sehr gut gefallen, der Code im Buch ist sehr schön und die Erklärungen sind sehr verständlich. Trotzdem muss man konzentriert lesen, ein Buch für Anfänger ist es sicherlich nicht. Die Frage ist, was es einem nützt, so ein Buch zu lesen? Neue Ideen für Projekte habe ich eigentlich nicht bekommen, aber das Lesen hat Spass gemacht und war ein guter Zeitvertreib. Durch die relativ unabhängigen Kapitel kann man gut mal ein Thema innerhalb einer zweistündigen Schicht auf der Wache lesen.

No comment »