Githubs Editor Atom feierte kürzlich seinen ersten Geburtstag. Das Unternehmen bewirbt die extrem konfigurierbare freie Anwendung als Kompromiss zwischen Vi und Emacs auf der einen, Sublime und Textmate auf der anderen Seite. Auch im Rohzustand wirkt die Mischung schon vielversprechend.
Als Github im Juni 2014 Atom [1] ankündigte, stöhnten viele Kommentatoren: Braucht die Welt wirklich noch einen Editor? Die Github-Macher jedenfalls sind davon überzeugt. Sublime Text [2] und Textmate [3] seien zwar komfortabel, aber zu wenig anpassbar. Emacs und Vi ließen sich hingegen extrem modifizieren, seien aber für Einsteiger eher wenig komfortabel.
Die Github-Macher wissen ziemlich genau, wie die Open-Source-Welt tickt, und machen bislang nicht viel falsch. Auch nicht bei Atom. Man glaubt, dass Projekte wie Vi und Emacs nur deshalb gut und dauerhaft funktionieren würden, weil sie einerseits offen sind und andererseits über eine große Community verfügen. Daher plant Github sich für den Editor, der unter einer MIT-Lizenz steht, langfristig zu engagieren.
Das schließt nicht aus, dass Github irgendwann eine Enterprise-Variante des Editors anbietet, doch für die aktuelle Version 1.0, die im Juni 2015 erscheinen soll, ist davon nicht die Rede.
Atommodell
Mit Atom sollen Entwickler plattformübergreifende Desktop- und Webapps entwickeln. Die Software bringt dafür Grammatiken für verschiedene Programmiersprachen mit, von Javascript über Perl und Python bis hin zu C, C++ oder Java. Letztlich ist Atom eine spezialisierte Variante des Browsers Chromium und die Fenster sind nichts anderes als lokal gerenderte Webseiten. Die in ihnen angezeigten Inhalte dürfen dabei auf das Node.js-API zugreifen.
Atom besteht aus einem überschaubaren Kern (Atom Core), die meisten anderen Komponenten liegen hingegen als Atom-Pakete vor, die der Atom Package Manager (APM) verwaltet. Der Kern und die Pakete laufen in einer Umgebung namens Electron [4], die vormals Atom Shell hieß. Diese kümmert sich um automatische Updates, bringt einen Windows-Installer mit, fertigt Crashreports an und liefert Benachrichtigungen aus. Die Funktionen sind über Javascript-APIs erreichbar.
Der Einfachheit halber verwenden und empfehlen die Entwickler für die Arbeit mit Atom Coffeescript anstelle von Javascript sowie Less als Ersatz für CSS. Allerdings lässt sich der Editor auch mit Javascript und CSS erweitern.
Steuerpult
Nach der Installation (siehe Kasten “Atom installieren”), die etwas weniger aufwändig sein könnte, landet der Entwickler auf einer grafischen Oberfläche (Abbildung 1). Sie besteht aus verschiedenen Bereichen, als Panes bezeichnet, die er flexibel vergrößert und verkleinert, auf Wunsch auch neu anordnet. Die einzelne Datei, an der er arbeitet, heißt im Atom-Jargon Buffer.
Atom installieren
Die Installation erforderte unter Ubuntu 14.04 mit LXDE-Desktop ein wenig Aufwand, was vor allem an der für Atom benötigten Node.js-Umgebung liegt. Es gibt fertige Pakete, aber wer die Software selbst kompilieren möchte, muss zunächst die passenden Dateien installieren:
sudo apt-get install build-essential git libgnome-keyring-dev fakeroot gconf-service libnss3
Dann gilt es, die neueste Node.js-Version zu besorgen, die Nodesource.com [6] betreut:
curl -sL https://deb.nodesource.com/ setup | sudo bash -
Die Befehlsfolge holt im Wesentlichen ein Setup-Skript für die aktuelle Node-Version auf den Rechner und führt es mit Rootrechten aus. Vorsichtige Zeitgenossen setzen nach der Pipe ein »more« , um das Skript vor dem Ausführen zu betrachten. Das Kommando
sudo apt-get install -y nodejs
installiert – ist es ohne Ärger durchgelaufen – die neueste Variante des Framework.
Zeitigt der Befehl »which node« jedoch anschließend kein Ergebnis, liegt das wahrscheinlich daran, dass das Binary unter »/usr/bin/« »nodejs« heißt. Atom sucht aber nach »/usr/bin/node« . Der Befehl
sudo update-alternatives --install /usr/bin/node node /usr/bin/nodejs 10
korrigiert das. Die nächste Befehlsfolge klont das Atom-Repository auf Github und checkt dann – aus dem Verzeichnis »atom« heraus – die letzte Release von Atom aus.
git clone https://github.com/atom/atom cd atom git fetch -p git checkout $(git describe --tags `git rev-list --tags --max-count=1`)
Schließlich führt der Admin das Buildskript aus und startet dann den Javascript Task Runner Grunt [7], um die ausführbare »atom« -Datei und den Paketmanager »apm« nach »/usr/local/bin« zu installieren. Nebenbei: Mit Grunt lässt sich über »script/grunt mkdeb« auch ein Debian-Paket erzeugen.
Im linken Bereich befindet sich der Verzeichnisbaum für das aktuelle Projekt, in das große Feld in der Mitte gehört der Code. Über [F11] gelangt der Entwickler in den Vollbildmodus, die Einstellungen öffnet Atom als zusätzlichen Reiter, wenn sein Benutzer sie über [Strg]+[,] oder »Edit | Preferences« aufruft.
Weiß er mal nicht genau, was er tun soll, lässt sich der Anwender des Editors zunächst über [Strg]+[Shift]+[P] sämtliche verfügbaren Befehle anzeigen. Im Internet gibt es auch ein hilfreiches Flight Manual [5], das leider bislang nur auf Englisch vorliegt.
Im Reaktor
Obwohl der Editor noch ein recht junges Projekt ist, bringt er bereits einige hilfreiche Features mit. Eine oder mehrere Codezeilen rückt der Entwickler nach rechts ein, indem er diese markiert und [Tab] verwendet. Über [Shift]+[Tab] wandert der Codeblock nach links.
Auch eine Auto Completion ist implementiert, hier versprechen die Entwickler künftig noch mehr Features. Aktuell lässt sie sich über [Strg]+[Space] aktivieren und zeigt Alternativen zu dem Element an, über dem sich der Cursor im Augenblick befindet.
Ruft der Entwickler die Settings auf –mit [Strg]+[,] – und setzt unter »Editor Settings« ein Häkchen bei »Soft Wrap« , wechselt der Editor am Bildschirmrand die Zeile. Ein weiteres Häkchen bei »Soft Wrap At Preferred Line Lenght« bricht den Code nach n Zeichen um. Eine sichtbare Linie markiert die Umbruchsgrenze, die per Default bei 80 Zeichen liegt. Das ändert der Atom-User in der Zeile »Preferred Line Length« .
Aktiviert der Programmierer die Option »Soft Tabs« , wandelt der Editor Tabs automatisch in Leerzeichen um, deren Anzahl sich ebenfalls in den Settings festlegen lässt (»Tab Length« ).
Beim Folding geht es dem Entwickler darum, die Struktur des Codes sichtbar zu machen, indem er ihn unterhalb einer Methode, Anweisung oder Funktion einklappt. Das ließe sich besser lösen, denn die kleinen Dreiecke links neben den Faltstellen sind mitunter schwer zu treffen und der Editor springt dann plötzlich in andere Codepassagen.
Schwächen und Stärken
Das junge Tool weist auch noch ein paar Mankos auf. Das auffälligste: Atom verschluckt sich an Dateien, die 2 MByte überschreiten, die Entwickler arbeiten an einer Lösung. Permanent feilen sie auch daran, den eher gemächlichen Start des Editors und die Reaktionsgeschwindigkeit des GUI zu beschleunigen. Es reagierte im Test einen Tick zu träge, was aber möglicherweise an der sie umgebenden virtuellen Maschine lag.
Besser klappt hingegen, wen wundert’s, die integrierte Versionsverwaltung mit Git und Github. So stellt [Strg]+[Alt]+[Z] die letzte gute Version einer Datei wieder her, das Kommando entspricht:
git checkout HEAD -- /Pfad git reset HEAD -- /Pfad
Möchte der Entwickler zum Beispiel wissen, welche seiner Dateien Git nicht trackt, drückt er [Strg]+[Shift]+[B], was einem »git status« gleichkommt. Mit Hilfe des Pakets »language-git« hebt er die Commit-, Merge- und Rebase-Messages für Git optisch hervor. Über das Paket »git-diff« erhält der Editor die Fähigkeit, veränderte Zeilen visuell zu betonen.
Sucht ein Entwickler auf Github nach Informationen zu einer Datei, die er aktuell bearbeitet, hilft ihm ebenfalls eine Reihe von Tastaturkürzeln, die Tabelle 1 auflistet.
Tabelle 1
Github-Kürzel für Atom
|
Kürzel |
Aktion |
|---|---|
|
[Alt]+[G]+[O] |
Datei auf Github öffnen |
|
[Alt]+[G]+[B] |
Github-Infos zu den letzten Änderungen für eine Datei anzeigen |
|
[Alt]+[G]+[H] |
Github-Historie einer Datei betrachten |
|
[Alt]+[G]+[C] |
Github-URL des aktuellen File kopieren |
|
[Alt]+[G]+[R] |
Branch-Vergleich mit Github |
Hackbar bis zum Kern
Ein weiteres Plus von Atom ist die Möglichkeit, die Software weitgehend zu modifizieren. Ein Package Generator erzeugt dafür ein Skeleton für ein Paket, das im Test klassischerweise »hello-world« heißen soll. Das Paket tut nichts weiter, als ein Fenster mit der »Hallo-Welt« -Nachricht anzuzeigen (Abbildung 2).
Über [Strg]+[Shift]+[P] startet der Entwickler dann die Befehlssuche und ruft »Package Generator: Generate Package« auf. Der dabei erzeugte Boilerplate-Code landet im Verzeichnis »github/Projektname« , wobei der Projektname im Beispiel »hello-world« lautet. Zugleich erscheint der erzeugte Baum von Verzeichnissen in der Tree-Ansicht links, Abbildung 3 zeigt das Grundgerüst des »hello-world« -Pakets.
Die darin sichtbare vorletzte Datei heißt »package.json« . Sie enthält verschiedene Meta-Informationen zum Paket (Abbildung 4), darunter den Namen, die Versionsnummer, das potenzielle Github-Repository, aber auch den Pfad zu den ausführbaren Dateien im Unterverzeichnis »lib« .
Dieses Unterverzeichnis ist weiter oben in Abbildung 3 zu sehen und enthält gleich zwei Dateien: »hello-world.coffee« und »hello-world-view.coffee« . Während letztere die Elemente für das grafische Userinterface arrangiert (Listing 1), zeigt Abbildung 3 auch den Code mit der Logik für das Paket. Die Methoden »activate« , »deactivate« , »serialize« und »toggle« sind per Folding gekürzt, um die Struktur zu verdeutlichen, Listing 2 zeigt den nicht sichtbaren Code.
Listing 1
lib/hello-world-view.coffee
01 module.exports =
02 class HelloWorldView
03 constructor: (serializedState) ->
04 # Root-Element erzeugen
05 @element = document.createElement('div')
06 @element.classList.add('hello-world')
07
08 # Nachrichten-Element erzeugen
09 message = document.createElement('div')
10 message.textContent = "Hallo Welt!"
11 message.classList.add('message')
12 @element.appendChild(message)
13
14 # Gibt ein Objekt zurück, wenn der Nutzer das Paket aktiviert
15 serialize: ->
16
17 # Element entfernen
18 destroy: ->
19 @element.remove()
20
21 getElement: ->
22 @element
Listing 1 erzeugt das Rootelement (»@element« ) und ordnet diesem das Nachrichten-Element »message« als Child zu (Zeile 12). Darunter legt der Code fest, wie das Element auf »getElement()« – und »destroy()« -Aufrufe reagiert.
Die ersten drei der vier Methoden in Listing 2 gehören in der Regel fest zu einem Package. Die »activate()« -Methode erzeugt ein modales UI-Element (»ModalPanel« ) und pinnt es an Atoms Arbeitsfläche (Zeile 4). Die »subscriptions()« -Methode ordnet den in Listing 3 definierten Menü-Eintrag der Methode »@toggle()« zu. »@toggle()« (Zeile 20 in Listing 2) ist optional. Es sorgt dafür, dass unter dem Menüpunkt »Packages« ein Eintrag für »hello-world« auftaucht. Wer in dessen Submenü auf »Toggle« klickt oder [Alt]+[Strg]+[O] drückt, sieht das Fenster aus Abbildung 2 auftauchen oder verschwinden.
Listing 2
lib/hello-world.coffee
01 [...] 02 activate: (state) -> 03 @helloWorldView = new HelloWorldView (state.helloWorldViewState) 04 @modalPanel = atom.workspace.addModalPanel(item: @helloWorldView.getElement(), visible: false) 05 06 # Atom-Events lassen sich über CompositeDisposable einfach aufräumen 07 @subscriptions = new CompositeDisposable 08 09 # @toggle()-Methode mit 'hello-world:toggle' verknüpfen 10 @subscriptions.add atom.commands.add 'atom-workspace', 'hello-world:toggle': => @toggle() 11 12 deactivate: -> 13 @modalPanel.destroy() 14 @subscriptions.dispose() 15 @helloWorldView.destroy() 16 17 serialize: -> 18 helloWorldViewState: @helloWorldView.serialize() 19 20 toggle: -> 21 console.log 'HelloWorld was toggled!' 22 23 if @modalPanel.isVisible() 24 @modalPanel.hide() 25 else 26 @modalPanel.show()
Die Details im Menü sind anpassbar, Listing 3 zeigt das simple Schema. Es steckt im Ordner »menus« in der Datei »hello-world.cson« und erzeugt einen Eintrag für das Kontextmenü (Zeile 1) und für das Atom-Menü (Zeile 8).
Listing 3
menus/hello-world.cson
01 'context-menu':
02 'atom-text-editor': [
03 {
04 'label': 'Toggle hello-world'
05 'command': 'hello-world:toggle'
06 }
07 ]
08 'menu': [
09 {
10 'label': 'Packages'
11 'submenu': [
12 'label': 'hello-world'
13 'submenu': [
14 {
15 'label': 'Toggle'
16 'command': 'hello-world:toggle'
17 }
18 ]
19 ]
20 }
21 ]
Daneben kann der stilsichere Entwickler noch den Stil in einer Less-Datei ändern (unter »styles« ), ein Tastaturkürzel festlegen (»keymaps« ) und Spezifikationen für Tests erstellen (»spec« ). Mit den Specs lassen sich Funktionen gegen Regressionen testen [8], die Atom-Macher setzen dafür auf das hauseigene Javascript-Test-Framework Jasmine [9].
Fazit
Für eine Version 1.0 macht Atom bereits einen soliden Eindruck und ist tatsächlich einfach und tiefgehend konfigurierbar. Nutzern des Editors Sublime Text dürften viele Elemente bekannt vorkommen, offenbar haben sich die Entwickler kräftig bei der proprietären Python-Software bedient. Sicherlich versprechen sich die Macher dank der guten Github-Anbindung des Editors auch eine neue und dauerhafte Nutzerbasis für ihre Codeplattform.
Doch braucht auch Atom ein wenig Einarbeitungszeit. Defizite hat der Editor noch bei der Reaktionszeit des Userinterface und im Umgang mit großen Dateien. Auch die Installation zeigt sich etwas hakelig. Dafür hat Atom schon nach einem Jahr eine sehr aktive Community und wurde bereits 750000-mal heruntergeladen. Die 803 Entwickler haben 1861 Pakete ergänzt, offenbar trifft der Editor einen Bedarf.
Infos
- Atom: https://atom.io
- Sublime Text: http://www.sublimetext.com
- Textmate: https://macromates.com
- Electron: http://electron.atom.io
- Atom Flight Manual: https://atom.io/docs/v0.198.0/
- Node.js-Installationsanleitung von Nodesource: https://github.com/nodesource/distributions
- Grunt: http://gruntjs.com
- Specs für Atom schreiben: https://atom.io/docs/v0.186.0/writing-specs
- Jasemine: http://jasmine.github.io










