Dopo aver visto a grandi linee come funziona Git adesso ci occupiamo di quello che reputo il più agguerrito concorrente di Git: Bazaar. Bazaar ha un vantaggio fondamentale: è supportato da Launchpad, la migliore e la più completa piattaforma di project-hosting a mio avviso. Contro bazaar pendono soprattutto due critiche: bazaar è mediamente più lento di Git e più insicuro in quanto l’algoritmo crittografico di Git è praticamente inviolabile mentre bazaar è leggermente meno sicuro.

Ciò non toglie che per quei progetti che non siano immensi le differenze sono trascurabili.

Vediamo come utilizzare bazaar:

Innanzitutto dobbiamo presentarci. Per fare questo utilizziamo i comandi:

$ bzr whoami "Bill Gates <ilovemac@gmail.com>"

Una volta fatto ciò andiamo nella cartella del nostro progetto e diamo:

$ bzr init
$ bzr add

In questo modo tutta la cartella verrà ricorsivamente aggiunta al sistema. Confermiamo con:

$ bzr commit -m "First commit"

Adesso si può inviare il progetto su launchpad con:

$ bzr push bzr+ssh://bill.gates@bazaar.launchpad.net/~bill.gates/+junk/myproject

Come avete visto bazaar è leggermente più intuitivo e permette un più facile management.

Con questi pochi semplici comandi potete già cominciare a lavorare. ;)

Quello che personalmente mi mancha è una gui potente come quella di Git. Ma vedrò di fare qualche ricerca.

 

Ho letto quasi una settimana fa la notizia che nella release 2.6.32 del kernel linux udev verrà inesorabilmente spazzato via per far spazio a devtmpfs. Ammetto con onestà che la mia conoscenza di linux in modo più dettagliato è cominciata con il rilascio della serie 2.6. Proprio la serie che ha inserito udev all’interno del kernel al posto di devfs. Quindi ho cercato di informarmi al riguardo delle poco lusinghiere valutazioni di devfs.

Per chi non lo sapesse udev è il sistema grazie al quale viene gestita la creazione dinamica delle periferiche in /dev. Infatti, diversamente dai sistemi Unix tradizionali, Linux mantiene dinamicamente il contenuto di /dev visualizzando solo i nodi associati a periferiche attualmente collegate al pc.

Udev soppiantò devfs per due ragioni fondamentali:

  • Udev supporta un naming persistente dei device. Ovvero le periferiche vengono associati a file il cui nome non dipende dall’ordine in cui le periferiche vengono collegate al pc. Il nome è legato a come sono connessi a livello hardware i vari device.
  • Udev lavora in user space mentre devfs lavora in kernel space.

Nonostante ciò devfs è utilizzato da ogni altro sistema Unix: Solaris, Mac OS X, FreeBSD, DragonFly BSD. Questo rende Linux sicuramente un po più avanzato rispetto ai concorrenti. Infatti i due punti sopracitati oltre a complicare e a rendere meno pratico il popolamento e la gestione di /dev offrono il fianco ad alcuni attacchi di privilege escalation.

Linux però non si accontenta. Scarta anche udev per devtmpfs. Questa nuova implementazione offre un approccio ibrido kernel-user e il conseguente popolamento di /dev fin dalle primissime fasi di boot.

Questa scelta ha però suscitato violente reazioni dagli osteggiatori di devfs che hanno rinominato in modo dispreggiativo il nuovo device file system con il nome di devfs2.

Onestamente ho letto le motivazioni ed alcuni commenti al riguardo qui e qui e le trovo sensate. Stando a quello che ho letto penso che devtmpfs possa essere un buon passo in avanti anche se non so quanto significativo.

Altra questione che mi preoccupava era il passaggio di versione. Come si comporta la distribuzione nel passaggio da udev a devtmpfs? La questione è spinosa e importante per molti motivi. Io utilizzo una rolling distro e passaggi molto pesanti sono sempre un piccolo rischio. Ma non solo. La versione 2.6.32 del kernel sarà anche quella della nuova probabile LTS di Ubuntu, 10.4 Lucid Lynx.

Il passaggio sembra però essere del tutto indolore. Comunque è ancora troppo presto per poter dare giudizi. La questione è accesa.

 

Lo so. La versione 0.13 è stata rilasciata il 27 luglio e non è quindi una news tanto new. Ma solo da ieri è stata inserita nei repository Unstable di Debian e quindi disponibile agli utenti debian e sidux senza doversi ricompilare a mano i sorgenti.

La versione 0.13 introduce le chiamate vocali tramite Jabber/GTalk. Cosa veramente utile in un panorama in cui l’unico modo, e se non unico sicuramente più diffuso, di comunicare vocalmente tramite IM era atraverso software proprietari quali MSN e Skype.

Se usate psi vi sarà senz’altro arrivato l’aggiornamento alla versione 0.13. Ma da sola questa non basta per accedere alle chiamate vocali. Dobbiamo perciò installare il pacchetto psimedia.

# apt-get install psimedia

Adesso basta avviare Psi e troverete l’opzione per lanciare una chiamata vocale. Non ha ancora supporto per le video chiamate ma sicuramente da oggi avrò meno motivi per utilizzare Skype.

 

Vi segnalo che l’aggiornamento di oggi (22-09-09) può dare problemi. In particolare a causa dell’aggiornamento di alcune librerie dist-upgrade rimuove Amarok. Quindi se lo usate vi conviene aspettare un po.

root@siduxbox:/home/laplace# apt-get dist-upgrade -d
Lettura elenco dei pacchetti... Fatto
Generazione albero delle dipendenze       
Lettura informazioni sullo stato... Fatto
Calcolo dell'aggiornamento... Eseguito
I seguenti pacchetti saranno RIMOSSI:
 amarok amarok-dbg amarok-utils libtag-extras0
I seguenti pacchetti saranno aggiornati:
 konversation libtag1-vanilla libtag1c2a os-prober
4 aggiornati, 0 installati, 4 da rimuovere e 0 non aggiornati.
È necessario scaricare 4191kB di archivi.
Dopo quest'operazione, verranno liberati 103MB di spazio su disco.

EDIT: 23-09-09 – Il problema è stato risolto. La versione di amarok è stata ggiornata alla 2.2rc1.

 
Aaaaaargh!

Aaaaaargh!

PROTOCOLLO DI TRASFERIMENTO IN PRATICA – INVIO

Per questo punto abbiamo visto che è necessario serializzare il documento XML in uno stream secondario che useremo per calcolare la dimensione dei dati inviati e che poi riverseremo direttamente nello stream di output del socket.

Continue reading »

 

Perché!? Perché!?

Ho perso settimane alla ricerca di un modo elegante e pulito di trasferire informazioni fra server e client tramite un protocollo basato su XML. Possibile che nessuno abbia fatto una classe nelle librerie standard in grado di trasferire facilmente una manciata di tag XML? Non lo so. Fatto sta che il web non conteneva nessuna risposta alla mia domanda, così, domandando in giro sono arrivato a sviluppare 4 classi in grado di trasferire con un solo comando pacchetti XML attraverso un Socket.

Continue reading »

 

Pylint è uno static checker per Python. Ma fa anche di più.

Pylint non solo ci segnala tutti gli errori di sintassi ma ci indica anche quali convenzioni sul codice abbiamo infranto, dove manca l’adeguata documentazione e se il codice è adeguatamente commentato. Oltre a questo è possibile inserirein Pylint dei plugin per effettuare dei test personalizzati.

Dopo aver installato il rpgramma con

# apt-get install pylint

Ci basta avviarlo con

$ pylint nomescript.py

Il programma ci restituirà una dettagliata lista di warning, error e mancate convenzioni. Alla fine ci restituirà anche un punteggio, compreso fra 0 e 10 (ma vi assicuro che va anche in negativo xD ) che indica la “qualità” del codice. Ovviamente è solo un valore indicativo basato sulla sintassi. Ma è utile per istruire i novellini all’uso di documentazione, commenti e rispetto delle convenzioni. :)

 

La buona programmazione è merce rara. Frotte di programmatori al grido di “basta che funziona” popolano la rete. Hanno codice non commentato, arrabattato, non modulare in cui una classe svolge funzioni di altre classi e non ci si capisce nulla. Evitiamolo.

Le motivazioni sono molteplici: miglior debug, risoluzione dei bug, facilità nella portabilità, estendibilità, maggior comprensione del codice per chi volesse aiutarvi e molto altro.

Un elemento fondamentale di questa programmazione elegante è l’information hiding. Parlerò in dettaglio dell’information hiding nel mio progetto GaPG, vi basti sapere, se non ne siete a conoscenza, che per information hiding si intende la pratica di “nascondere” gli attributi di una classe e renderli accessibili solo tramite funzioni pubbliche chiamate setter, getter e in alcuni linguaggi anche deller.

Ovviamente non devono esistere tutte queste funzioni ogni volta. Sicuramente vogliamo che il nostro attributo sia accessibile all’esterno, quindi sicuramente metteremo sempre un getter. Ma potremmo volere che un certo attributo sia immutabile o, comunque, non possa essere modificato a piacere dall’esterno, e quindi non forniremo tramite attributo di un setter, rendendo così impossibile la modifica esterna.

Questo atteggiamento è spesso incompreso dai programmatori novelli. Essi infatti pensano che sia soltanto una forma di pornografia informatica, un feticismo da nerd. Grave. L’information hiding è la migliore contromisura per ogni sorta di bug. Impedire l’accesso solo a dati “puliti” è essenziale. Tramite un setter ad esempio possiamo controllare che il valore inserito rientri nel range di validità del valore, ad esempio, impedendo che il campo età di Persona possa essere impostato con un età negativa.

Python pecca parecchio da questo punto di vista. E questo è probabilmente il punto debole più vistoso di python. Così nelle versioni si è cercato di “pezzarlo” come si poteva. Python infatti non distingue fra attributi pubblici e attributi privati. Assume che siano sempre pubblici.

Una convenzione molto usata consiste nel anteporre all’attributo un doppio underscore ( _ _ ) in modo da segnalare che quell’attributo è privato. Ad esempio:

class CartaDaGioco():

    def __init__(self,seme,valore):
        self.__seme = seme
        self.__valore = valore

Ma il concetto di privato inserito in questo modo è del tutto relativo. L’unica cosa che fa l’interprete per rendere più scomodo l’accesso a tali attributi è di rinominarli in _CartaDaGioco__seme e in _CartaDaGioco__valore. Questi metodi però restano accessibili per chi ne conosce il nome e sono ancora una forte tentezione.

Python offre però un metodo interessante per disincentivare ulteriormente l’uso scorretto dell’information hiding, offre la possibilità di gestire come se fosse un attributo setter e getter tramite delle variabili “virtuali”. Ma un esempio chiarirà di molto questo concetto in apparenza complesso.

class CartaDaGioco()
    def __init__(self,seme,valore):
        self.__seme = seme
        self.__valore = valore

@property
def valore(self):
return self.__valore

@valore.set
def valore(self,newseme):
if 1<=newseme<11 : self.__valore = newseme

In questo modo, tramite l’uso del decoratore property abbiamo creato un attributo virtuale valore associato all’attributo reale __valore. In questo modo possiamo accedere alla variabile come fosse un normale attributo:

>>> a = CartaDaGioco('bastoni',7)
>>> print(a.valore)
'7'
>>> a.valore = 9
>>> print(a.valore) # il valore è stato modificato perché è un valore valido.
'9'
>>> a.valore = -20
>>> print(a.valore) # il valore non è cambiato perché -20 non è un valore valido.
'9'

Come potete vedere, sebbene l’utilizzo di valore sia completamente uguale all’uso di un attributo abbiamo inserito un “vincolo” ai valori di valore ridefinendo il suo setter. Non specificando nessun setter, inoltre, quando proviamo a scrivere sull’attributo virtuale, ci viene restituito errore. Proprio come volevamo per creare un attributo immutabile.

Il decoratore property permette inoltre di creare attributi fittizi il cui valore è dato dalla combinazioni di attributi reali. Ad esempio se la classe Dipendente ha come unico attributo il campo stipendio possiamo definire con @property un attributo stipendioannuale che restituirà il valore di stipendio moltiplicato per 12.

Insomma. L’uso di property non è obbligatorio ma fornisce quel tocco di eleganza alla vostra programmazione.

Per maggiori informazioni vi rimando alla documentazione ufficiale. :)

Alla prossima.

 

Penso abbiate tutti presente l”utilissima funzione “man”. Man sta per manual anche se io spesso penso derivi da manna in quanto il 90% dei problemi li risolvo grazie a lei. In GNU/Linux la totalità dei programmi ha la sua manpage associata e, grazie ad essa, possiamo sapere vita morte e miracoli di ogni eseguibile o comando sia presente sulla nostra macchina. Ma non solo! Man racchiude anche la sintassi e la semantica completa di praticamente tutte le funzioni e le system call unix. Indispensabile per chi programma in C/C++.

Così noi stiamo preparando il nostro programmino. E perché il nostro dovrebbe essere da meno? Perché il nostro applicativo non deve avere la sua manpage? Perché gettare nella disperazione i nostri utenti?

Infatti non dobbiamo. Impariamo quindi a fare la manpage per il nostro programma!

Creare una manpage è decisamente semplice. Innanzitutto impariamo quelle 7 istruzioni di markup che ci servono:

  • .TH – Indica il titolo della manpage
  • .SH – Indica il titolo della sezione
  • .SS – Indica il titolo della sotto-sezione
  • .pp – Indica l’inizio di un nuovo paragrafo
  • .B – Mostra il testo in grassetto
  • .I – Mostra il testo in corsivo
  • .” – Indica che la riga corrente è un commento (non viene visualizzata nel manuale)

Ora siamo praticamente pronti. Sappiamo tutto quello che ci serve. Apriamo il nostro editor di testo e iniziamo a scrivere la nostra manpage come in questo esempio:

.TH MioSoftware
.SH NAME
MioSoftware Super Calculator
.SH DESCRIPTION
.I MioSoftware
è un programma troppo bello!
.SH URL

http://www.linuxqualityhelp.it

E così via. Fate attenzione che ogni tag deve capitare come primo comando della riga.

A questo punto salviamo il nostro file come, ad esempio, mioprogramma.txt

Adesso dobbiamo copiarlo nella cartella di sistema affinché venga rilevato dal sistema. In debian questa cartella è /usr/share/man

All’interno di questa cartella sono presenti diverse sotto cartelle per indicare le varie “categorie” di manuali. Queste cartelle sono segnate da man1, man2, man3 e così via. Le categorie associate ad ogni numero variano da sistema a sistema ma generalmente sono:

  • 0 – File Header
  • 1 – Comandi Standard (quindi i normali eseguibili)
  • 2 – Kernel System Call
  • 3 – Funzioni Standard della libreria C
  • 4 – Device speciali
  • 5 – Formati di file e convenzioni
  • 6 – Giochi
  • 7 – Varie, ad esempio informazioni sugli standard (ISO)
  • 8 – Comandi root
  • 9 – Dettagli  del Kernel

Noi per esempio inseriremo la nostra man page nella categoria 1. Per farlo basta dare da root:

# cp mioprogramma.txt /usr/share/man/man1/mioprogramma.1

A questo punto abbiamo finito. Per vedere il risultato basta dare:

$ man mioprogramma

E crogiolarsi nella senzazione di “professionalità” che la manpage da al vostro software. :)

Serve aiuto? LQH!

 

Chi utilizza Sidux sa bene che i kernel vengono aggiornati con ritmi che sfiorano il giornaliero. Inoltre, i kernel vecchi, per ragioni di stabilità e sicurezza, non vengono eliminati automaticamente. Questo comporta che nel giro di qualche settimana il tipico utente Sidux si ritrova con almeno 5-6 versioni del kernel installate e 300Mb di spazio utilizzato da cose che, con ogni probabilità, non utilizzeremo mai.

Dobbiamo quindi eliminare i Kernel in eccesso. Innanzitutto identifichiamo tutti i kernel che abbiamo installato con:

# dpkg -l | grep linux-image*

Così abbiamo la lista di tutti i kernel. A questo punto non ci resta che eliminarli con

# apt-get purge linux-image-versione_del_kernel

Vi consiglio di cancellarli tutti ad esclusione di quello attuale (per ovvi motivi) e quello subito precedente (per sicurezza). Per sapere la versione del kernel in uso basta dare:

$ uname -r

A questo punto possiamo eliminare anche gli header associati ai kernel che abbiamo eliminato. Possiamo trovare la lista con

# dpkg -l | grep linux-header*

E possiamo cancellarli in modo analogo.

PS EDIT:

Ho spiegato anche un metodo più automatizzato e più sicuro in QUESTO POST!

© 2008-2012 SlashCode Suffusion theme by Sayontan Sinha