Symfony 1.2: Salvare relazioni M-M con admin generator ed Embedded Forms
Scusate per il titolo criptico, ma non trovato altro modo per semplificare la questione che mi ha fatto perdere non poco tempo.
La questione è questa (caso base):
- Schema con 1 relazione M-M
- Modulo generato con l’admin generator
- Embed sulla form principale di un’altra form a cui è associata la relazione M-M (Category <-> Article)
Quindi prendiamo questo schema:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 |
anagrafica:
id: ~
nome: { type: varchar(255), required: true }
cognome: { type: varchar(255), required: true }
sesso: { type: varchar(255), required: true }
eta: { type: integer, required: true }
caratteristica_id: ~
caratteristica:
id: ~
nome: { type: varchar(255), required: true }
malattia:
id: ~
nome: { type: varchar(255), required: true }
caratteristica_malattia:
caratteristica_id: { type: integer, foreignTable: caratteristica, foreignReference: id, required: true, primaryKey: true, onDelete: cascade }
malattia_id: { type: integer, foreignTable: malattia, foreignReference: id, required: true, primaryKey: true, onDelete: cascade } |
2) Generiamo un modulo di amministrazione per la tabella Anagrafica:
1 | symfony propel:generate-admin Anagrafica --module=anagrafica |
3) Facciamo l’embed dal modulo anagrafica della form caratteristica:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | class AnagraficaForm extends BaseAnagraficaForm { public function configure() { // get Related Object model $caratteristica = $this->getObject()->getCaratteristica(); if (is_null($caratteristica)) { $caratteristica = new Caratteristica(); $caratteristica->setAnagrafica($this->getObject()); $this->getObject()->setCaratteristica($caratteristica); } $caratteristica_form = new CaratteristicaForm($caratteristica); $this->embedForm('Caratteristica', $caratteristica_form); parent::configure(); } } |
3) A questo punto, la form è completa, sulla form Anagrafica avremo la form caratteristica correttamente “embeddata”, l’unico problema (che è poi il cuore di questo articolo) è che la relazione M-M non verrà correttamente salvata.
Perchè ? In realtà ci sono già alcuni ticket aperti:
http://trac.symfony-project.org/ticket/4850
Quando la form embeddata viene salvata, non viene chiamata la funzione doSave(), ma l’oggetto viene salvato direttamente, è stata proposta la patch di cui sopra, ma il buon Fabien ci fa sapere che in questo caso è bene utilizzare l’override della funzione updateObject(), quindi la soluzione potrebbe essere questa:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 | class CaratteristicaForm extends BaseCaratteristicaForm { public function updateObject($values = null) { $this->updateCaratteristicaMalattia(); parent::updateObject($values); } public function updateCaratteristicaMalattie() { $con = $this->getConnection(); $c = new Criteria(); $c->add(CaratteristicaMalattiaPeer::CARATTERISTICA_ID, $this->object->getPrimaryKey()); CaratteristicaMalattiaPeer::doDelete($c, $con); $values = $values['caratteristica_malattia_list']; if (is_array($values)) { foreach ($values as $value) { $obj = new CaratteristicaMalattia(); $obj->setCaratteristicaId($this->object->getPrimaryKey()); $obj->setMalattiaId($value); $obj->save(); } } } } |
Dove la funzione updateCaratteristicaMalattie() non è altro che un piccolo refactoring della funzione “saveCelgeneCaratteristicaMalattiaList()” che gia troviamo nella classe “BaseCaratteristicaForm”.
Non aggiungo altro, qui c’è tutto per risolvere questo strano comportamento di sfPropel.
Creare un social network con Drupal

Erano anni che mi ripromettevo (rimandando in continuazione) di approfondire e di sviluppare qualcosa di un pochino complesso con il CMF in questione, finalmente l’occasione giusta è arrivata (grazie alla nostra piccola startup, Ideato e Mikamai) e solo grazie ad un lavoro di questa portata, siamo riusciti ad apprezzare in pieno, le potenzialità di un framework di sviluppo ben modellato come Drupal, che vanta più di ogni altro, una libreria pressochè immensa di moduli che permettono out-of-the-box di avere immediatamente un mare di funzionalità aggiuntive.
Anche se è da dire che il primo approccio con Drupal, è un esperienza disarmante e frustrante, putroppo la documentazione ufficiale è troppo lacunosa, vengono date per scontate sezioni fondamentali e non esiste un workflow logico da seguire per capire il complesso sistema di Hook e ovverride che il core di Drupal innesca ad ogni chiamata.
Comunque con qualche buon libro e una pagina sempre aperta sulle API (qui documentazione ottima), si riesce in brevtempo ad entrare con semplicità nei meccanismi (tante volte un pochino strani) ed essere subito produttivi.
Tornando al tema del post, come sviluppare un Social Network con Drupal ?
Prima sarebbe da chiederci quali sono le caratteristiche base che un Social network dovrebbe assolutamente avere ?
- Messaggi privati: http://drupal.org/project/privatemsg
- Buddylist: http://drupal.org/project/buddylist (in alternativa http://drupal.org/project/user_relationship)
- Inviti e Contact grabber: http://drupal.org/project/invite e http://drupal.org/project/dcl_importer
- Gruppi: http://drupal.org/project/og
- Sharing: http://drupal.org/project/forward (o http://drupal.org/project/send), http://drupal.org/project/addthis
- Mashup semplice: http://drupal.org/project/emfield , http://drupal.org/project/ipaper
- Notifiche: http://drupal.org/project/notifications (o http://drupal.org/project/subscriptions)
- Facebook: http://drupal.org/project/fb (mai provato ma sembra molto molto interessante)
Ovviamente, senza menzionare i moduli “standard” che non fanno parte del core, ma sono assolutamente indispensabili:
- CCK, Views, Panels (per me non lo è molto), Workflow-ng
Alcuni moduli, sono un pochino “scarni” di funzionalità, ad esempio Privatemsg, non permette di inviare il messaggio via mail, o selezionare i contatti dalla propria buddylist, per questo ho sviluppato un modulo di estensione:
Ho avuto da pochi giorni l’accesso al CVS Drupal, appena ho qualche minuto libero, gli darò un posto più dignitoso
Che features aggiunge privatemsg-ng ?
- Integrazione con OG, Buddylist, User roles (core)
- File attachment (viene inviato all’utente insieme al messaggo un link da dove scaricare l’allegato, ovviamente sarà scaricabile solo da chi ha i permessi)
- Mailing out integrato con job_queue
Per ora è tutto, se ancora non avete provate Drupal, questo è il momento giusto
Ciau
WiCD: Un network manager avanzato per Linux
Chi utilizza Debian/Ubuntu o più in generale GNU/Linux e Gnome, sicuramente si sarà trovato di fronte al blasonato Network Managaer progetto ufficiale di Gnome, il cui compito sarebbe quello di semplificare la vita agli utenti mobili nella connessioni a svariati tipi di rete, in effetti sulla carta le feature ci sono, ma in realtà il discorso è ben diverso, è un software molto lento e ha delle mancanze che il più delle volte fanno solamente venire il nervoso, come non poter collegarsi ad una rete Wireless con la nm-applet e utilizzare un IP statico, oppure collegarvi ad una rete dove ci sono più AP in WDS…praticamente un incubo..
Ed è qui che Wicd ci viene in aiuto, queste sono le feature principali:
- No Gnome dependencies (although it does require GTK), so it is easy to use in XFCE, Fluxbox, Openbox, Enlightenment, etc.
- Ability to connect to wired and wireless networks
- Profiles for each wireless network and wired network
- Many encryption schemes, some of which include WEP/WPA/WPA2
- Remains compatible with wireless-tools
- Tray icon showing network activity and signal strength
Per l’installazione su Ubuntu troviamo i pacchettini binari aggiungendo al repository APT il seguente URL:
deb http://apt.wicd.net [Dapper || Edgy || Feisty || Gutsy] extras
Symfony 1.1 in arrivo, ma senza più Ajax..
Anche se sembra essere stato il suo tassello vincente rispetto ad altri framework, ecco spuntare fuori direttamente dalle pagine wiki di Symfony, la lista degli Helper attualmente disponibili nella versione di sviluppo 1.1:
All helpers in JavascriptHelper are deprecated and they won’t have equivalent in symfony 1.1.
symfony 1.2 won’t have Prototype/script.aculo.us included as we want to give the user the choice of their JavaScript library. Also, we think that JavaScript have to be written in JavaScript, and as such, there won’t be any official port of these helpers in the future.
Concordo che Javascript deve essere scritto in JS per evitare qualsiasi tipo di problema, ma resta comunque il fatto che (almeno io) trovato gli helpers javascript veramente comodissimi, sopratutto quando nei task ripetitivi e anche per la gestione delle form (form_remote_tag, link_to_funcion, link_to_remote ecc..), tutti helper che non avremo più (almeno da quanto mi sembra di aver capito, nella nuova versione 1.1
Peccato!
Update: E’ stato appena creato il branch su svn della versione 1.1 che si avvicina definitivamente ad essere la prossima release stabile, mentre per il trunk ora sarà solo per la versione 1.2, che sarà sviluppata a partire da subito.