From f6f72cc09da3f72f800355183952b5b6f735e69e Mon Sep 17 00:00:00 2001 From: Abel Hoogeveen Date: Sat, 7 Mar 2015 13:53:10 +0100 Subject: [PATCH 1/5] Added the possibility to retrieve a mod and not add them to the mod register --- Core/System/class.core.php | 102 +++++++++++++++++++------------------ 1 file changed, 53 insertions(+), 49 deletions(-) diff --git a/Core/System/class.core.php b/Core/System/class.core.php index 7d3caf5..6d0d4c1 100644 --- a/Core/System/class.core.php +++ b/Core/System/class.core.php @@ -58,64 +58,68 @@ class Core { ## MODLOADING public function loadMod($name) { + if (!isset($this->mods->$name)) { + $CLASS = $this->loadModule($name); + $this->mods->{strtolower($name)} = &$CLASS; + } + } + + public function getMod($name) { + $CLASS = $this->loadModule($name); + return $CLASS; + } + + private function loadModule($name) { // Class name $class_name = ucfirst($name); - // Check if mod is already loaded - if (!isset($this->mods->$name)) { - // Check if class is already included - // If the class is not loaded, load it - if (!class_exists($class_name)) { + // If the mod is in the top mod directory, load it directly + $file = FUZEPATH . "/Core/Mods/class.".$class_name.".php"; + if (file_exists($file)) { + $this->mods->logger->log("Loading module '".$class_name."'"); + $path = FUZEPATH . "/Core/Mods/class.".$class_name.".php"; + require_once($file); - // If the mod is in the top mod directory, load it directly - $file = FUZEPATH . "/Core/Mods/class.".$class_name.".php"; - if (file_exists($file)) { - $this->mods->logger->log("Loading module '".$class_name."'"); - $path = FUZEPATH . "/Core/Mods/class.".$class_name.".php"; - require_once($file); + // If not, and a mod config file is found, follow that + } elseif ( file_exists(FUZEPATH . "/Core/Mods/".strtolower($name)."/moduleInfo.php" )) { + // Load the config file + $cfg = (object) require(FUZEPATH . "/Core/Mods/".strtolower($name)."/moduleInfo.php"); - // If not, and a mod config file is found, follow that - } elseif ( file_exists(FUZEPATH . "/Core/Mods/".strtolower($name)."/moduleInfo.php" )) { - // Load the config file - $cfg = (object) require(FUZEPATH . "/Core/Mods/".strtolower($name)."/moduleInfo.php"); + // Load the class name and file + $class_file = FUZEPATH . "/Core/Mods/".strtolower($name)."/" . $cfg->module_file; + $class_name = $cfg->module_class; - // Load the class name and file - $class_file = FUZEPATH . "/Core/Mods/".strtolower($name)."/" . $cfg->module_file; - $class_name = $cfg->module_class; - - // Load the dependencies first - $deps = (isset($cfg->dependencies) ? $cfg->dependencies : array()); - for ($i=0; $i < count($deps); $i++) { - $this->loadMod($deps[$i]); - } - - $path = FUZEPATH . "/Core/Mods/".strtolower($name)."/"; - $this->mods->logger->log("Loading Module '".$cfg->name."' v".$cfg->version." made by '".$cfg->author."' : '".$cfg->website."'"); - - require_once($class_file); - - // If no config file found, but a main class is, load that - } elseif ( file_exists(FUZEPATH . "/Core/Mods/".strtolower($name)."/class.".$class_name.".php") ){ - $this->mods->logger->log("Loading module '".$class_name."'"); - $path = FUZEPATH . "/Core/Mods/".strtolower($name)."/"; - require_once(FUZEPATH . "/Core/Mods/".strtolower($name)."/class.".$class_name.".php"); - - // Otherwise Abort - } else { - // MOD NOT FOUND - throw new Exception("Requested mod '".$name."' was not found", 1); - return false; - } + // Load the dependencies first + $deps = (isset($cfg->dependencies) ? $cfg->dependencies : array()); + for ($i=0; $i < count($deps); $i++) { + $this->loadMod($deps[$i]); } - // Create class object - $CLASS = new $class_name($this); - if (method_exists($CLASS, 'setModulePath')) { - $CLASS->setModulePath($path); - } - $this->mods->{strtolower($name)} = &$CLASS; - $CLASS->onLoad(); + $path = FUZEPATH . "/Core/Mods/".strtolower($name)."/"; + $this->mods->logger->log("Loading Module '".$cfg->name."' v".$cfg->version." made by '".$cfg->author."' : '".$cfg->website."'"); + + require_once($class_file); + + // If no config file found, but a main class is, load that + } elseif ( file_exists(FUZEPATH . "/Core/Mods/".strtolower($name)."/class.".$class_name.".php") ){ + $this->mods->logger->log("Loading module '".$class_name."'"); + $path = FUZEPATH . "/Core/Mods/".strtolower($name)."/"; + require_once(FUZEPATH . "/Core/Mods/".strtolower($name)."/class.".$class_name.".php"); + + // Otherwise Abort + } else { + // MOD NOT FOUND + throw new Exception("Requested mod '".$name."' was not found", 1); + return false; } + + // Create class object + $CLASS = new $class_name($this); + if (method_exists($CLASS, 'setModulePath')) { + $CLASS->setModulePath($path); + } + $CLASS->onLoad(); + return $CLASS; } } From 68c68cf91c22afc58947a9ae15f2eb4688c7dc3e Mon Sep 17 00:00:00 2001 From: Abel Hoogeveen Date: Sat, 14 Mar 2015 15:46:05 +0100 Subject: [PATCH 2/5] Added a mod register which allows the system to load advanced modules. This allows for the future build of module versions, prevention of module name conflicts and much more. --- Application/Config/config.main.php | 1 + Application/Config/config.modregister.php | 0 Core/System/class.abstract.module.php | 23 ++++ Core/System/class.core.php | 157 +++++++++++++++------- Core/System/class.events.php | 6 +- 5 files changed, 138 insertions(+), 49 deletions(-) create mode 100644 Application/Config/config.modregister.php diff --git a/Application/Config/config.main.php b/Application/Config/config.main.php index 76e258c..118ca4b 100644 --- a/Application/Config/config.main.php +++ b/Application/Config/config.main.php @@ -2,6 +2,7 @@ 'SITE_URL' => '', 'SITE_DOMAIN' => '', 'SERVER_NAME' => '', + 'registers_update_interval' => 3600, 'administrator_mail' => '', 'default_controller' => 'standard', 'default_function' => 'index', diff --git a/Application/Config/config.modregister.php b/Application/Config/config.modregister.php new file mode 100644 index 0000000..e69de29 diff --git a/Core/System/class.abstract.module.php b/Core/System/class.abstract.module.php index 3cab4e5..0003a7c 100644 --- a/Core/System/class.abstract.module.php +++ b/Core/System/class.abstract.module.php @@ -17,6 +17,11 @@ class Module extends Bus { */ protected $moduleName = 'placeholder'; + /** + * @var String name used in the mod array + */ + protected $linkName = 'placeholder'; + /** * Constructor * @@ -59,4 +64,22 @@ class Module extends Bus { if($this->modulePath === null) $this->modulePath = $modulePath; } + + /** + * Set the link name of the module. The link name is the address in the module array so that the module can self reference. + * @access public + * @param String link name + */ + public function setModuleLinkName($linkName) { + $this->linkName = $linkName; + } + + /** + * The name that is required to load itself, eg 'exampleauthor/examplemodulename' or 'techfuze/cms' + * @access public + * @param String module name + */ + public function setModuleName($modName) { + $this->moduleName = $modName; + } } \ No newline at end of file diff --git a/Core/System/class.core.php b/Core/System/class.core.php index 6d0d4c1..a1cde43 100644 --- a/Core/System/class.core.php +++ b/Core/System/class.core.php @@ -11,6 +11,7 @@ class Core { public $mods; private $loaded = false; + private $register; ## START/STOP public function init() { @@ -23,6 +24,12 @@ class Core { $this->loadStartupFiles(); $this->mods->events->fireEvent('coreStartEvent'); + // Mod register exists, check if expired + if ( ( date('U') - $this->mods->config->main->registers_last_update) > $this->mods->config->main->registers_update_interval) { + $this->mods->logger->log("Registers have expired. Updating...", 'Core'); + $this->buildModRegister(); + $this->mods->events->buildEventRegister(); + } } public function loadStartupFiles() { @@ -57,69 +64,127 @@ class Core { } ## MODLOADING - public function loadMod($name) { + public function loadMod($name, $version = null) { if (!isset($this->mods->$name)) { $CLASS = $this->loadModule($name); - $this->mods->{strtolower($name)} = &$CLASS; + $this->mods->{strtolower($CLASS[1])} = &$CLASS[0]; } } - public function getMod($name) { + public function getMod($name, $version = null) { $CLASS = $this->loadModule($name); - return $CLASS; + return $CLASS[0]; } - private function loadModule($name) { - // Class name - $class_name = ucfirst($name); - - // If the mod is in the top mod directory, load it directly - $file = FUZEPATH . "/Core/Mods/class.".$class_name.".php"; - if (file_exists($file)) { - $this->mods->logger->log("Loading module '".$class_name."'"); - $path = FUZEPATH . "/Core/Mods/class.".$class_name.".php"; - require_once($file); - - // If not, and a mod config file is found, follow that - } elseif ( file_exists(FUZEPATH . "/Core/Mods/".strtolower($name)."/moduleInfo.php" )) { - // Load the config file - $cfg = (object) require(FUZEPATH . "/Core/Mods/".strtolower($name)."/moduleInfo.php"); - - // Load the class name and file - $class_file = FUZEPATH . "/Core/Mods/".strtolower($name)."/" . $cfg->module_file; - $class_name = $cfg->module_class; - - // Load the dependencies first - $deps = (isset($cfg->dependencies) ? $cfg->dependencies : array()); - for ($i=0; $i < count($deps); $i++) { - $this->loadMod($deps[$i]); - } - - $path = FUZEPATH . "/Core/Mods/".strtolower($name)."/"; - $this->mods->logger->log("Loading Module '".$cfg->name."' v".$cfg->version." made by '".$cfg->author."' : '".$cfg->website."'"); - - require_once($class_file); - - // If no config file found, but a main class is, load that - } elseif ( file_exists(FUZEPATH . "/Core/Mods/".strtolower($name)."/class.".$class_name.".php") ){ - $this->mods->logger->log("Loading module '".$class_name."'"); - $path = FUZEPATH . "/Core/Mods/".strtolower($name)."/"; - require_once(FUZEPATH . "/Core/Mods/".strtolower($name)."/class.".$class_name.".php"); - - // Otherwise Abort + private function loadModule($name, $version = null) { + // Load the register if not loaded yet + if (!isset($this->mods->config->modregister->register)) { + $this->buildModRegister(); } else { - // MOD NOT FOUND + + $this->register = $this->mods->config->modregister->register; + } + + // The basic module path + $path = FUZEPATH . "/Core/Mods/"; + + // Chech if the requested module is set + if (isset($this->register[$name])) { + // Check if the config file is loaded + if (!empty($this->register[$name])) { + // Load the config file + $cfg = (object) $this->register[$name]; + + // Check if a specific version is requested + if (isset($version)) { + // @TODO: Implement + } else { + // Or load the main version + $file = $cfg->directory . $cfg->module_file; + + // Load the dependencies before the module loads + $deps = (isset($cfg->dependencies) ? $cfg->dependencies : array()); + for ($i=0; $i < count($deps); $i++) { + $this->loadMod($deps[$i]); + } + + // Check if the file exists + if (file_exists($file)) { + // And load it + require_once($file); + $class_name = $cfg->module_class; + $msg = "Loading Module '".ucfirst((isset($cfg->name) ? $cfg->name : $cfg->module_name)) . "'"; + $msg .= (isset($cfg->version) ? " version:".$cfg->version : ""); + $msg .= (isset($cfg->author) ? " made by ".$cfg->author : ""); + $msg .= (isset($cfg->website) ? " from ".$cfg->website: ""); + $this->mods->logger->log($msg); + } else { + // Throw Exception if the file does not exist + throw new Exception("Requested mod '".$name."' could not be loaded. Class file not found", 1); + return false; + } + } + } else { + // Throw Exception if the module has an invalid config file + throw new Exception("Requested mod '".$name."' could not be loaded. Invalid config", 1); + return false; + } + } else { + // Throw Exception if the module is not defined throw new Exception("Requested mod '".$name."' was not found", 1); - return false; + return false; } // Create class object $CLASS = new $class_name($this); if (method_exists($CLASS, 'setModulePath')) { - $CLASS->setModulePath($path); + $CLASS->setModulePath($cfg->directory); + } + if (method_exists($CLASS, 'setModuleLinkName')) { + $CLASS->setModuleLinkName($cfg->module_name); + } + if (method_exists($CLASS, 'setModuleName')) { + $CLASS->setModuleName($name); } $CLASS->onLoad(); - return $CLASS; + return array($CLASS, $cfg->module_name); + } + + public function buildModRegister() { + $this->mods->logger->newLevel("Building Mod Register", 'Core'); + $dir = FUZEPATH . "Core/Mods/"; + $mods = array_values(array_diff(scandir($dir), array('..', '.'))); + $register = array(); + for ($i=0; $i < count($mods); $i++) { + $mod_dir = $dir . $mods[$i] . "/"; + if (file_exists($mod_dir . "/moduleInfo.php")) { + $cfg = (object) require($mod_dir . "/moduleInfo.php"); + $name = ""; + $name .= (!empty($cfg->author) ? strtolower($cfg->author)."/" : ""); + $name .= strtolower($cfg->module_name); + + // Append directory + $cfg->directory = $mod_dir; + $register[$name] = (array) $cfg; + } else { + // Get the name + $name = $mods[$i]; + + // Build a dynamic module config + $cfg = new stdClass(); + $cfg->module_class = ucfirst($name); + $cfg->module_file = 'class.'.strtolower($name).".php"; + $cfg->module_name = $name; + $cfg->dependencies = array(); + $cfg->versions = array(); + $cfg->directory = $mod_dir; + $register[$name] = (array)$cfg; + } + } + + $this->mods->logger->stopLevel(); + $this->mods->config->set('modregister', 'register', $register); + $this->mods->config->set('main', 'registers_last_update', date('U')); } } diff --git a/Core/System/class.events.php b/Core/System/class.events.php index 78ea4ae..441e224 100644 --- a/Core/System/class.events.php +++ b/Core/System/class.events.php @@ -156,9 +156,9 @@ class Events extends Bus{ public function buildEventRegister() { $this->logger->newLevel("Building Event Register", 'Events'); $dir = FUZEPATH . "/Core/Mods/"; - $mods = array_values(array_diff(scandir($dir), array('..', '.'))); - for ($i=0; $i < count($mods); $i++) { - $this->core->loadMod($mods[$i]); + $mods = $this->config->modregister->register; + foreach ($mods as $key => $value) { + $this->core->loadMod($key); } $event = $this->fireEvent('eventRegisterBuildEvent', ''); From 892068d583ed846a6fe74c6ac9da9d97d20c24ab Mon Sep 17 00:00:00 2001 From: Abel Hoogeveen Date: Sat, 14 Mar 2015 16:02:18 +0100 Subject: [PATCH 3/5] Implemented versions --- Core/System/class.core.php | 57 +++++++++++++++++++++----------------- 1 file changed, 32 insertions(+), 25 deletions(-) diff --git a/Core/System/class.core.php b/Core/System/class.core.php index a1cde43..f33e310 100644 --- a/Core/System/class.core.php +++ b/Core/System/class.core.php @@ -97,32 +97,39 @@ class Core { // Check if a specific version is requested if (isset($version)) { - // @TODO: Implement + if (isset($cfg->versions)) { + if (isset($cfg->versions[$version])) { + $ncfg = (object) $cfg->versions[$version]; + foreach ($ncfg as $key => $value) { + $cfg->$key = $value; + } + } + } + } + + // Or load the main version + $file = $cfg->directory . $cfg->module_file; + + // Load the dependencies before the module loads + $deps = (isset($cfg->dependencies) ? $cfg->dependencies : array()); + for ($i=0; $i < count($deps); $i++) { + $this->loadMod($deps[$i]); + } + + // Check if the file exists + if (file_exists($file)) { + // And load it + require_once($file); + $class_name = $cfg->module_class; + $msg = "Loading Module '".ucfirst((isset($cfg->name) ? $cfg->name : $cfg->module_name)) . "'"; + $msg .= (isset($cfg->version) ? " version:".$cfg->version : ""); + $msg .= (isset($cfg->author) ? " made by ".$cfg->author : ""); + $msg .= (isset($cfg->website) ? " from ".$cfg->website: ""); + $this->mods->logger->log($msg); } else { - // Or load the main version - $file = $cfg->directory . $cfg->module_file; - - // Load the dependencies before the module loads - $deps = (isset($cfg->dependencies) ? $cfg->dependencies : array()); - for ($i=0; $i < count($deps); $i++) { - $this->loadMod($deps[$i]); - } - - // Check if the file exists - if (file_exists($file)) { - // And load it - require_once($file); - $class_name = $cfg->module_class; - $msg = "Loading Module '".ucfirst((isset($cfg->name) ? $cfg->name : $cfg->module_name)) . "'"; - $msg .= (isset($cfg->version) ? " version:".$cfg->version : ""); - $msg .= (isset($cfg->author) ? " made by ".$cfg->author : ""); - $msg .= (isset($cfg->website) ? " from ".$cfg->website: ""); - $this->mods->logger->log($msg); - } else { - // Throw Exception if the file does not exist - throw new Exception("Requested mod '".$name."' could not be loaded. Class file not found", 1); - return false; - } + // Throw Exception if the file does not exist + throw new Exception("Requested mod '".$name."' could not be loaded. Class file not found", 1); + return false; } } else { // Throw Exception if the module has an invalid config file From 44ae54445eab0aa3b98a6dce3006bcd6b5f576b1 Mon Sep 17 00:00:00 2001 From: Abel Hoogeveen Date: Sat, 14 Mar 2015 16:03:38 +0100 Subject: [PATCH 4/5] Added a very basic system to disabled modules using $enabled = false; in the moduleInfo.php --- Core/System/class.core.php | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/Core/System/class.core.php b/Core/System/class.core.php index f33e310..48e230a 100644 --- a/Core/System/class.core.php +++ b/Core/System/class.core.php @@ -95,6 +95,13 @@ class Core { // Load the config file $cfg = (object) $this->register[$name]; + // Check if the module is enabled, otherwise abort + if (isset($cfg->enabled)) { + if (!$cfg->enabled) { + return false; + } + } + // Check if a specific version is requested if (isset($version)) { if (isset($cfg->versions)) { From b636e904621b1ea403a2a8dc2cb0d1922c0c87e4 Mon Sep 17 00:00:00 2001 From: Abel Hoogeveen Date: Sat, 14 Mar 2015 16:05:07 +0100 Subject: [PATCH 5/5] Added a logger entry --- Core/Mods/sections/class.sections.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/Core/Mods/sections/class.sections.php b/Core/Mods/sections/class.sections.php index 4fbdaa4..a1b62f5 100644 --- a/Core/Mods/sections/class.sections.php +++ b/Core/Mods/sections/class.sections.php @@ -111,6 +111,8 @@ class Sections extends Module { // And finally set the controller, if no parameters are set, load the default function $controller = (!empty($event->function) ? $event->function : $this->config->main->default_controller ); + } else { + $this->logger->log("No section was found with name: '".$name."'", 'Sections'); } if($controller !== null)$event->controller = $controller;