Der wirkliche Wendepunkt im Projekt kam, als Harry Hochheiser mir
seinen von fetchmail unabhängigen Code für das Weiterreichen von Mail
an das SMTP-Port der Klientenmaschine schickte. Ich erkannte fast
augenblicklich, dass eine zuverlässige Implementation dieses
Leistungsmerkmals alle anderen Modi der Zustellung fast überflüssig
machen würde.
Viele Wochen lang hatte ich an fetchmail und an einer kleinen
Verbesserung nach der anderen gebastelt und hatte dabei den Eindruck,
dass das Schnittstellen-Design zwar leicht zu handhaben, aber nicht
ganz sauber durchdacht sei -- ohne Eleganz und mit zu vielen
geringfügigen Optionen, die überall heraushängten. Die Optionen für
das Umleiten von abgeholter Mail in einer Mailbox-Datei oder zur
Standardausgabe war mir ein besonderer Dorn im Auge, ich konnte aber
nicht herausfinden, warum.
Als ich mir die Sache mit dem SMTP-Forwarding überlegte, erkannte ich
das Problem. Popclient versuchte zu viele Dinge auf einmal. Er wurde
entworfen und gebaut, um sowohl als Mail Transport Agent (MTA) als
auch als Local Mail Delivery Agent (MDA) aufzutreten. SMTP-Forwarding
würde ihn aus dem MDA-Geschäft hinausbugsieren und ihn zu einem reinen
MTA machen, der Mail für die lokale Zustellung an andere Programme
weiterreicht -- so wie
sendmail
das tut.
Warum eigentlich, so meine selbstgestellte Frage, sollte ich mich mit
der ganzen Komplexität der Konfiguration eines Mail Delivery Agent
plagen oder lock-and-append für eine Mailbox aufbauen, wenn doch Port
25 fast garantiert auf jeder Plattform existiert, die TCP/IP
unterstützt? Speziell wenn dies bedeutete, dass die abgeholte Mail
garantiert wie gewöhnliche sender-initiated SMTP-Mail aussehen würde -
was eigentlich das ist, was wir wirklich wollen.
Hier kann man einige Lektionen lernen. Die erste: Diese Idee mit dem
Weiterreichen von SMTP-Mail war die lohnendste Einzelleistung, in
deren Genuss ich durch bewusstes Nachahmen von Linus' Methoden kam.
Diese glänzende Idee kam von einem Benutzer -- alles, was ich tun
musste war, deren Auswirkungen zu verstehen.
11. Das zweitbeste nach eigenen guten Ideen ist das Erkennen von guten
Ideen von Benutzern. Manchmal ist letzteres sogar das bessere.
Paradoxerweise werden Sie schnell herausfinden, dass, wenn Sie total
selbstlos die ganze Wahrheit darüber offenbaren, wieviel Sie anderen
Menschen verdanken, Sie die ganze Welt behandeln wird, als hätten Sie
jede einzelne Erfindung höchstpersönlich gemacht und würden einfach
nur die natürliche Bescheidenheit des wahren Genies zeigen. Wir haben
alle gesehen, wie gut das für Linus funktionierte!
(Als ich auf der perl-Konferenz im August 1997 meine Rede hielt, saß
Larry Wall
in der ersten Reihe. Als ich zur eben aufgeschriebenen
Zeile kam, ereiferte er sich im gespielten Tonfall eines Predigers:
Verkünde es, Bruder, verkünde es!.
Das ganze Publikum lachte, denn
jeder wusste, dass sie auch für den Erfinder von
perl funktioniert
hatte.)
Nach einigen wenigen Wochen in diesem Geiste begann ich in den Genuss
von ähnlichem Lob zu kommen -- nicht nur von Benutzern, sondern auch
von Leuten, die von meinem Projekt erfahren hatten. Ich habe einige
von den E-Mails aufgehoben; eines Tages werfe ich vielleicht noch
einen Blick darauf, falls ich mich fragen sollte, ob mein Leben einen
Sinn gehabt hat :-).
Es gibt hier aber zwei fundamentalere, nicht-politische Lektionen zu
lernen, die für alle Arten von Design gelten.
12. Oft stammen die hervorragendsten und innovativsten Lösungen aus
der Erkenntnis, dass die ganze Vorstellung vom Problem falsch war.
Ich hatte versucht, das falsche Problem zu lösen, als ich fortfuhr,
popclient als einen kombinierten MTA/MDA zu entwickeln, der alle
möglichen Modi der lokalen Zustellung unterstützte. Fetchmails Design
musste von Grund auf neu überdacht und als reiner MTA gesehen werden,
und als Teil des üblichen SMTP-sprechenden Internet-Postweges.
Nun, so kam ich zu einer Neufassung meines Problems. Klar war, dass (1)
Unterstützung für SMTP-Forwarding in den generischen Treiber
dazugehackt werden musste, (2) dies der Standardmodus werden musste, und
(3) schließlich alle anderen Modi der Zustellung hinaus gehörten,
besonders die Möglichkeit, Mail in eine Datei oder zur Standardausgabe
umzuleiten.
Bei Schritt 3 zögerte ich für einige Zeit. Ich hatte Angst, alte
popclient-Benutzer zu vergrämen, die von alternativen
Zustellungsmechanismen abhängig waren. Theoretisch hätten sie sofort
zu .forward-Dateien oder deren Non-sendmail-Äquivalenten wechseln
können, praktisch aber war dieser Wechsel ein Alptraum.
Als ich mich dazu entschied, stellten sich die Vorzüge als riesig
heraus. Die haarigsten Teile des Treiber-Codes verschwanden einfach.
Die Konfiguration wurde radikal leichter -- kein Stöbern mehr nach der
System-MDA und der Mailbox des Benutzers, keine Sorgen mehr darüber,
ob das zugrunde liegende Betriebssystem das file locking unterstützt.
Auch verschwand die einzige Möglichkeit, Mail zu verlieren. Wenn man
Zustellung in eine Datei spezifizierte und die Disk voll war,
verschwand die Mail. Das konnte bei SMTP-Forwarding nicht mehr
passieren, da der SMTP-Listener einfach kein OK gab, solange die
Nachricht nicht zugestellt werden oder wenigstens für spätere
Zustellung gespoolt werden konnte.
Auch der Durchsatz erhöhte sich (obwohl man das in einem einzigen
Durchlauf wahrscheinlich nicht bemerken könnte). Ein weiterer, nicht
unbedeutender Nutzen dieser Änderung war, dass die Manpage wesentlich
simpler wurde.
Später musste ich einen benutzerspezifizierten lokalen MDA wieder zum
Funktionieren bringen, um einige obskure Situationen abzudecken, die
Dynamic SLIP involvierten. Ich fand aber eine viel schlichtere Methode
dafür.
Die Moral der Geschichte? Zögern Sie nicht, überholte Features
aufzugeben, wenn die Effektivität davon unbeeinflusst bleibt.
Antoine de Saint-Exupéry
(der Pilot und Flugzeugdesigner war, wenn er nicht
mit dem Schreiben von klassisch gewordenen Kinderbüchern beschäftigt
war) sagte einmal:
13. "Perfektion (im Design) ist nicht erreicht, wenn es nichts mehr
hinzuzufügen gibt, sondern wenn es nichts mehr wegzunehmen gibt."
Wenn Ihr Code sowohl besser als auch einfacher wird, dann wissen Sie,
dass Sie es richtig gemacht haben. Dadurch bekam fetchmail seine eigene
Identität und löste sich von seinem Vorfahren popclient.
Es wurde Zeit für eine Namensänderung. Das neue Design sah mehr nach
einer Entsprechung von sendmail aus als der alte popclient; beide sind
MTAs, aber so wie sendmail die Zustellungen fortschickt, so fängt sie
der neue popclient ein. Daher taufte ich ihn in fetchmail um.
Es gibt hier aber eine noch allgemeiner anwendbare Lektion darüber,
wie
SMTP-Zustellung
ein fetchmail-Feature wurde. Es ist die, dass nicht
nur Debugging parallelisierbar ist -- auch die Entwicklung ist es und
(in einem vielleicht überraschenden Ausmaß) auch die Erforschung des
Designraumes. Wenn der Entwicklungsmodus mit sehr kurzen
Iterationszyklen arbeitet, werden Entwicklung und Erweiterung zu
Spezialfällen des Debuggings -- zu einer Beseitigung von Fehlern, die
Auslassungen sind - Auslassungen im ursprünglichen Konzept der
Software.
Sogar auf höheren Ebenen des Entwurfs kann es sehr wertvoll sein, das
Denken vieler Mit-Entwickler in den Design-Raum eines Produkts
ausschwärmen zu lassen. Stellen Sie sich dazu vor, wie eine
Wasserpfütze einen Abfluss findet, oder noch besser, wie Ameisen Essen
finden: Erforschung durch Einsickern, gefolgt von einer Diskussion,
die über skalierbare Kommunikationsmittel geführt wird. Das
funktioniert sehr gut; wie bei Harry Hochheiser und mir, wird einer
Ihrer Späher einen riesigen Gewinn in Ihrer Reichweite entdecken, den
Sie aufgrund eines vernagelten Blickfeldes nicht gesehen hatten.
|