<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Born to be Geek</title>
	<atom:link href="http://blog.davialexandre.com.br/feed/" rel="self" type="application/rss+xml" />
	<link>http://blog.davialexandre.com.br</link>
	<description>Programação, tecnologia, linux, games e qualquer coisa que der na telha =D</description>
	<lastBuildDate>Sat, 14 Apr 2012 21:35:09 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.3.2</generator>
		<item>
		<title>AttributesBackupBehavior extension for the Yii Framework</title>
		<link>http://blog.davialexandre.com.br/2012/01/13/attributesbackupbehavior-extension-for-the-yii-framework/</link>
		<comments>http://blog.davialexandre.com.br/2012/01/13/attributesbackupbehavior-extension-for-the-yii-framework/#comments</comments>
		<pubDate>Fri, 13 Jan 2012 03:57:09 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[desenvolvimento]]></category>
		<category><![CDATA[php]]></category>
		<category><![CDATA[programação]]></category>
		<category><![CDATA[yii framework]]></category>
		<category><![CDATA[active record]]></category>
		<category><![CDATA[extension]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=92</guid>
		<description><![CDATA[Sometimes, when using ActiveRecord, we need to know if some attribute value has changed after it was loaded from the database. To make things easier and avoid duplicated code, I created this behavior to help me with this task. Basically, what it does is to make a copy of all attributes values from the object, [...]]]></description>
			<content:encoded><![CDATA[<p>Sometimes, when using ActiveRecord, we need to know if some attribute value has changed after it was<br />
loaded from the database. To make things easier and avoid duplicated code, I created this behavior<br />
to help me with this task. Basically, what it does is to make a copy of all attributes values from<br />
the object, right after it is loaded from the database, so the behavior can work with this original<br />
values to know if any of them was changed.</p>
<p><strong>Usage</strong><br />
The behavior usage is pretty simple. First, add the behavior to the ActiveRecord where you intend to<br />
use it:</p>
<pre class="brush: php">
&lt;?php
class User extends ActiveRecord {
	...
	public function behaviors() {
		return array(
			&#039;AttributesBackupBehavior&#039; =&gt; &#039;ext.AttributesBackupBehavior&#039;,
		);
	}
	...
}
?&gt;
</pre>
<p>After this, 3 new methods will be added to your User class: attributesChanged(), attributeChanged()<br />
and getOldAttributeValue().</p>
<p>Below is a description of it:</p>
<p><strong><em>attributesChanged()</em></strong><br />
With this method you can check if any of the object attributes was changed after it was loaded from<br />
the database:</p>
<pre class="brush: php">
&lt;?php
$user = User::model()-&gt;find(); // User-&gt;status == &#039;Active&#039;
var_dump($user-&gt;attributesChanged()); // FALSE
$user-&gt;status = &#039;Inactive&#039;;
var_dump($user-&gt;attributesChanged()); // TRUE
?&gt;
</pre>
<p><strong><em>attributeChanged()</em></strong><br />
This should be used when you want to know if a specific attribute value was changed:</p>
<pre class="brush: php">
&lt;?php
$user = User::model()-&gt;find(); // User-&gt;status == &#039;Active&#039;
$user-&gt;status = &#039;Inactive&#039;;
var_dump($user-&gt;attributeChanged(&#039;email&#039;)); // FALSE
var_dump($user-&gt;attributeChanged(&#039;status&#039;)); // TRUE
?&gt;
</pre>
<p><em><strong>getOldAttributeValue()</strong></em><br />
In case you need to retrieve the original value loaded from the database, this is the method you gonna use:</p>
<pre class="brush: php">
&lt;?php
$user = User::model()-&gt;find(); // User-&gt;status == &#039;Active&#039;
$user-&gt;status = &#039;Inactive&#039;;
var_dump($user-&gt;getOldAttributeValue(&#039;status&#039;)); // &#039;Active&#039;
?&gt;
</pre>
<p>Besides those three methods, there&#8217;s also one property that can be configured in this behavior:<br />
<em>$reloadAfterSave</em>.</p>
<p>By default, after you call the ActiveRecord save method, the old attributes will be erased and filled<br />
with the just saved new ones, show it will reflect the stored record. If for some reason you want<br />
to keep the original loaded values, you need to set <em>$reloadAfterSave</em> as false:</p>
<pre class="brush: php">
&lt;?php
class User extends ActiveRecord {
	...
	public function behaviors() {
		return array(
			&#039;AttributesBackupBehavior&#039; =&gt; array(
				&#039;class&#039; =&gt; &#039;ext.AttributesBackupBehavior&#039;,
				&#039;reloadAfterSave&#039; =&gt; false,
		);
	}
	...
}
?&gt;
</pre>
<p>You can donwload the extension from its page at the Yii Framework site: <a href="http://www.yiiframework.com/extension/attributesbackupbehavior/" title="http://www.yiiframework.com/extension/attributesbackupbehavior/" target="_blank">http://www.yiiframework.com/extension/attributesbackupbehavior/</a></p>
<p>You can also fork the projet at Github: <a href="https://github.com/davialexandre/AttributesBackupBehavior" title="https://github.com/davialexandre/AttributesBackupBehavior" target="_blank">https://github.com/davialexandre/AttributesBackupBehavior</a></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2012/01/13/attributesbackupbehavior-extension-for-the-yii-framework/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Trabalhando com contadores utilizando o ActiveRecord no Yii Framework</title>
		<link>http://blog.davialexandre.com.br/2011/12/02/trabalhando-com-contadores-utilizando-o-activerecord-no-yii-framework/</link>
		<comments>http://blog.davialexandre.com.br/2011/12/02/trabalhando-com-contadores-utilizando-o-activerecord-no-yii-framework/#comments</comments>
		<pubDate>Fri, 02 Dec 2011 16:36:47 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[desenvolvimento]]></category>
		<category><![CDATA[php]]></category>
		<category><![CDATA[programação]]></category>
		<category><![CDATA[tutorial]]></category>
		<category><![CDATA[yii framework]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=83</guid>
		<description><![CDATA[Vamos supor, por exemplo, que você está desenvolvendo um blog ou algum outro tipo de CMS e quer registrar o número de vezes que cada post foi acessado (talvez para mostrar uma lista dos mais visitados). A maneira mais fácil de fazer isso é adicionar uma coluna na tabela de posts, que será utilizada para [...]]]></description>
			<content:encoded><![CDATA[<p>Vamos supor, por exemplo, que você está desenvolvendo um blog ou algum outro tipo de CMS e quer registrar o número de vezes que cada post foi acessado (talvez para mostrar uma lista dos mais visitados).</p>
<p>A maneira mais fácil de fazer isso é adicionar uma coluna na tabela de posts, que será utilizada para armazenar o número de visitas para aquele item. Cada vez que um post for exibido o valor dessa coluna será aumentado em 1. O código para fazer isso é algo parecido com isso:</p>
<pre class="brush: php">
public function actionView($id) {
    $post = Post::model()-&gt;findByPk($id);
    $post-&gt;visitas += 1;
    $post-&gt;save();
    $this-&gt;render(&#039;view&#039;, array(&#039;post&#039; =&gt; $post));
}
</pre>
<p>Essa abordagem tem dois problemas. Queremos atualizar apenas a coluna visitas, mas todo o registro do post será atualizado. Além disse, caso o argumento false não seja passado para o método save, todo o processo de validação será executado.</p>
<p>Desde a versão 1.1.8, a classe CActiveRecord tem um método que pode nos ajudar com isso. Trata-se do método <a href="http://www.yiiframework.com/doc/api/1.1/CActiveRecord#saveCounters-detail" target="_blank" title="CActiveRecord::saveCounters()">CActiveRecord::saveCounters()</a> e a sua utilização é muito simples:</p>
<pre class="brush: php">
public function actionView($id) {
    $post = Post::model()-&gt;findByPk($id);
    $post-&gt;saveCounters(array(&#039;visitas&#039;=&gt;1));
    $this-&gt;render(&#039;view&#039;, array(&#039;post&#039; =&gt; $post));
}
</pre>
<p>Com isso, somente a coluna visitas será atualizada e a validação não será disparada.</p>
<p>Caso você ainda não utilize a versão 1.1.8, você pode utilizar o método <a href="http://www.yiiframework.com/doc/api/1.1/CActiveRecord#updateCounters-detail" target="_blank" title="CActiveRecord::updateCounters()">CActiveRecord::updateCounters()</a>:</p>
<pre class="brush: php">
public function actionView($id) {
    $post = Post::model()-&gt;findByPk($id);
    $post-&gt;updateCounters(
        array(&#039;visitas&#039;=&gt;1),
        array(&#039;condition&#039; =&gt; &quot;id = :id&quot;),
        array(&#039;:id&#039; =&gt; $this-&gt;id),
    );
    $this-&gt;render(&#039;view&#039;, array(&#039;post&#039; =&gt; $post));
}
</pre>
<p>O trecho de código acima faz exatamente o mesmo que o saveCounters. Note que o método updateCounters tem dois parâmetros a mais. Depois de informar a coluna utilizada para contar, é preciso passar uma condição que diz qual registro deverá ser atualizado. Se você utilizou algum parâmetro nessa condição (como o &#8220;:id&#8221;), você também deve informar o valor dele, utilizando o terceiro argumento do método.</p>
<p><strong>Importante: Se você não informar nenhuma condição, todos os registros serão atualizados.</strong></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2011/12/02/trabalhando-com-contadores-utilizando-o-activerecord-no-yii-framework/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Working with counters using the ActiveRecord in Yii Framework</title>
		<link>http://blog.davialexandre.com.br/2011/12/01/working-with-counters-using-the-activerecord-in-yii-framework/</link>
		<comments>http://blog.davialexandre.com.br/2011/12/01/working-with-counters-using-the-activerecord-in-yii-framework/#comments</comments>
		<pubDate>Fri, 02 Dec 2011 02:04:43 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[desenvolvimento]]></category>
		<category><![CDATA[php]]></category>
		<category><![CDATA[programação]]></category>
		<category><![CDATA[tutorial]]></category>
		<category><![CDATA[yii framework]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=78</guid>
		<description><![CDATA[Let&#8217;s say, for example, that you are developing a blog or some kind of CMS and you want to track the number of times each post was viewed (maybe to show a list of the most viewed ones). The easier way to do that is by adding a column to the post table, which will [...]]]></description>
			<content:encoded><![CDATA[<p>Let&#8217;s say, for example, that you are developing a blog or some kind of CMS and you want to track the number of times each post was viewed (maybe to show a list of the most viewed ones).</p>
<p>The easier way to do that is by adding a column to the post table, which will be used to store the number of visits of that item. Each time the post is displayed the value of this column will be increased by 1. The code for this would be something like:</p>
<pre class="brush: php">
public function actionView($id) {
    $post = Post::model()-&gt;findByPk($id);
    $post-&gt;visits += 1;
    $post-&gt;save();
    $this-&gt;render(&#039;view&#039;, array(&#039;post&#039; =&gt; $post));
}
</pre>
<p>We have two problems with this approach. All we want is to update the visits column, but the entire record will be updated. Also, if we didn&#8217;t pass the false argument to the save method, all the validation process will be executed.</p>
<p>Since 1.1.8, the CActiveRecord class has a method that can help us with this task. It&#8217;s the <a href="http://www.yiiframework.com/doc/api/1.1/CActiveRecord#saveCounters-detail" target="_blank" title="CActiveRecord::saveCounters()">CActiveRecord::saveCounters()</a> method and its usage is pretty simple:</p>
<pre class="brush: php">
public function actionView($id) {
    $post = Post::model()-&gt;findByPk($id);
    $post-&gt;saveCounters(array(&#039;visits&#039;=&gt;1));
    $this-&gt;render(&#039;view&#039;, array(&#039;post&#039; =&gt; $post));
}
</pre>
<p>With this, only the visits column will be updated and the validation will not be triggered.</p>
<p>If you&#8217;re not using the 1.1.8 yet, there&#8217;s the <a href="http://www.yiiframework.com/doc/api/1.1/CActiveRecord#updateCounters-detail" target="_blank" title="CActiveRecord::updateCounters()">CActiveRecord::updateCounters()</a> method:</p>
<pre class="brush: php">
public function actionView($id) {
    $post = Post::model()-&gt;findByPk($id);
    $post-&gt;updateCounters(
        array(&#039;visits&#039;=&gt;1),
        array(&#039;condition&#039; =&gt; &quot;id = :id&quot;),
        array(&#039;:id&#039; =&gt; $this-&gt;id),
    );
    $this-&gt;render(&#039;view&#039;, array(&#039;post&#039; =&gt; $post));
}
</pre>
<p>The piece of code above does exactly the same that saveCounters does. Note that updateCounters has two additional parameters. After the column used to count, we pass a condition to tell which record(s) should be updated. If you used any paramater in this condition (like the &#8220;:id&#8221;), you should pass the parameter value in the third argument of the method.</p>
<p><strong>Important: If you do not pass a condition, all records will be updated.</strong></p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2011/12/01/working-with-counters-using-the-activerecord-in-yii-framework/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Backup simples com Incron+rsync+Dropbox</title>
		<link>http://blog.davialexandre.com.br/2010/03/31/backup-simples-com-incronrsyncdropbox/</link>
		<comments>http://blog.davialexandre.com.br/2010/03/31/backup-simples-com-incronrsyncdropbox/#comments</comments>
		<pubDate>Wed, 31 Mar 2010 03:05:40 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[backup]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[tutorial]]></category>
		<category><![CDATA[dropbox]]></category>
		<category><![CDATA[incron]]></category>
		<category><![CDATA[rsync]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=69</guid>
		<description><![CDATA[Eu ja perdi um HD cheio de coisas importantes. Foi assim que aprendi a importância do backup; o que não quer dizer que eu o faça. Contudo, recentemente o disco do meu notebook começou a dar sinais de que está agonizando. Na verdade, não sei se trata-se apenas de problemas no sistema de arquivos ou [...]]]></description>
			<content:encoded><![CDATA[<p>Eu ja perdi um HD cheio de coisas importantes. Foi assim que aprendi a importância do backup; o que não quer dizer que eu o faça.</p>
<p>Contudo, recentemente o disco do meu notebook começou a dar sinais de que está agonizando. Na verdade, não sei se trata-se apenas de problemas no sistema de arquivos ou um falha de hardware iminente, mas os constantes erros me trouxeram más lembranças e me deixaram com medo.</p>
<p>Desde a perda do primeiro HD, tenho procurado uma solução simples e eficiente para backups. Tenho pensando bastante em um NAS, com suporte a RAID ou um PC Mini-ITX. Enquanto o dinheiro não vem, e os erros aumentam,  encontrei uma solução mais simples para o backup de meus arquivos, composta dos seguintes itens:</p>
<p><span id="more-69"></span></p>
<p><strong><a href="http://inotify.aiken.cz/?section=incron&amp;page=about&amp;lang=en" target="_blank">Incron</a></strong><br />
É um cron para o sistema de arquivos. Trabalha junto com o inotify e permite agendar comandos que são executados como resposta a eventos em diretórios e arquivos. Utilizo ele para monitorar os itens que quero manter no backup.</p>
<p><strong><a href="http://rsync.samba.org/" target="_blank">Rsync</a></strong><br />
É um programa utilizado para manter a sincronização de arquivos entre dois diretórios diferentes. A grande sacada é a possibilidade de realizar transferência incremental de arquivos. Ou seja, são sincronizados apenas os itens que sofreram alterações. Na minha solução de backup, utilizo ele para sincronizar os arquivos e diretórios que desejo efetuar backup com o diretório do Dropbox.</p>
<p><strong><a href="http://www.dropbox.com" target="_blank">Dropbox</a></strong><br />
O Dropbox é um serviço online de armazenamento de arquivos. Na versão gratuita são oferecidos 2Gb de espaço em disco. Seu instalador possui um daemon que monitora um determinado diretório em seu computador. Qualquer alteração nesse diretório é atualizada na sua cópia online.</p>
<p><strong>Como instalar?</strong><br />
Aqui, no Arch Linux, o processo de instalação foi bastante simples. O incron e o rsync estão disponiveís nos repositórios community e extra, respectivamente. Já o dropbox está disponível no <a href="http://aur.archlinux.org">AUR</a>. Para instalar tudo, bastou o comando:</p>
<p><code>$ yaourt -S incron rsync dropbox</code></p>
<p><strong>Configurando</strong><br />
Antes de tudo, precisamos configurar o Dropbox. Ele deve estar localizado em Aplicativos -&gt; Internet -&gt; Dropbox. Na primeira execução você poderá configura-lo com os dados de sua conta, caso já possua uma, ou criar um nova. Por fim, selecione o diretório que será monitorado pelo daemon.</p>
<p>Agora que você já possui um diretório em seu computador ligado a sua conta do Dropbox, precisamos fazer com que as atualizações nos itens que deseja realizar backup sejam replicadas para o diretório do serviço de armazenamento. Para monitorar essas atualizações vamos utilizar o incron.</p>
<p>Aqui não foi necessário nenhuma configuração do daemon. Entretanto é necessário adiciona-lo a lista de inicialização de daemon no arquivo /etc/rc.conf. Feito isso, basta adicionar as entradas no incrontab, indicando qual diretório/arquivo monitorar, em quais eventos e qual ação a ser executada. Para editar o incrontab, digite:</p>
<p><code>$ incrontab -e </code></p>
<p>Umas das entradas em meu arquivo é:</p>
<p><code>/home/davi/Documentos IN_CREATE,IN_DELETE,IN_MODIFY,IN_MOVE rsync -a --delete /home/davi/Documentos /home/davi/Dropbox/backup</code></p>
<p>Com isso, indico que o incron deve monitorar o diretório /home/davi/Documentos e, cada vez que um arquivo ou diretório seja criado, removido, modificado e movido, deverá executar o comando rsync, sincronizando o diretório monitorado com o diretório /home/davi/Dropbox/backup. Assim que a sincronização for concluída o daemon do Dropbox se encarregará de enviar seus arquivos para o armazenamento online, concluindo o backup.</p>
<p>Após realizar qualquer alteração no incrontrab é necessário recarregar o arquivo através do comando:</p>
<p><code>$ incrontab -d</code></p>
<p>Pronto! Assim concluímos a criação de um sistema simples e prático para backup automático. Por enquanto, pretendo continuar utilizando o Dropbox para armazenar meus arquivos. Futuramente, caso mude a forma de armazenamento, os ajustes necessários serão simples. Na verdade, será necessário apenas alterar o comando rsync para ter como destino o novo local para onde deverá enviar os arquivos.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2010/03/31/backup-simples-com-incronrsyncdropbox/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Plugin Musicbrainz para o Exaile</title>
		<link>http://blog.davialexandre.com.br/2010/01/18/plugin-musicbrainz-para-o-exaile/</link>
		<comments>http://blog.davialexandre.com.br/2010/01/18/plugin-musicbrainz-para-o-exaile/#comments</comments>
		<pubDate>Mon, 18 Jan 2010 17:25:16 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[exaile]]></category>
		<category><![CDATA[plugin]]></category>
		<category><![CDATA[projetos]]></category>
		<category><![CDATA[download]]></category>
		<category><![CDATA[musicbrainz]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=58</guid>
		<description><![CDATA[Por muito tempo eu fui usuário do Amarok. Para mim ele era O music player. Mas um dia resolveram atualiza-lo e lançaram a versão 2.0, uma bela porcaria! Desde então testei diversos tocadores: Listen, RhythmBox e Banshee e nenhum me agradou. Foi então que encontrei o Exaile e gostei. Trata-se de um player leve, escrito [...]]]></description>
			<content:encoded><![CDATA[<p>Por muito tempo eu fui usuário do Amarok. Para mim ele era O music player. Mas um dia resolveram atualiza-lo e lançaram a versão 2.0, uma bela porcaria! Desde então testei diversos tocadores: Listen, RhythmBox e Banshee e nenhum me agradou. Foi então que encontrei o Exaile e gostei.</p>
<p>Trata-se de um player leve, escrito em python e utilizando GTK. Sem frescuras, tem poucos recursos,  praticamente todos os que eu utilizava no Amarok. Até a interface lembra bastante a versão antiga do meu último player. Entretanto senti falta de uma funcionalidade: Preencher as tags do arquivo com informações do <a href="http://musicbrainz.org" target="_blank">Musicbrainz</a>. É comum ter arquivos com tags fora de padrão, ou até mesmo sem nenhuma informação nelas e arrumar isso na mão é um saco. Para resolver o problema, criei um plugin!</p>
<p><span id="more-58"></span></p>
<p>Com o plugin Musicbrainz basta selecionar uma música em sua playlist, clicar com o botão direito e selecionar &#8220;Fill tags with MusicBrainz suggestions&#8221;. Irá surgir uma janela, como na imagem abaixo:</p>
<p style="text-align: center;"><a rel="lightbox" href="http://blog.davialexandre.com.br/wp-content/uploads/2010/01/track_suggestions_sample.png" title="Track Suggestions"><img class="size-medium wp-image-60 aligncenter" title="track_suggestions_sample" src="http://blog.davialexandre.com.br/wp-content/uploads/2010/01/track_suggestions_sample-300x127.png" alt="MusicBrainz Tracks Suggestions" width="300" height="127" /></a></p>
<p>As sugestões estão ordenadas por score. Quanto maior o escore, maior a probabilidade de ser a correta. Para preencher as tags de seu arquivo, basta selecionar a opção que melhor se encaixe no seu caso e clicar em &#8220;Save&#8221;.</p>
<p>Sim, o plugin trabalha apenas com uma música por vez. A idéia não é arrumar toda a sua coleção, mas sim corrigir um ou outro erro em um arquivo. Para recursos mais elaborados você pode utilizar o <a href="http://musicbrainz.org/doc/MusicBrainz_Picard">Picard</a>, da própria Musicbrainz. Entretanto, quem sabe em futuras versões não tenha uma versão mais completa? ;D</p>
<p>Para baixar o plugin utilize o link abaixo. No Exaile, para instalar, vá em Edit &gt; Preferences &gt; Plugins. Clique em <em>Install Plugin File</em> e selecione o arquivo em seu computador. Por fim, habilite o Musicbrainz na lista de plugins!</p>
<div class="downloadbox">
<p class="download">Dowload: <a href="http://davialexandre.com.br/projetos/musicbrainz_plugin/musicbrainz.exz">Musicbrainz plugin para Exaile</a></p>
<p class="version">Versão: 0.0.1</p>
</div>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2010/01/18/plugin-musicbrainz-para-o-exaile/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Let&#8217;s GO! (Instalando o GO)</title>
		<link>http://blog.davialexandre.com.br/2009/11/12/lets-go-instalando-o-go/</link>
		<comments>http://blog.davialexandre.com.br/2009/11/12/lets-go-instalando-o-go/#comments</comments>
		<pubDate>Thu, 12 Nov 2009 03:57:34 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[configuração]]></category>
		<category><![CDATA[GO]]></category>
		<category><![CDATA[linguagens]]></category>
		<category><![CDATA[programação]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=49</guid>
		<description><![CDATA[O Google acaba de lançar sua própria linguagem de programação, a GO. Trata-se de uma liguagem &#8220;meio frankestein&#8221;, com uma sintaxe com características de C/C++, Python, Ruby e alguma outra coisa que eu não consigo identificar. GO é uma linguagem compilada e, até o momento, existem compiladores apenas para ambientes *nix. Acabo de instalar aqui [...]]]></description>
			<content:encoded><![CDATA[<p>O Google acaba de lançar sua própria linguagem de programação, a <a title="Linguagem GO" href="http://golang.org/" target="_blank">GO</a>.</p>
<p>Trata-se de uma liguagem &#8220;meio frankestein&#8221;, com uma sintaxe com características de C/C++, Python, Ruby e alguma outra coisa que eu não consigo identificar.</p>
<p>GO é uma linguagem compilada e, até o momento, existem compiladores apenas para ambientes *nix. Acabo de instalar aqui no meu Xubuntu e o processo foi bastante simples.</p>
<p><span id="more-49"></span></p>
<p>Primeiro é necessário configurar algumas variáveis de ambiente:</p>
<ul>
<li>$GOROOT &#8211; A raiz da estrutura de diretórios do GO. Vamos utilizar $HOME/go.</li>
<li>$GOOS  &#8211; O sistema operacional que estamos utilizando. No meu caso linux.</li>
<li>$GOARCH &#8211; A arquitetura do sistema operacional. No meu caso 386. Para quem tem sistemas 64bits, utilize amd64.</li>
<li>$GOBIN &#8211; Essa é opcional e trata-se do diretório onde ficarão os binários do GO. Por padrão utiliza o diretório $HOME/bin, <strong>que já deve estar em seu PATH e existir</strong>.</li>
</ul>
<p>Para adicionar essas variáveis ao seu sistema, edite o arquivo ~/.bashrc:</p>
<pre>$ vim ./bashrc</pre>
<p>No fim do arquivo adicione as seguintes linhas:</p>
<pre>export GOROOT=$HOME/go
export GOOS=linux
export GOARCH=386
export PATH=$PATH:$HOME/bin</pre>
<p>Caso o diretório $HOME/bin não exista, você deverá cria-lo.<strong> É preciso sair e entrar novamente no terminal para que essas alterações tenham efeito.</strong></p>
<p>Com o sistema configurado, precisamos instalar algumas ferramentas para compilar o compilador do GO. Utilize:</p>
<pre>$ sudo apt-get install mercurial bison gcc libc6-dev ed</pre>
<p>Com as ferramentas instaladas, devemos baixar o código fonte do repositório do GO. Utilize:</p>
<pre>$ hg clone -r release <a href="https://go.googlecode.com/hg/" rel="nofollow">https://go.googlecode.com/hg/</a> $GOROOT</pre>
<p>Ao término da cópia dos arquivos, entre no diretório $GOROOT/src:</p>
<p><code>$cd $GOROOT/src</code></p>
<p>E execute:</p>
<p><code>$ ./all.bash</code></p>
<p>Aguarde a compilação. Ao término, caso tudo ocorra bem você deverá ler a mensagem:</p>
<p><code>--- cd ../test<br />
N known bugs; 0 unexpected bugs</code></p>
<p>Podem acontecer alguns erros durante a compilação. Aqui, ocorreu um durante a teste da lib net, onde é realizada uma tentativa de conexão com o google. Nesse caso, bastou indicar ao processo que essa biblioteca não deveria ser testada. Para isso, editei o arquivo $GOROOT/src/pkg/Makefile, e, no item NOTEST, adicione um novo item &#8220;net\&#8221;. Por fim, executei novamente all.bash.</p>
<p>Pronto, agora você já pode começar a brincar com a nova linguagem. Para compilar utilize:</p>
<p><code>$ 8g arquivo.go &amp;&amp; 8l arquivo.8</code></p>
<p>Será criado o executavel arquivo.out.</p>
<p>Caso utilize um sistema 64bits, troque o 8 pelo 6:</p>
<p><code>$ 6g arquivo.go &amp;&amp; 6l arquivo.6</code></p>
<p>Agora, restar estudar a linguagem e ver do que ela é capaz =D</p>
<p>Para mais informações, alguns links:</p>
<ul>
<li><a href="http://golang.org/doc/go_tutorial.html" target="_blank">Tutorial</a> &#8211; Resumo geral da linguagem. Ideal para quem está começando.</li>
<li><a href="http://golang.org/doc/effective_go.html" target="_blank">Effective GO</a> &#8211; Documentação detalhada sobre a sintaxe da linguagem.</li>
<li><a href="http://golang.org/cmd/" target="_blank">Documentação dos comandos</a></li>
<li><a href="http://golang.org/pkg/" target="_blank">Documentação dos pacotes e bibliotecas</a></li>
<li><a href="http://groups.google.com/group/golang-nuts" target="_blank">Lista de discussão GO-Nuts</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2009/11/12/lets-go-instalando-o-go/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Instalando o Ubuntu 8.10 no notebook Kennex U50SA</title>
		<link>http://blog.davialexandre.com.br/2009/03/08/instalando-o-ubuntu-810-no-notebook-kennex-u50sa/</link>
		<comments>http://blog.davialexandre.com.br/2009/03/08/instalando-o-ubuntu-810-no-notebook-kennex-u50sa/#comments</comments>
		<pubDate>Sun, 08 Mar 2009 04:02:34 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[configuração]]></category>
		<category><![CDATA[linux]]></category>
		<category><![CDATA[notebook]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=40</guid>
		<description><![CDATA[Acabo de comprar um notebook. O modelo escolhido foi o Kennex U50SA. Como a Kennex, em um raro momento de sabedoria, não considera a troca de sistema operacional um procedimento que viola a garantia do produto, a primeira coisa que fiz foi remover o Insigne Linux que vem instalado no notebook e instalar o Windows [...]]]></description>
			<content:encoded><![CDATA[<p>Acabo de comprar um notebook. O modelo escolhido foi o <a href="http://www.kennex.com.br/u502370.html" target="_blank">Kennex U50SA.</a></p>
<p>Como a Kennex, em um raro momento de sabedoria, não considera a troca de sistema operacional um procedimento que viola a garantia do produto, a primeira coisa que fiz foi remover o <a href="http://www.insignesoftware.com/default.php" target="_blank">Insigne Linux</a> que vem instalado no notebook e instalar o <a href="http://www.microsoft.com/windows/windows-7/default.aspx" target="_blank">Windows 7</a> em dual boot com o <a href="http://ubuntu.com" target="_blank">Ubuntu 8.10</a>.</p>
<p>A instalação do Windows 7 ocorreu sem nenhum problema. Tudo funcionando perfeitamente nesse sistema. Ao término da instalação somente foi necessário instalar os drivers da placa de rede com e sem fio.</p>
<p>Já para a instalação do Ubuntu são necessárias algumas configurações.</p>
<p><span id="more-40"></span>Ao inicializar o computador através do live cd, será preciso apertar a tecla F6, para selecionar outras opções de boot. Marque a opção <em>&#8220;nolapic&#8221;</em>. Somente assim você conseguirá iniciar  e instalar o sistema através do cd.</p>
<p>Após instalar o sistema não será possível dar boot pelo Ubuntu. Para isso, serão necessárias algumas configurações no GRUB, o gerenciado de boot utilizado pelo Ubuntu.</p>
<p>Ao iniciar, quando exibida a tela de opções para escolher o sistema operacional a ser iniciado, selecione o Ubuntu e pressione a tecla <em>&#8220;e&#8221;</em>, para editar as opções de boot. Você deverá adicionar ao final da terceira linha, os seguintes parâmetros:</p>
<p><code style="linux-code">noapic pci=assign-busses apicmaintimer idle=poll</code></p>
<p>Feito isso, pressione <em>&#8220;b&#8221;</em>, para iniciar o sistema.</p>
<p>Com o Ubuntu em execução, adicione os mesmos parâmetros diretamente ao arquivo menu.lst de seu GRUB. Para isso acesse o seu terminal (Aplicativos &gt; Acessórios &gt; Consola), e execute o comando:</p>
<p><code style="linux-code">sudo su</code></p>
<p>Assim você ganhará permissões de administrador para executar as alterações necessárias no arquivo. Para edita-lo  execute:</p>
<p><code>vim /boot/grub/menu.lst</code></p>
<p>Procure neste arquivo pela mesma linha que você editou na inicialização do computador. Por padrão, ela deve ser a 4ª linha encontrada logo abaixo do texto:</p>
<pre>## ## End Default Options ##</pre>
<p>Lá, assim como feito antes, você deverá adicionar os parâmetros de inicialização citados acima. Para habilitar a edição de textos no Vim, você deve pressionar a tecla <em>&#8220;i&#8221;</em>.</p>
<p>Para salvar as alterações, pressione <em>&#8220;esc&#8221;</em> e, em seguida, digite :wq e pressione <em>&#8220;enter&#8221;</em>. Pronto! Todas as alterações necessárias foram realizadas. Agora seu sistema operacional poderá ser iniciado sem nenhum problema.</p>
<p>O Ubuntu é uma excelente escolha para esse notebook!. Tudo funciona perfeitamente, sem necessidade de nenhuma configuração.</p>
<p>Logo mais irei fazer uma análise mais detalhada do novo notebook, que, já adiantando, tem uma performance bastante impressionante!</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2009/03/08/instalando-o-ubuntu-810-no-notebook-kennex-u50sa/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Apostilas de Gimp, OpenOffice e outros</title>
		<link>http://blog.davialexandre.com.br/2009/02/10/apostilas-de-gimp-openoffice-e-outros/</link>
		<comments>http://blog.davialexandre.com.br/2009/02/10/apostilas-de-gimp-openoffice-e-outros/#comments</comments>
		<pubDate>Wed, 11 Feb 2009 00:26:52 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[apostilas]]></category>
		<category><![CDATA[software livre]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=38</guid>
		<description><![CDATA[Desde 1997 o Metrô de São Paulo, gradativamente, vem substituindo softwares proprietários em suas estações de trabalho por equivalentes livres. Segundo informações da Companhia, apenas a substituição do Ms Office pelo OpenOffice gerou uma economia de aproximadamente R$ 1,4 milhões por ano. Durante esse período de transição, a equipe de TI do Metrô desenvolveu algumas [...]]]></description>
			<content:encoded><![CDATA[<p>Desde 1997 o <a href="http://www.metro.sp.gov.br" target="_blank">Metrô de São Paulo</a>, gradativamente, vem substituindo softwares proprietários em suas estações de trabalho por equivalentes livres. Segundo informações da Companhia, apenas a substituição do Ms Office pelo <a href="http://broffice.org" target="_blank">OpenOffice</a> gerou uma economia de aproximadamente R$ 1,4 milhões por ano.</p>
<p>Durante esse período de transição, a equipe de TI do Metrô desenvolveu algumas apostilas utilizadas para treinamentos dos funcionários da empresa. Seguindo a filosofia do software livre, as apostilas desenvolvidas foram disponibilizadas livremente para download no seguinte endereço:</p>
<p><a href="http://www.metro.sp.gov.br/diversos/download/tedownload.asp" target="_blank">http://www.metro.sp.gov.br/diversos/download/tedownload.asp</a></p>
<p>Na página acima é possível encontrar apostilas de GIMP, Gantt Project, Firefox, Thunderbird e OpenOffice.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2009/02/10/apostilas-de-gimp-openoffice-e-outros/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Uma lista, muitas opções</title>
		<link>http://blog.davialexandre.com.br/2009/02/02/uma-lista-muitas-opcoes/</link>
		<comments>http://blog.davialexandre.com.br/2009/02/02/uma-lista-muitas-opcoes/#comments</comments>
		<pubDate>Mon, 02 Feb 2009 19:08:05 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[CSS]]></category>
		<category><![CDATA[desenvolvimento]]></category>
		<category><![CDATA[HTML]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=35</guid>
		<description><![CDATA[Procurando uma solução para um menu com listas aninhadas, acabei encontrando o site da Maxdesign e sua seção de CSS. Lá você encontra o Listutorial, um tutorial mostrando o básico sobre formatação de listas com CSS. Além disso temos o Listmatic e o Listmatic2. Nessas seções o pessoal da maxdesign parte da idéia de &#8220;Uma [...]]]></description>
			<content:encoded><![CDATA[<p>Procurando uma solução para um menu com listas aninhadas, acabei encontrando o site da <a href="http://maxdesign.com.au" target="_blank">Maxdesign</a> e sua seção de <a href="http://css.maxdesign.com.au" target="_blank">CSS</a>.</p>
<p>Lá você encontra o <a href="http://css.maxdesign.com.au/listutorial/" target="_blank">Listutorial</a>, um tutorial mostrando o básico sobre formatação de listas com <abbr title="Cascading Style Sheet">CSS</abbr>. Além disso temos o <a href="http://css.maxdesign.com.au/listamatic/" target="_blank">Listmatic</a> e o <a href="http://css.maxdesign.com.au/listamatic2" target="_blank">Listmatic2</a>. Nessas seções o pessoal da maxdesign parte da idéia de &#8220;Uma lista, muitas opções&#8221; e mostram como é possível, a partir de uma simples lista, criar os mais diversos tipos de menus. Em Listmatic, existem vários exemplos utilizando um lista não ordenada simples, já em Listmatic2 os exemplos utilizam uma lista não ordenada aninhada.</p>
<p>Todos os exemplos utilizam apenas CSS e HTML e possuem uma tabela de compatibilidade com navegadores.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2009/02/02/uma-lista-muitas-opcoes/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Evitando a fadiga com Python</title>
		<link>http://blog.davialexandre.com.br/2009/01/13/evitando-a-fadiga-com-python/</link>
		<comments>http://blog.davialexandre.com.br/2009/01/13/evitando-a-fadiga-com-python/#comments</comments>
		<pubDate>Wed, 14 Jan 2009 00:58:46 +0000</pubDate>
		<dc:creator>davi</dc:creator>
				<category><![CDATA[preguiça]]></category>
		<category><![CDATA[programação]]></category>
		<category><![CDATA[python]]></category>

		<guid isPermaLink="false">http://blog.davialexandre.com.br/?p=23</guid>
		<description><![CDATA[Desde pequeno aprendi com Jaiminho à evitar a fadiga. Faz bem para a saúde. Foi assim que resolvi desenvolver um script para baixar imagens de sites. Várias vezes gastei meu dedo, clicando com o botão direito do mouse sobre imagens e mais imagens e escolhendo &#8220;salvar como&#8221;. Agora, com o script, basta apenas informar a [...]]]></description>
			<content:encoded><![CDATA[<p>Desde pequeno aprendi com Jaiminho à evitar a fadiga. Faz bem para a saúde.</p>
<p>Foi assim que resolvi desenvolver um script para baixar imagens de sites. Várias vezes gastei meu dedo, clicando com o botão direito do mouse sobre imagens e mais imagens e escolhendo &#8220;salvar como&#8221;. Agora, com o script, basta apenas informar a url da página com as imagens e todo o trabalho é feito em alguns segundos (ou minutos, dependendo do tamanho da imagem):</p>
<pre class="brush: python">
import urllib
import re

for img in re.findall(&quot;&lt;img .*?src=\&quot;(.+?)\&quot;&quot;, urllib.urlopen(&quot;<a href="http://www.uol.com.br&#038;quot" rel="nofollow">http://www.uol.com.br&#038;quot</a>;).read()):
    arq_imagem = open(img[img.rfind(&#039;/&#039;) + 1:], &#039;wb&#039;)
    arq_imagem.write(urllib.urlopen(img).read())
    arq_imagem.close()
</pre>
<p><span id="more-23"></span>O legal é que o código acima pode facilmente ser convertido para baixar imagens de toda uma galeria. Por exemplo, imagine um site onde a galeria siga um padrão para urls como este:</p>
<p><a href="http://www.exemplo.com.br/galerias/0001/imagens.html" rel="nofollow">http://www.exemplo.com.br/galerias/0001/imagens.html</a></p>
<p>Para baixar, por exemplo, as 100 primeiras galerias:</p>
<pre class="brush: python">

import urllib
import re

for galeria in range(100):
    url = &quot;<a href="http://www.exemplo.com.br/galerias/&#038;quot" rel="nofollow">http://www.exemplo.com.br/galerias/&#038;quot</a>; + (&quot;%04d&quot; % (galeria + 1)) + &quot;/imagens.html&quot;

    for img in re.findall(&quot;&lt;img .*?src=\&quot;(.+?)\&quot;&quot;, urllib.urlopen(url).read()):
        arq_imagem = open(img[img.rfind(&#039;/&#039;) + 1:], &#039;wb&#039;)
        arq_imagem.write(urllib.urlopen(img).read())
        arq_imagem.close()

    galeria += 1
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.davialexandre.com.br/2009/01/13/evitando-a-fadiga-com-python/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

