Ecco, si spera, una buona spiegazione dietro l'idea del sistema di routing e le aggiunte specifiche drupal ad esso.
Panoramica generale
I componenti di Symfony hanno due concetti importanti qui. Il kernel http è un sistema che ottiene la richiesta, in qualche modo chiede ad altri sistemi di produrre per definire il pezzo di codice che produce l'output richiesto (un oggetto di risposta) e rispedire la risposta al client. Questo pezzo di codice è chiamato controller, quindi può essere una pura funzione simile a php4, un metodo su un oggetto o persino una funzione anonima.
Il sistema che sa quale controller è responsabile della richiesta corrente è il sistema di routing.
File di routing di base
Come sviluppatore del modulo definisci l'elenco di route e i controller corrispondenti.
Ecco un esempio per una risposta json:
taxonomy.autocomplete_vid:
path: '/taxonomy/autocomplete_vid/{taxonomy_vocabulary}'
defaults:
_controller: '\Drupal\taxonomy\Controller\TermAutocompleteController::autocompletePerVid'
requirements:
taxonomy_vocabulary: \d+
La maggior parte della documentazione di symfony menziona lo schema, ma drupal ha deciso di consentire solo la chiave "percorso" non deprecata nel suo file di routing.
Il concetto chiave è il controller che ottiene alcuni parametri dal sistema e li converte in risposta. In questo esempio hai il parametro 'taxonomy_vocabulary'. Pertanto, tutto senza un carattere di sottolineatura è considerato un parametro per il controller. Se si desidera specificare un valore predefinito, lo si inserisce nella matrice dei valori predefiniti. Nello stesso array yml si specifica la classe e il metodo connessi con '::' per dire al sistema dove cercare gli oggetti. Ogni altra proprietà non ha nulla a che fare con i parametri del controller e quindi sono considerati interni e quindi hanno un trattino basso come prefisso.
Symfony stesso consente anche di definire espressioni regolari per convalidare la validità del parametro in entrata (usando 'requisiti'). Qui corrisponderebbe solo ai numeri.
Controller resolver
Una volta che symfony ha scoperto quale controller è attivo sulla richiesta corrente, chiede al risolutore del controller di creare un'istanza del controller, che può essere eseguita tramite call_user_func_array. Il resolver del controller ha un metodo per richiamare il controller (oggetto + metodo, funzione anonima) e un metodo per ottenere i parametri passati al controller, vedere Controller resolver
Estensioni di Drupal
Questo è fondamentalmente ciò che ti dà symfony.
Drupal è leggermente più complicato:
- Puoi controllare l'accesso al percorso. Ad esempio, chiamare user_access () era molto comune in Drupal 7 e versioni successive.
- Non vuoi convertire il taxonomy_vocabulary nel suo oggetto entità reale
- Non vuoi generare la risposta a pagina intera, ma solo il "contenuto principale".
Verifica d'accesso
Drupal ha introdotto un sistema in cima alle parti di symfony che controlla se l'utente ha accesso al percorso corrente e in alternativa lancia un'eccezione 403 (accesso negato). Manager degli accessi
Nel file di routing si specifica questo nella parte dei requisiti. I bit più comuni sono elencati nell'esempio:
path: '/user/{user}'
options:
_access_mode: 'ANY'
requirements:
_permission: 'access user profiles'
_entity_access: 'user.view'
_role: 'administrator'
_permission definisce una chiamata a user_access (), _role assicura che l'utente abbia un determinato ruolo (puoi specificare più ruoli tramite, per OR e + per la logica AND). _entity_access chiede al sistema entità se hai accesso per visualizzare l'entità utente. Per impostazione predefinita, drupal ti assicura di aggiungere checker di accesso che ti consentono di procedere, ma puoi cambiarlo nelle opzioni tramite la modalità _access_.
upcasting
Come menzionato nell'elenco, non ti devi preoccupare di caricare un'entità, vedi / user / {user} come esempio. Per le entità in pratica usi semplicemente il nome del tipo di entità ed eseguirà un entity_load con l'ID passato nell'URL. Gestore del convertitore di parametri
Risposta alla pagina
Come scritto prima, il controller è responsabile della generazione dell'oggetto response. Questo sarebbe orribile in Drupal poiché una pagina è molto più simile a tutti i blocchi che compaiono nelle sue regioni, i modelli html e di pagina ecc. Pertanto drupal ha specificato una chiave diversa per specificare un controller che restituisce il contenuto di una pagina:
user.page:
path: '/user'
defaults:
_content: '\Drupal\user\Controller\UserController::userPage'
requirements:
_access: 'TRUE'
La stringa definita è il controller utilizzato per generare l'array di rendering per l'area di contenuto principale della pagina.
Un'altra aggiunta è anche il modo in cui gestire i moduli, poiché la restituzione di una pagina con un modulo è leggermente più complessa di un semplice array di rendering, quindi è possibile definire _form con FormInterface responsabile del modulo corrente.
user.pass:
path: '/user/password'
defaults:
_form: '\Drupal\user\Form\UserPasswordForm'
requirements:
_access: 'TRUE'
Nota: questo copre i punti più importanti dal mio punto di vista, anche se ci sono sicuramente molti più punti di cui parlare.
TL; DR
- I caratteri di sottolineatura sono specificati per tutto ciò che non è un parametro per il controller. Questo sta arrivando come una sorta di "standard" di symfony.
- Questi parametri vengono aggiornati tramite il convertitore di parametri e passati al controller utilizzando il resolver del controller
- Drupal ha alcune aggiunte per facilitare l'interazione delle persone con il sistema di routing di symfony.