A Catedral e o Bazar/VI
O verdadeiro ponto de mudança no projeto foi quando Harry Hochheiser me mandou o seu rascunho de código para reenviar mensagens para a porta SMTP da máquina cliente. Eu percebi quase imediatamente que uma implementação segura desta característica iria tornar todos os outros modos de envio perto do obsoleto.
Por muitas semanas eu fiquei customizando o fetchmail de maneira incremental enquanto percebia como o projeto de interface estava aproveitável mas feio -- não estava elegante e com muitas pequenas opções por toda parte. As opções para extrair mensagens coletadas para um arquivo de mensagens ou saída padrão particularmente me aborreciam, mas eu não conseguia descobrir por que.
O que eu vi quando eu pensei sobre reenvio SMTP foi que o popclient estava tentando fazer muitas coisas. Ele foi projetado para ser tanto um agente transportador de correspondência (MTA) quanto um agente local de entrega (MDA). Com reenvio SMTP, ele poderia retirar o MDA e ser somente um MTA, transferindo as correspondências para outros programas para entrega local como o sendmail faz.
Por que se envolver com toda a complexidade de configurar um agente de entrega de correspondência ou configurar lock-e-append em um arquivo de correio quando a porta 25 é quase garantida para estar lá em primeiro lugar em qualquer plataforma com suporte para TCP/IP? Especialmente quando isso significa que o correio coletado é garantido parecer como um correio SMTP iniciado pelo remetente normalmente, o que, de qualquer maneira, é realmente o que queremos.
Há várias lições aqui. Primeira, esta idéia de reenvio por SMTP foi o primeiro grande retorno que eu obtive por tentar conscientemente emular os métodos do Linus. Um usuário me deu esta idéia brilhante -- tudo que eu tive que fazer foi entender as implicações.
11. A melhor coisa depois de ter boas idéias é reconhecer boas idéias dos seus usuários. As vezes a última é melhor.
E o que é interessante, você irá rapidamente descobrir que se você está se achando completamente desacreditado sobre o quanto você deve a outras pessoas, o mundo inteiro irá tratá-lo como se você mesmo tivesse criado cada bit da invenção e está somente sendo modesto sobre seu gênio inato. Nós todos podemos ver o quanto isso funcionou para Linus!
(Quando eu mostrei este documento na conferência de Perl em Agosto de 1997, Larry Wall estava na primeira fila. Quando eu li a última linha acima ele gritou fervorosamente, em um estilo religioso nostálgico, "Diga, diga, irmão!". Toda a audiência riu, porque eles sabiam que isso também funcionou para o criador do Perl.)
Após poucas semanas executando o projeto no mesmo espírito, eu comecei a ganhar um louvor semelhante não apenas dos meus usuários mas de outras pessoas que deixaram as palavras escaparem. Eu guardei algumas destas mensagens; irei olhar para elas novamente algum dia se eu começar a questionar se a minha vida valeu a pena :-).
Mas há duas lições mais fundamentais aqui, não políticas, que são gerais para todos os tipos de projeto.
12. Freqüentemente, as soluções mais impressionantes e inovadoras surgem ao se perceber que o seu conceito do problema estava errado.
Eu estava tentando resolver o problema errado ao desenvolver continuamente o popclient como um MTA/MDA combinado com todos os tipos de modos de distribuição local. O projeto do fetchmail precisava ser repensado do início como um puro MTA, uma parte do caminho normal do correio da Internet que fala SMTP.
Quando você atinge uma parede ao desenvolver -- quando você dificilmente se encontra pensando em algo depois do próximo patch -- é freqüentemente tempo para perguntar não se você tem a resposta certa, mas se você está perguntando a pergunta correta. Talvez o problema precise ser reformulado.
Bem, eu reformulei meu problema. Claramente, a coisa certa a fazer era (1) codificar o suporte para reenvio por SMTP no driver genérico, (2) tornar isto o modo default, e (3) eventualmente desfazer todos os outros modos de envio, especialmente as opções de enviar-para-arquivo e enviar-para-saída-padrão.
Eu hesitei sobre o passo 3 por algum tempo, temendo aborrecer os usuários de longa data do popclient dependentes dos mecanismos alternativos de envio. Em teoria, eles poderiam imediatamente passar a usar arquivos .forward ou seus equivalentes não-sendmail para obter os mesmos efeitos. Na prática a transição poderia ser confusa.
Mas quando eu a fiz, os benefícios provaram-se altos. As partes obscuras do código do driver sumiram. A configuração ficou radicalmente mais simples -- não mais rastejar à volta atrás do MDA do sistema e da caixa de correio do usuário, não mais preocupações sobre se o sistema operacional suportava locking de arquivo.
Além disso, a única maneira de perder correio sumira. Se você especificava envio para um arquivo e o disco estava cheio, seu correio estaria perdido. Isto não pode acontecer com o reenvio por SMTP porque o receptor SMTP não retornará OK a não ser que a mensagem possa ser enviada ou pelo menos reprogramada para um envio mais tarde.
E também, a performance aumentou (embora você não perceberia isso somente com uma execução). Outro benefício não insignificante foi que a página do manual ficou muito mais simples.
Mais tarde, eu tive que recolocar envio por um MDA local especificado pelo usuário para permitir o tratamento de algumas situações obscuras envolvendo SLIP dinâmico. Mas eu encontrei uma maneira muito mais simples de fazer isto.
A moral? Não hesite em jogar fora características obsoletas quando você puder fazer isso sem perda de efetividade. Antoine de Saint-Exupéry (que foi um aviador e projetista de aviões quando ele não estava sendo o autor de livros clássicos infantis) disse:
13. "A perfeição (em projetar) é alcançada não quando não há mais nada a adicionar, mas quando não há nada para jogar fora."
Quando o seu código está ficando tão bom quanto simples, é quando você sabe que está correto. E no processo, o projeto do fetchmail adquiriu uma identidade própria, diferente do ancestral popclient.
Era tempo para a mudança de nome. O novo projeto parecia muito mais como um irmão do sendmail do que o velho popclient parecia; ambos eram MTAs, mas aonde o sendmail passa e então envia, o novo popclient coleta e então envia. Então, após 2 meses, eu mudei o nome para fetchmail.