Freitag, 29. Mai 2015

OSX-Notification beim Abbruch von SSH-Tunnel

Ein kleiner Trick wie man das Abbrechen eines SSH-Tunnels schneller bemerken kann.
Das kann beispielsweise praktisch sein, wenn man im Hintergrund einen SSH-Tunnel offen hat den man für Arbeiten im Vordergrund braucht.


Dazu folgenden Befehl ausführen:

ssh -N -L 80:localhost:80 serverx; terminal-notifier -message "SSH-Tunnel beendet"


Syntaktisch sind das bloss zwei nacheinander ausgeführte Shell-Befehle, die mit Semikolon ";" getrennt werden.

Mit Hilfe des Tools terminal-notififier kann man unter Mac OS X aus der Shell Notifications erzeugen.
Es lässt sich am Einfachsten per homebrew installieren.

terminal-notifier versteht noch einige zusätzliche Parameter:
  • -title Setzt den Titel
  • -subtitle Setzt einen Untertitel
  • -group Definiert eine Gruppen-ID
  • -open Öffnet beim Klick eine URL
  • -execute Führt beim Klick ein Shell-Kommando aus

Die Option "execute" liesse sich zum Beispiel nutzen um beim Klick auf die Notification gleich wieder eine neue SSH-Verbindung aufzubauen.

Dienstag, 19. Mai 2015

JSON Formatierung mit TextWranger

Im Rahmen der Arbeit mit REST APIs habe ich in letzter Zeit öfters mit JSON-Output zu tun gehabt.
Da ist es praktisch, wenn der Output bereits schön formatiert ist. Mit "schön" bezeichne ich JSON das richtig eingerückt ist.
Wenn der Output nicht schön eingerückt ist, so kann dies mit Text Wrangler leicht gelöst werden.

Dafür habe ich das Python-Script von Steve Windsberg neu in Ruby implementiert.
Als Bonus werden in dieser Implementierung die Keys nicht umsortiert sondern bleiben in der vorgegebenen Reihenfolge.

JSON Formatierung mit TextWrangler

Die Ruby implementierung ist kurz, sehr kurz.

require 'json'
data = ARGF.read
json = JSON.parse(data)
puts JSON.pretty_generate(json)


Das Script muss in ~/Library/Application Support/TextWrangler/Text Filters platziert werden und Zugriffsrechte für Execute (chmod u+x) haben.

Ein kleines Installer-Package als Download (2.8 KB) erledigt die Installation gleich komplett.

Montag, 11. Mai 2015

Programmierung eines Lightroom Plugins mit Lua

Motivation

In meinen letzten Ferien habe ich einige Time-Lapse-Videos erstellt.
Dazu habe ich meist iStopMotion verwendet. Es wird zwar nicht ausdrücklich dafür beworben, doch es erfüllt den Zweck. Man kann Fotos importieren, die Bild-Rate wählen und das Resultat dann als Video rendern.
Es gibt zwar noch Alternativen wie LRTimelapse (99 EUR) die viele nette Features bringen, doch die Bedienung und der Workflow wirken etwas umständlich.
Wenn es nur darum geht eine erste Ansicht eines Video zu erstellen wäre es schön, wenn es einfacher wäre.

Deshalb habe ich mich entschieden ein eigenes kleines Plugin namens "Video Renderer" für Adobe Photoshop Lightroom® zu schreiben.

Meine Anforderungen sind vorerst ziemlich eingeschränkt:
- Rendern eines Filmes aus einer Sequenz von Fotos in Lightroom unter Mac OS X
- Codec: H264, Bild-Rate 30fps
- Bild-Grösse 1080p

Das Resultat steht auf Github kostenlos zum Download zur Verfügung.
Das Binary und der Source-Code stehen können unter der MIT Lizenz genutzt werden.

Vorgehen zur Entwicklung eines solchen Plugins.


1. Erkunden des SDKs

Das SDK steht bei Adobe als Download (8MB) zur Verfügung.
Das API ist in Lua geschrieben. Dies bedeutet dass Plugins grundsätzlich auch in Lua programmiert werden müssen.
Natürlich kann man mit Lua externe Prozesse starten und dies ist auch möglich in Lightroom Plugins. Somit können beliebige externe Tools eingebunden werden.

Das SDK wird begleitet von einem ausführlichem Programmers Guide als PDF und einer HTML-Basierten API-Referenz. Für alle der verschiedenen Plugin-Typen gibt es ein ausführliches Beispiel mit komplettem Programm-Code.

Grundsätzlich sind diese Features in Lightroom erweiterbar:

  • Befehle im Menu "Library", "Help" und "Export"
  • Export- und Publish-Dienste
  • Metadaten-Felder
  • HTML Web-Engine für Fotogalerien

Es gibt sowohl ein Lightroom Users Forum als auch ein Lightroom SDK Forum. Auf der Website des SDK wird aber leider nur auf das User Forum verlinkt.
Der Typ "Export-Service" scheint für meine Zwecke zu passen.

Die Verwendung des Plugins stelle ich mir etwa so vor:
  1. Fotos aus Lightroom-Katalog selektieren und exportieren.
  2. Im Export-Dialog das Plugin "Video Renderer" wählen und die Render-Parameter wählen.
  3. Button "Exportieren" anklicken und ein paar Sekunden warten.
2. Plugin implementieren

Eine einfache Möglichkeit um Bildsequenzen zu rendern, ist die Open-Source Software ffmpeg.
Der Render-Befehl damit in Lua so aus:

local ffmpegPath = LrPathUtils.child(_PLUGIN.path, "ffmpeg")
local outputPath = exportParams.LR_export_destinationPathPrefix
local outputFile = exportParams.filename
local command = string.format("\"%s\" -y -i %s/\%05d.jpg -c:v libx264 -r 30 -vf scale=-1:1080 -pix_fmt yuv420p \"%s/%s\"", 
ffmpegPath, outputPath, outputPath, outputFile)
result = LrTasks.execute(command)

LrPathUtils und LrTasks sind Teil des Lightroom SDKs.

Für das Rendern muss ich mit dem Plugin eine Version von ffmpeg mitliefern. Da ich momentan nur OS X unterstützen möchte, ist das relativ einfach. Ich besorge mir hier ein statisches Binary für Mac OS X 64-bit Intel.

Der Export-Dialog in Lightroom kann mit einigen Zeilen Lua definiert werden:

exportServiceProvider.sectionsForBottomOfDialog = function ( f, propertyTable )
local LrView = import 'LrView'
local bind = LrView.bind
local share = LrView.share
local result = {
{
title = LOC "$$$/VideoRenderer/ExportDialog/VideoSettings=Render Settings",
synopsis = bind { key = 'fullPath', object = propertyTable },
f:row {
f:static_text {
title = LOC "$$$/VideoRenderer/ExportDialog/FileName=File Name:",
alignment = 'right',
width = share 'leftLabel',
},
f:edit_field {
value = bind 'filename',
truncation = 'middle',
immediate = true,
fill_horizontal = 1,
},
}
}
}
return result
end

Schlussendlich sieht der Export-Dialog mit ein paar Erweiterung dann so aus:



3. Plugin testen

Für Lua gibt es einige Tools die Unit-Testing bzw. auch BDD-Testing ermöglichen. Am besten gefallen hat mit busted von Olivine-Labs.
Leider ist es etwas aufwändig für das Lightroom SDK ein Test-Harness zu erstellen, deshalb gibt es vorerst noch keine automatischen Tests für mein Plugin.
Ich nehme mir vor für die nächste Version das Rendern automatisiert zu testen.

4. Installer und Disk-Image erstellen

Das XCode-Tool pkgbuild ermöglich es, mit der Kommandozeile Pkg-Archive zu erstellen die sich mit dem OSX-Installer installieren lassen.

pkgbuild --identifier ch.andyhermann.videorenderer --install-location ~/Library/Application\ Support/Adobe/Lightroom/Modules/ --root plugin_src plugin.pkg

Leider erscheint ohne signieren des Packages eine Warnung beim Öffnen. Damit muss ich vorerst leben.

Unsigniertes Installer-Package


Das Verbreiten von Software für Mac OS X wird traditionell mit Disk-Images gemacht.
Auch dafür gibt es ein CLI-Tool namens hdituil dass sich einfach einbinden lässt:

hdiutil create "target/VideoRenderer.dmg" -volname "Video Renderer" -srcfolder "target/disk_image"

Natürlich soll der Build alle Schritte automatisiert durchführen. Mangels einfacher Alternativen für lua benutze ich dafür rake.

5. Plugin veröffentlichen

Ich nutze das Release-Feature von Github für ein einfaches Hosting der Dateien.
Die neuste Version des Plugins ist hier verfügbar.

Resultat eines einfachen Timelapse-Videos





Natürlich fehlen dem Plugin viele wichtige Features wie Deflickering, Stabilization, Ken-Burns etc.
Doch die Bedienung ist dafür ziemlich simpel.

Ich bin gespannt auf Feedback. Ist das Plugin nützlich für irgend jemanden?

Source Code des Projekts:
https://github.com/andreashermann/VideoRenderer

Montag, 4. Mai 2015

Highlights der Spring I/O Barcelona

Die zwei Tage Spring I/O in Barcelona waren vollgepackt mit meist interessanten Vorträgen von Rednern der Spring-Community aus der ganzen Welt. Gewisse Themen waren sehr prominent vertreten und wurden überall "gehyped".
Es folgt eine Übersicht meiner favorisierten Buzz-Words.

Völlig unumstritten waren Microservices das meist erwähnte Thema der Spring I/O. Netflix ist dabei das Vorzeige-Exemplar unter den Firmen welche Software nach diesem Architekturstil entwickeln. David Syer gab einen Vortrag über den Open-Source-Stack des amerikanischen Streaming-Giganten. Dazu erwähnte er im Schnellgang einige Tools, welche den Betrieb von Microservices vereinfachen.
Beispielsweise:


Spring Boot ist die Technologie, zu welcher es an der Konferenz die meisten Talks gab. Das relativ junge Spring-Produkt ermöglicht es, mit wenig Code neue Applikationen zu entwickeln und zu deployen. Der Clou bei Spring Boot ist die automatische Konfiguration der Module. Ein Spring-Boot-Modul muss nur als Abhängigkeit eingebunden werden. Es bringt bereits selbst eine sinnvolle Konfiguration mit.
Spring Boot ist ausserdem perfekt geeignet für den Einsatz mit Docker. Es ermöglicht das Erzeugen eines startbaren JARs inklusive aller Abhängigkeiten wie auch z.B. Embedded Tomcat oder Undertow.

Josh Long gab einen unterhaltsamen Talk mit dem Titel How to build 'Bootiful' applications with Spring Boot. Prägnant formulierte er das Motto: "Make jar, not war". Mit Groovy schrieb er einen winzigen Demo-Service der sogar in einen Tweet passte.
Auf der URL http://start.spring.io bietet Pivotal, die neue Firma hinter Spring, einen Projekt-Generator der hilft die passenden Maven- oder Gradle-Konfigurationen zu erstellen. Die Website ist sogar optimiert für curl!
Welche Vereinfachungen Spring Boot für den Betrieb bieten, vermittelte Nicolas Fränkel im Vortrag Spring Boot for Devops. Jede Spring-Komponente registriert seine Metrics und Health-Status automatisch. Ein Rest-API ermöglicht das andocken von existierenden Monitoring-Tools wie zum Beispiel Graphite. Als Implementierung wird die bewährte Dropwizard-Metrics Library verwendet.

start.spring.io with curl


Alvaro Sanchez-Mariscal erklärte Lösungen für Stateless Authentication. Einerseits zeigte er dass es mit OAuth2 einen verbesserten Standard gibt, der in seiner Funktionsweise relativ leicht verständlich ist. Andererseits vermittelte er die Konzepte von JSON Web Tokens, einem Standardformat für Tokens mit OAuth2.

Ray Tsang von Google demonstrierte in seinem Talk wie man mit Kubernetes seine Docker-Container orchestrieren kann. Er demonstrierte auch das neue UI. Google arbeitet aktuell an einem Container-Service Google Container Engine, welcher auf Kubernetes basiert.

Kubernetes UI


Sehr aufschlussreich war der Vortrag von Sébastien Deleuze über Isomorphic Templating. Es ermöglich das Verwenden der gleichen Templates für das Rendern auf dem Server und dem Client. Was erst etwas weit hergeholt erscheint für normale Web-Applikationen, hat in der Anwendung für grosse Websites mit viel Inhalt durchaus seine Berechtigung.
Die Technik kann die initiale Ladezeit von Mobil-Applikationen etwa um einen Faktor Fünf verringern. Sie vereinfacht auch die Zugänglichkeit für Suchmaschinen, was für manche Zwecke auch wichtig sein kann. 
Sébastien demonstrierte eine Implementierung auf Basis von der Nashorn und React.

Wer Big Data betreibt, findet mit Spring XD eine Platform für Entwicklung und Betrieb. Sie baut auf Spring Integration auf und wird als Alternative zu Frameworks wie Storm, Flume, Oozie oder Sqoop bezeichnet. 
Die Runtime bietet Stream Processing, Batch Workflows, Analytics und einen Message Bus.
Natürlich bringt die Platform bereits komfortable Management-Tools mit, die den Betrieb vereinfachen.
Spring XD

Neben den Vorträgen fanden auch Workshops zu verwandten Themen statt. Dort gab es die Gelegenheit die Themen in der Praxis zu vertiefen.
Ingesamt fand ich die Spring I/O extrem interessant und kann einen Besuch sehr empfehlen. Ob die Konferenz nächstes Jahr wieder stattfindet ist noch nicht gesichert.