Como usar os recursos do CodeIgniter fora de um Controller? Ou, como usar o get_instance()?
Olá, feliz 2017!
Já deve ter acontecido de você criar uma biblioteca própria que não estende o CI_Controller ,ou então, criar uma função helper e precisar usar algum recurso nativo do CodeIgniter, como consultar um banco de dados, por exemplo.
Então, vamos imaginar um exemplo bem simples.
Imagine que você tem um relatório e que neste relatório há um select que mostra os anos para o usuário filtrar.
Como criar um select dinâmico somente com os anos que existem no banco de dados?
Uma maneira de resolvermos isto é criarmos este select dinâmico que será preenchido com o menor e maior ano que está lançado no banco de dados, assim, este select irá refletir somente informações que existem no banco de dados.
Criando um helper
O primeiro passo seria criar um helper que faria a criação deste select, para que quando precisássemos dele, bastaria chamá-lo no código.
Crie um arquivo chamado, por exemplo: funcoes_helper.php e salve na pasta helpers dentro de application.
Dentro deste arquivo você pode colocar o seguinte código:
<?php function selectAnos() { $ano = 2017; $ano_final = 2020; $options = "<select name='ano'>"; $options .= "<option value=''></option>"; for ($ano ; $ano <= $ano_final ; $ano++) { $options .= "<option value='{$ano}'>{$ano}</option>"; } $options .= "</select>"; return $options; } ?>
Para usar o código acima, basta carregar o seu helper no seu controller, assim: $this->load->helper(“funcoes”); ou no autoloader.php dentro da pasta application/config, depois basta digitar em qualquer lugar: echo selectAnos();
Ao executar o código acima, notaremos que ele funcionará perfeitamente, gerando um select entre os anos 2017 e 2020.
Porém, isto não resolve. E se no banco de dados houver anos inferiores a 2017, ou então superiores a 2020?
Então, o mais correto é nós sabermos quais são os anos que existem lançados no banco de dados e montarmos nosso select em função disto.
Para isto, precisaríamos consultar o banco de dados, porém, se você fizer isto: $this->db->get(“tabela”); dentro do seu arquivo de helper, não vai funcionar, pois o arquivo de helper não é uma classe PHP, e mesmo se fosse, ela não estaria estendendo a classe pai CI_Controller.
O que precisamos agora é trazer para dentro do nosso helper os recursos do CodeIgniter e é aí que entra nosso amigo get_instance();
A função get_instance() simplesmente faz uma referência para o super objeto do CodeIgniter, trazendo nesta referência todos os recursos que o super objeto possui.
Para podermos usar estes recursos precisamos fazer uma atribuição por referência, desta forma;
$CI =& get_instance();
A linha acima faz com que a variável $CI aponte para o mesmo endereço de memória onde está localizado o super objeto do CodeIgniter, por isso que existe aquele =& que nada mais é do que um ponteiro para a posição de memória da variável de origem.
Você pode ver mais detalhes sobre isto na documentação do PHP, aqui.
Agora, nossa variável $CI possui todos os recursos que precisamos do CodeIgniter.
Vamos agora complementar o código para que faça uma consulta a uma tabela no banco de dados que tem nossos lançamentos.
Apenas para fins didáticos, vamos imaginar que existe uma tabela chamada lancamentos e que ela possui 3 campos: id, lancamento e data e que tem os seguintes valores:
id | lancamento | data |
---|---|---|
1 | Mercado | 2014-10-03 |
2 | Aluguel | 2015-03-26 |
3 | Academia | 2016-11-13 |
4 | Almoço | 2017-01-09 |
Agora, nosso código deverá ser capaz de identificar qual o menor e maior anos que estão cadastrados nesta tabela.
Aqui não vou criar um model nem configurar banco de dados, pois não é esse o foco do post, vou simplesmente digitar a consulta diretamente no helper.
Porém, você poderia normalmente carregar um model e depois chamar um método dentro dele para trazer os registros do banco de dados.
Nosso código ficaria assim:
<?php //Atribui por referência o super objeto CodeIgniter $CI =& get_instance(); //Agora, não devemos mais usar $this, mas sim $CI $menor_ano = $CI->db->select_min("YEAR(data) as ano")->get('lancamentos')->row()->ano; $maior_ano = $CI->db->select_max("YEAR(data) as ano")->get('lancamentos')->row()->ano; $ano = $menor_ano; $ano_final = $maior_ano; $options = "<select name='ano'>"; $options .= "<option value=''>Escolha o ano</option>"; for ($ano ; $ano <= $ano_final ; $ano++) { $options .= "<option value='{$ano}'>{$ano}</option>"; } $options .= "</select>"; echo $options; ?>
Agora, nosso select será gerado entre os anos de 2014 e 2017 automaticamente.
E se entrar um registro novo, de 2018, por exemplo, o select será ajustado automaticamente quando a página for recarregada.
Porém, note que não é possível usar o $this, pois não estamos dentro de uma classe.
Nosso $this foi mudado para $CI, ou qualquer outra variável que você quiser.
Esta variável agora é nosso objeto que possui todos os recursos nativos do CI.
Se você precisasse carregar um model para usar um método dentro dele, você faria assim:
$CI->load->model(“Lancamentos_model”);
$CI->Lancamentos_model->metodoXYZ();
E é isto, você pode usar a função get_instance() em qualquer lugar da sua aplicação que não esteja diretamente dentro do escopo do CodeIgniter, e assim trazer para você tudo aquilo de bom que o CI nos oferece.
Obs.: O exemplo acima não chegou a ser testado, pois tem intuito somente de lhe passar a ideia de como fazer tudo.
Abraços e até o próximo post!
Fabio