Como usar Hooks no CodeIgniter
Imagine que você precise rodar uma função antes que seu sistema começasse a rodar. Ou então, rodar algum procedimento somente após todo o seu sistema já ter sido carregado. Ou ainda, rodar alguma verificação antes de algum método específico dentro de algum controller específico rodar.
Pra fazer isso do jeito POG(programação orientada a gambiarras), você iria nos arquivos do Core do CodeIgniter e colocaria as chamadas para as suas próprias funções.
Nem queira imaginar a dor de cabeça que isso traria no futuro. Bastaria uma simples atualização do Framework pra você perder tudo.
Felizmente existe uma funcionalidade do CodeIgniter chamada Hook, que basicamente é a maneira correta de você dar uma mexida nas entranhas do framework sem mexer nos arquivos do Core.
A tradução da palavra Hook nada mais é do que gancho, que demonstra exatamente como ele funciona, ou seja, seu código engancha em algum trecho do código do CI chamado a função que você criou. (que belo exemplo hein?)
Por exemplo: imagine que você precisasse rodar alguma função antes mesmo de qualquer controller ser carregado.
Para isto, bastaria criar um hook do tipo pre_controller.
Se você preciasasse rodar alguma função imediatamente após um controller ser carregado, então bastaria criar um hook do tipo: post_controller.
Veja abaixo uma lista dos tipos de hooks que você pode criar:
- pre_system: Chamado imediatamente a cada inicialização do sistema durante a sua execução. Somente as classes de benchmarks e hooks foram carregadas até este ponto. Nenhum roteamento ou algum outro processo foi executado ainda.
- pre_controller: Chamado imediatamente antes de qualquer um dos seus controller serem chamados. Todas as classes base, roteamento e verificações de segurança já foram executadas.
- post_controller_constructor: Chamado imediatamente após seu controller ser instanciado, mas antes de qualquer chamada de método ser executada.
- post_controller: Chamado imediatamente aós seu controller ser completamente executado.
- display_override: Sobrescreve o método _display() usado para enviar uma página já finalizada para o navegador no final da execução do sistema. Isto lhe permite usar sua própria metodologia para mostrar suas páginas. Note que será necessário você referenciar o superobjeto do CodeIgniter assim: $this->CI =& get_instance() e então os dados já finalizados estarão disponíveis quando você chamar: $this->CI->output->get_output();
- cache_override: Habilita a possibilidade de você chamar seu próprio método de _display_cache() na biblioteca Output. Isto lhe permite usar seu próprio mecanismo para mostrar a página.
- post_system: Chamado depois que a página é renderizada é enviada ao navegador, no final da execução do sistema depois dos dados terem sido enviados ao navegador.
Como usar um Hook?
Todos os seus Hooks deverão ser definidos neste arquivo: application/config/hooks.php e devem seguir o seguinte formato:
$hook['pre_controller'] = array( 'class' => 'MyClass', 'function' => 'Myfunction', 'filename' => 'Myclass.php', 'filepath' => 'hooks', 'params' => array('beer', 'wine', 'snacks') );
O índice da array deve estar de acordo com o nome do hook que você deseja usar, ou seja, você deverá substituir o pre_controller pelo nome do hook que mencionei na lista logo acima.
No exemplo acima, o hook criado irá apontar para o nome pre_controller. Os seguintes itens devem ser definidos na sua array que irá criar o hook:
- class: O nome da classe que você deseja acessar. Se você desejar usar uma função procedural em vez de uma classe, deixe este item em branco.
- function: O nome da função (ou método) que você deseja chamar.
- filename: O nome do arquivo que contém sua classe/função
- filepath: O nome do diretório que contém o seu script. Nota: seu script deve estar localizado em um diretório DENTRO da pasta application, sendo assim, o caminho do seu arquivo é relativo a este diretório. Exemplo: se seus scripts estiverem localizados em: application/hooks, use “hooks” como seu caminho de arquivo (filepath). Se seu script estiver localizado em: application/hooks/utilities/ você irá usar “hooks/utilities” como seu filepath. Sem barras.
- params: Qualquer parâmetro que você deseja passar para seu script. Este item é opcional.
Se você está rodando uma versão do PHP igual ou maior que a 5.3, você também poder usar as funções anônimas, ou closures como hooks, com esta simples sintaxe:
$hook['post_controller'] = function() { /* faça algo aqui */ };
Múltiplas chamadas para o mesmo hook
Se você quiser usar o mesmo apontamento de hook com mais de um script, simplesmente crie uma array multidimensional, assim:
$hook['pre_controller'][] = array( 'class' => 'MyClass', 'function' => 'MyMethod', 'filename' => 'Myclass.php', 'filepath' => 'hooks', 'params' => array('beer', 'wine', 'snacks') ); $hook['pre_controller'][] = array( 'class' => 'MyOtherClass', 'function' => 'MyOtherMethod', 'filename' => 'Myotherclass.php', 'filepath' => 'hooks', 'params' => array('red', 'yellow', 'blue') );
Note os colchetes depois de cada índice da array:
$hook['pre_controller'][]
Isto lhe permite usar o mesmo hook para chamar vários scripts. A ordem que você definir seu array será a ordem de execução do código.
É isso, espero que isto lhe seja útil.
Abraços
Fábio