Я пытаюсь разработать небольшой сайт MVC на PHP для работы с паролями.(Без какой-либо структуры, такой как Laravel или аналогичная, для целей обучения).
Для этого я написал как минимум 4 класса и индексный файл:
Контроллер -> Базовый классбыть расширенным, охватывая всю базовую логику для контроллеров;
Индекс -> Класс контроллера для обработки при обычном входе пользователя в систему;
Admin -> Класс контроллера для обработки при входе пользователя с правами администратора;
Bootstrap -> Класс для интерпретации переданного URL и использования в качестве маршрутизатора;
Классы отображаются следующим образом:
libs / Controller.php
<?php
class Controller {
protected $view;
protected $security_level;
function __construct() {
$this->security_level = 0;
}
public function model($model) {
$path = 'models/' . ucfirst($model). '.php';
if (file_exists($path)) {
require_once ($path);
return new $model();
}
}
public function getSecurityLevel(){
return $this->securiy_level;
}
public function view($view, $data = []){
require_once('views/commom/header.php');
require_once('views/' . $view . '.php');
require_once('views/commom/footer.php');
}
}
controllers / Index.php
<?php
class Index extends Controller {
public function __construct() {
parent::__construct();
$this->model('UserModel');
//$this->securiy_level = 0;
}
public function index($error = 0) {
$this->view('index/index', ['error' => $error]);
}
public function admin($error = 0) {
$this->view('index/index_adm', ['error' => $error]);
}
public function login(){
$auth = new Authentication();
$permission = $auth->authenticate("user");
if($permission){
header("location: /account/index");
}
else{
$this->index(1);
}
}
public function login_adm(){
$auth = new Authentication();
$permission = $auth->authenticate("admin");
if($permission){
header("location: /admin/index");
}
else{
$this->admin(1);
}
}
public function signin(){
echo "method sign in invoked <br />";
}
public function logout(){
$this->view('index/logout');
}
public function lostMyPassword(){
echo "method lost invoked <br />";
}
public function details() {
$this->view->view('index/index');
}
}
controllers / Admin
<?php
//I Think that this is VERY wrong, but okay
@session_start();
class Admin extends Controller {
private $encrypt_unit;
public function __construct() {
parent::__construct();
$this->model('UserModel');
$this->encrypt_unit = new Encrypter();
$this->securiy_level = 1;
}
public function index($msg = "", $err = false){
$users = $this->recover();
$this->view('admin/index', ["msg" => $msg, "err" => $err, "users" => $users]);
}
public function create(){
$user_var = new UserModel();
$user_var->setLogin($_POST["login"]);
$user_var->setEmail($_POST["email"]);
$user_var->setPassword($this->encrypt_unit->encrypt($_POST["password"]));
$user_var->setIsAdmin($_POST["isAdmin"]);
$user_dao = new UserDAO();
$flag = $user_dao->insertUser($user_var);
if($flag)
$this->index("User created successfully", false);
else
$this->index("Can't created user, please try again", true);
}
public function recover(){
$user_dao = new UserDAO();
$all_users = $user_dao->getUsers();
$users = array();
foreach ($all_users as $value) {
array_push($users, [
"id" => $value->getId(),
"login" => $value->getLogin(),
"email" => $value->getEmail(),
"password" => $this->encrypt_unit->decrypt($value->getPassword()),
"isAdmin" => $value->getIsAdmin()
]);
}
return $users;
}
public function update(){
$user_var = new UserModel();
$user_var->setId($_POST["id"]);
$user_var->setLogin($_POST["login"]);
$user_var->setEmail($_POST["email"]);
$user_var->setPassword($this->encrypt_unit->encrypt($_POST["password"]));
$user_dao = new UserDAO();
$flag = $user_dao->updateUser($user_var);
if($flag)
$this->index("User updated successfully", false);
else
$this->index("Can't updated user, please try again", true);
}
public function update_credential($credential_level){
$user_var = new UserModel();
$user_var->setId($_POST["id"]);
$user_var->setIsAdmin($credential_level);
$user_dao = new UserDAO();
$flag = $user_dao->updateUserCredential($user_var);
if($flag)
$this->index("User updated successfully", false);
else
$this->index("Can't updated user, please try again", true);
}
public function delete(){
$user_var = new UserModel();
$user_var->setId($_POST["id"]);
$user_dao = new UserDAO();
$flag = $user_dao->deleteUser($user_var);
if($flag)
$this->index("User deleted successfully", false);
else
$this->index("Can't deleted user, please try again", true);
}
public function search(){
echo "method search invoked <br />";
}
}
libs / Bootstrap:
<?php
class Bootstrap {
// protected $controller;
// protected $method;
// protected $params;
function __construct() {
//$this->method = 'index';
$this->redirect();
}
public function parseUrl(){
return isset($_GET['url']) ? explode('/',filter_var(rtrim($_GET['url'], '/'), FILTER_SANITIZE_URL)) : null;
}
function redirect(){
$controller;
$method;
$params;
$url = $this->parseUrl();
if(empty($url[0])){
$controller_name = 'Index';
}
else{
$controller_name = ucfirst($url[0]);
}
$filename_controller = 'controllers/' . $controller_name . '.php';
if (file_exists($filename_controller)) {
require_once($filename_controller);
// Do this to use the rest of array to select method, and than parameters
unset($url[0]);
}
else{
$this->error("Controller $controller_name not founded");
return false;
}
$controller = new $controller_name;
//default method
$method = 'index';
if(isset($url[1])){
if (method_exists($controller, $url[1])) {
$method = $url[1];
// Do this to use the rest of array to select parameters
unset($url[1]);
}
else{
$this->error("The controller $controller_name doesn't have any public method called $url[1]");
}
}
//This 'array_values($url)' command is possible because we have unseted the first and second position of this aray before
$params = $url ? array_values($url) : [];
// Securiy comparassion?
var_dump($controller);
var_dump(get_class_methods($controller));
var_dump($controller->getSecurityLevel());
var_dump($controller->{"getSecurityLevel"}());
// if(property_exists($controller, "securiy_level")){
// $authEntity = new Authentication();
// $authEntity->auth($controller->getSecurityLevel());
// }
//(new $url[0])->{$url[1]}($url[2]);
call_user_func_array([$controller, $method], $params);
}
function error($msg="") {
//echo "error invoked: <br /> $msg <br />";
require_once('controllers/Error.php');
$errorHandler = new ErrorController();
$errorHandler->index();
return false;
}
}
/ index.php:
<?php
// Use an autoloader!
require_once('libs/Bootstrap.php');
require_once('libs/Controller.php');
require_once('libs/Model.php');
require_once('libs/View.php');
// Library
require_once('libs/Database.php');
require_once('libs/ConnectionDB.php');
require_once('libs/Session.php');
require_once('libs/Authentication.php');
require_once('libs/Encrypter.php');
require_once('config/paths.php');
require_once('config/database.php');
require_once('config/passwords.php');
// DAOS
require_once('daos/UserDAO.php');
require_once('daos/AccountDAO.php');
$app = new Bootstrap();
Моя основная проблема связана с классом Bootstrap, особенно когда я пытаюсь запустить:
var_dump($controller->getSecurityLevel()); //or
var_dump($controller->{"getSecurityLevel"}());
Это мой фактический выход, когда я пытаюсь получить доступ к странице "http://localhost/index/" is:
object (Index) # 2 (2) {["view": protected] => NULL ["security_level": protected] => int (0)}
array (12) {[0] => string (11) "__construct" [1] => string (5) "index" [2] => string (5) "admin" [3] => string (5) "login" [4] => string (9) "login_adm" [5] => string (6) "signin" [6] => string (6) "logout" [7] => string(14) "lostMyPassword" [8] => string (7) "details" [9] => string (5) "model" [10] => string (16) "getSecurityLevel" [11] => string (4)) "view"}
** Примечание: неопределенное свойство: Index :: $ securiy_level в /var/www/html/libs/Controller.php в строке 21 ** NULL
**Примечание: неопределенное свойство: Index :: $ securiy_level в /var/www/html/libs/Controller.php в строке 21 ** NULL
Я не могу понять, как PHP показывает, что *Переменная 1047 * имеет свойство, к которому я хочу получить доступ, у меня есть метод для доступа, но я не могу получить к нему доступ.И что означает «статическое» связывание, которое пытается сделать PHP, когда он показывает: «Index :: $ securiy_level».
Я знаю о области действия в PHP (хотя бы немного).И что я собираюсь сделать, используя переменную $ security_level в классе Controller, это предоставить значение по умолчанию всем controllers-child.Если программист не хочет явно объявлять другое значение $ security_level, он не должен беспокоиться об этом, просто используйте свойство отца.
Моя конфигурация: PHP 7, Ubuntu 16, apache2;
Любая помощь, которую я буду благодарен заранее.
Если мой вопрос неясен, пожалуйста, прокомментируйте его, чтобы прояснить что-либо.
* Обс .: Пожалуйста, обратите внимание на вывод, когдаЯ пытаюсь открыть "http://localhost/admin" is:
object (Admin) # 2 (4) {[" encrypt_unit ":" Admin ": private] => object (Encrypter) #3 (2) {["encrypt_key": "Encrypter": private] => string (20) "RmUzYm1hcUxnY3ZYcA ==" ["encrypt_algorithm": "Encrypter": private] => string (11) "aes-256-cbc"} [" view ": protected] => NULL [" security_level ": protected] => int (0) [" securiy_level "] => int (1)}
array (11) {[0] => строка (11) "__construct" [1] => строка (5) "индекс" [2] => строка (6) "создать" [3] => строка (7) "восстановить" [4] => string (6) "update" [5] => string (17) "update_credential" [6] => string (6) "delete" [7] => string (6)"search" [8] => string (5) "model" [9] => string (16) "getSecurityLevel" [10] => string (4) "view"} int (1) int (1)