Usamos cookies para medir audiência e melhorar sua experiência. Você pode aceitar ou recusar a qualquer momento. Veja sobre o iMasters.
Caros,
Estou fazendo uma aplicação-teste para obter melhores resultados em meus estudos em PHP OO e MVC. Na minha aplicação-teste estou tentando simular uma situação real,
e ela está dividida entre "site" e "admin" (área restrita).
Bom, o problema que estou enfrentando desta vez é pertinente à validação de usuários na parte restrita. A dúvida que surgiu e que não estou certo como solucionar é:
1) Onde devo fazer a validação se o usuário está ou não logado? Em cada controller que eu tiver interagindo com uma view? Por exemplo, tenho dois controller's:
UserController(){} e NewsController(){}
Eu poderia, por exemplo, incluir a validação da sessão dentro do método construtor dessas class? Exemplo:
class UserController() {
public function __construct() {
if ( !isset($_SESSION['user_logado']) ){
header("Location:login.php");
exit;
}
}
}
Isso não geraria acoplamento (hã) ? Imaginem se muda o nome da sessão, página de redirecionamento ou qualquer outra coisa... teria de mudar em todos os controller's...
De forma estruturada, eu criaria uma função do tipo "verificaLogado()" e incluiria este código no cabeçalho de todas as páginas. Qual o melhor approach no caso da OO?
De repente, criar uma classe específica para autenticação?
class Authenticate {
public function login( User $user ) {
//select id from users where pass = :pass AND email = :email;
}
public function validate() {
if ( !isset($_SESSION['user_logado']) ){
header("Location:login.php");
exit;
}
}
//etc
}
Estou com algumas duvidas que acredito serem basicas, mas não estou conseguindo pôr na minha cabeça onde vai cada coisa, quando e onde interagir com determinada model por exemplo..Acho que só com muito estudo e prática mesmo...
:blush:
Agradeço novamente a atenção de cada um,
Abs
Procure por Access Control List (ACL), é um "padrão" que serve exatamente para isso...
Eu trabalhei em um MVC que tinha essa classe para validação:
<?php
interface Filter {
public function execute($get, $post);
}
?>
<?php public function execute($get, $post){
if(!isset($_SESSION['USUARIO_ID']) && !isset($_SESSION['USUARIO_LOGIN'])){
MVC::redirect('adm/login');
}
}
}
?>Obrigado pelas respostas,
Procure por Access Control List (ACL), é um "padrão" que serve exatamente para isso...
Dei uma pesquisada - rápida, confesso - sobre ACL, e vi que ele vai até um pouco além do que estou precisando. Minha dúvida é **onde** implementar essa primeira checagem, seja ela um "padrão" ACL completo ou apenas um IF ... "isset($_SESSION) ENDIF".
Por exemplo, imagine que eu tenho uma classe ACL prontinha, onde eu deveria usar o "Acl::isLogged($_SESSION)" ? Em qual parte de minha aplicação MVC?
Atualmente, dentro de cada controller, no método construtor, eu faço algo assim:
public function __construct() {
if ( !isset( $_SESSION['ID'] ) ) {
header("Location:index.php");
exit;
}
}
Estaria errado inserir esta abordagem dentro do __construct() ?
Vou estudar mais a fundo essa abordagem ACL...
Ficar repetindo isso dentro de cada construtor fere o DRY.
Se você só tem um tipo de usuário e todas as ações necessitam de autenticação, você deve realizar a verificação no seu Front Controller.
Muitos frameworks têm uma classe FrontController ou algo similar, no meu caso, é apenas parte do código do [inline]index.php[/inline] (dei uma boa simplificada aqui, só pra você ter uma base):
$module = isset($_GET['module']) ? $_GET['module'] : null;
$controller = isset($_GET['controller']) ? ucfirst($_GET['controller']) : null;
$action = isset($_GET['action']) ? $_GET['action'] : null;
if ($module === null) {
throw new Exception('No module set');
}
if ($controller === null) {
throw new Exception('No controller set');
}
if ($action === null) {
throw new Exception('No action set');
}
$modules = [
'admin' => [
'actions.predispatch' => function() {
// se não for a tela de login, precisamos de uma autorização
if ($controller != 'login') {
if (!isset($_SESSION['ID'])) {
header('Location: login/');
exit;
}
}
}
// ...
],
'main' => [
// ...
]
];
// ...
// Antes de processar a requisição:
call_user_func($modules[$module]['actions.predispatch']);
// Agora processa a requisição:
$factory = new ControllerFactory();
$controller = $factory->create($controller, $module);
$controller->$action();Obrigado, Henrique, acho que consegui entender e deu uma clareada boa agora.
Abs!
E se você criar um model só para o controle de usuários onde vai ter a verificação disso?
Obs.: Não manjo muito de MVC (ou quase nada) pois nunca parei para estudá-lo, mas daqui a alguns dias começarei a me aprofundar no padrão, por isso não sei se minha resposta está muito certa, aguarde um mais especialista pra dizer. Se não estiver, pelo menos tentei hehe :natallaugh: