Blog (e email) de casa nova!

Mais uma vez tive um ataque de atualização-zite e resolvi abandonar algumas velhas práticas e adotar algumas novas: resolvi usar meu domínio pessoal (bruder.com.br) que hospeda meu blog e o email de mais de uma dezena de pessoas da família (desculpa aí pessoal!!) como cobaia:

  • Emails foram migrados de servidor próprio para a plataforma do Google, entre mortos e feridos salvaram-se todos e a migração foi menos dolorosa do que eu pensava que ia ser;
  • Já que migrei o email, resolvi migrar o host do blog que vos fala para uma instância micro do AWS da Amazon. Tudo bem que algumas compilações que fiz demoraram literalmente horas, mas depois do stack LAMP e WordPress bem configurados, para um blog de baixo volume como esse “máquina não fez falta”, e inclusive ficou (bem) mais rápido, vejam a comparação de 99 cargas foi “Average over 99 runs: 2.6 × faster, 670 ms / 1754 ms”. Bom resultado para uma instância micro, se me perguntarem.

SSH e SCP lentos? fear not!

Que fique aqui registrado como memória pública e notória para quando trombar novamente com ssh/scp’s com autenticações extremamente demoradas:

echo “GSSAPIAuthentication no” >> /etc/ssh/ssh_config ou ~/.ssh/config

Atenção leitores nerds irremediavelmente literais: esse append no ssh_config não é para ser literalmente executado, é apenas “desligue GSSAPIAuth..” em ssh_config ou ~/.ssh/config.

Instalando um .dmg via linha de comando

Precisei instalar um dmg (wget do rudix) hoje remotamente em um mac os, para referência futura e para quem mais precisar, eis como fazê-lo:

#hdiutil vai montar o dmg e dizer qual o path:
hdiutil attach wget-1.12-0.dmg
# no meu caso foi em /Volumes/wget.pkg/
cd /Volumes/wget.pkg/
# agora vamos efetivamente instalar o .pkg:
installer -allow -verbose -pkg wget.pkg -target /
# se "This package requires authentication to install.", sudo resolve:
sudo installer -allow -verbose -pkg wget.pkg -target /
# agora é desmontar o .dmg
cd ~ ; hdiutil detach /Volumes/wget.pkg

track de conteúdo não-HTML com analytics

Muito bem, eu e o resto do universo conhecido usa Google Analytics. Acabei trombando com a seguinte necessidade: Como fazer tracking de conteúdo não-HTML, que não pode rodar javascript? Descobri depois de algum tempo de procura que é bem fácil: Na página com os LINKS para o seu conteúdo sem-javascript (downloads, stream, o que for), acrescente onClick="javascript: pageTracker._trackPageview('/your/url');" no A HREF equivalente. Simples assim.

xcode

Desenvolvendo para iOS – para quem vem do desktop

Desenvolver para iPhone está longe de ser “só tenho que aprender Objective C e as libs usadas”. Principalmente se você já tem uma experiência anterior de desenvolvimento GUI para o desktop, um conjunto bem grande de conceitos que você nem mais pensava neles e os tinha por padrão são alterados, todo um novo ambiente para se acostumar. Claro que se você já tem experiência mobile muito disso já é velho conhecido seu (como eu descobri conversando sobre isso com o EPX, Symbian tem muitas limitações parecidas). Vou dar alguns exemplos de “esquisitisses” que encontrei no iPhone para quem vem do desktop:

  • Não há swap file, sem chance de memória virtual maior que a memória física. OUT OF MEMORY Handler no iOS é reboot(), não tem o que fazer.
  • iOS-específico: as aplicações tem um screenshot da primeira window mostrada, que é carregada e mostrada, para daí se proceder à carga da aplicação, para gerar no usuário a (falsa) impressão de “carregou instantaneamente”. Segundo o epx o caminho do screenshot é “application.app/resources/171/screenshot.png” :)
  • iPhone compila suas aplicações em um instruction set reduzido (16 bits)  de ARM, chamado THUMB para economizar memória (normalmente 35% de economia), performance de ponto flutuante é o que mais sofre, segundo a documentação.
  • Existe um sinal enviado pelo S.O. à aplicações para liberação cooperativa de memória (applicationDidReceiveMemoryWarning no delegate, didReceiveMemoryWarning em sub-classes de UIViewController, e UIApplicationDidReceiveMemoryWarningNotification notification). Safari, por exemplo, apaga caches e visualizações de tabs off-screen.
  • Leia o HIG (Human Interface Guidelines, para quem não conhecia o acrônimo), leia o HIG, leia o HIG. Muita coisa lá já foi pensada e mastigada para que você, desenvolvedor newbie como eu em plataformas mobile não tenha que sofrer re-inventando a roda ou fazendo a versão desktop socada na tela minúscula do telefone da sua aplicação. Mais uma vez, leia o HIG: iPhone Human Interface Guidelines.
  • Ironicamente, mesmo com toda essa limitação (a maior delas sendo memória, até agora), temos um hardware extremamente poderoso dentro do iphone, e olhe que nem estou falando do iphone 4 e sim do 3GS: O que eu já vi esse celular fazendo com openGL é algo fantástico.
41CJP5DNV3L._BO2,204,203,200_PIsitb-sticker-arrow-click,TopRight,35,-76_AA300_SH20_OU01_

Desenvolvendo para iOS – pós Hello World

Depois de muito bater a cabeça no esforço auto-didata de aprender sobre desenvolvimento para iOS, desisti de ser tão PÂNK e dei um passo atrás no auto-didatismo, comprei um livro sobre o assunto: iPhone Programming: The Big Nerd Ranch Guide (Big Nerd Ranch Guides). Até agora só cheguei no segundo capítulo e já passei da etapa hello world. O resumo do que aprendi até agora:

  • Desenvolvimento Cocoa (Touch) é MVC, you idiot. Eu teria passado (bem) menos trabalho se tivesse percebido que qualquer tentativa de fazer diferente disso só atrapalha;
  • Desenvolvimento no Interface Builder não tem NADA a ver com o velho RAD dos Delphi, VB & arredores. Quanto mais rápido você absorver o conceito que Interface Builder é um editor de objetos e que não é usual ficar sub-classeando objetos visuais, mais rápido você irá se achar;

streaming de áudio ao vivo

Faz vários anos que a IPI Maanaim realiza uma maratona de leitura bíblica, e como a vários anos fazemos, esse ano também vamos transmitir a maratona ao vivo via internet pelo site da igreja, e o assunto do post é a infra-estrutura de transmissão.

A alguns anos que usamos shoutcast no servidor e darkice/darksnow. Esse ano eu atualizei o shoutcast para a última versão estável, 1.9.8. Além disso abandonamos a dupla darkice & darksnow e estou pendente entre 2 soluções: butt ou Nicecast. Butt é multi-plataforma, Windows, Linux e Mac OS X e gratuito, Já Nicecast é somente Mac OS X e comercial (US$ 40). Todos os 2 são garantidamente compatíveis como geradores de stream para o shoutcast, já devidamente testados. A vantagem do Nicecast é o suporte a plugins de filtro para processamento do som: highpass, lowpass, compressores, reverb, etc. AUDynamicsProcessor é excelente para cortar o ruído de fundo entre-palavras, por exemplo. A melhora na qualidade de áudio é significativa com a aplicação racional de poucos filtros.

Caso adotemos Butt, provavelmente usaremos Linux (Ubuntu) na geração do áudio e a máquina Mac OS X fica como plano B. O problema do Nicecast é que não teremos plano B daí :p

Caso alguém tenha interesse em mais detalhes da configuração das 2 pontas (shoutcast no server e o gerador de streaming live na Maanaim), é só avisar, já vi gente batendo cabeça com isso.

UPDATE: No final das contas usamos a solução butt @ ubuntu, com um player flash no site, wavestreaming. No final das contas a solução inteira (butt, shoutcast, wavestreaming) é gratuita, mas não aberta.

UPDATE2: Um pequeno retoque no site com o player flash, desisti do popup (popups are so 90’s) e coloquei o player direto na página. Acabada a Maratona, tiramos o player. Nesse instante 8 clientes simultâneos, com pico de 11.

python 2.6 e concatenação de strings

Nerdeando no Python Brasil [6], alguém comentou que concatenação de strings é um caso que foi otimizado, e resolvemos testar. Não é que foi otimizado, mesmo?


concatena.py:
s = ''
for a in range(1000000):
s += 'a'

lista.py:
s = ''
lista = []
for a in range(1000000):
lista.append('a')
s = ''.join(lista)


python -V
Python 2.6.1

time python lista.py ; time python concatena.py

real 0m0.298s
user 0m0.248s
sys 0m0.046s

real 0m0.292s
user 0m0.250s
sys 0m0.039s