| Current Path : /home/magalijoj/www/blog/inc/core/ |
| Current File : /home/magalijoj/www/blog/inc/core/class.dc.modules.php |
<?php
# ***** BEGIN LICENSE BLOCK *****
# This file is part of DotClear.
# Copyright (c) 2005 Olivier Meunier and contributors. All rights
# reserved.
#
# DotClear is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation; either version 2 of the License, or
# (at your option) any later version.
#
# DotClear is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with DotClear; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
#
# ***** END LICENSE BLOCK *****
/**
@ingroup DC_CORE
@brief Modules handler
Provides an object to handle modules (themes or plugins). An instance of this
class is provided by dcCore $plugins property and used for plugins.
*/
class dcModules
{
private $path;
private $ns;
private $modules = array();
private $id;
private $mroot;
# Inclusion variables
private static $superglobals = array('GLOBALS','_SERVER','_GET','_POST','_COOKIE','_FILES','_ENV','_REQUEST','_SESSION');
private static $_k;
private static $_n;
public $core; ///< <b>dcCore</b> dcCore instance
/**
Object constructor.
@param core <b>dcCore</b> dcCore instance
*/
public function __construct(&$core)
{
$this->core =& $core;
}
/**
Loads modules. <var>$path</var> could be a separated list of paths
(path separator depends on your OS).
<var>$ns</var> indicates if an additionnal file needs to be loaded on plugin
load, value could be:
- admin (loads module's _admin.php)
- public (loads module's _public.php)
- xmlrpc (loads module's _xmlrpc.php)
<var>$lang</var> indicates if we need to load a lang file on plugin
loading.
*/
public function loadModules($path,$ns=null,$lang=null)
{
$this->path = explode(PATH_SEPARATOR,$path);
$this->ns = $ns;
foreach ($this->path as $root)
{
if (!is_dir($root) || !is_readable($root)) {
continue;
}
if (substr($root,-1) != '/') {
$root .= '/';
}
if (($d = @dir($root)) === false) {
continue;
}
while (($entry = $d->read()) !== false)
{
$full_entry = $root.'/'.$entry;
if ($entry != '.' && $entry != '..' && is_dir($full_entry)
&& file_exists($full_entry.'/_define.php')
&& !file_exists($full_entry.'/_disabled'))
{
$this->id = $entry;
$this->mroot = $full_entry;
require $full_entry.'/_define.php';
$this->id = null;
$this->mroot = null;
}
}
$d->close();
}
# Sort plugins
uasort($this->modules,array($this,'sortModules'));
# Load translation, _prepend and ns_file
foreach ($this->modules as $id => $m)
{
if (file_exists($m['root'].'/_prepend.php'))
{
$r = require $m['root'].'/_prepend.php';
# If _prepend.php file returns null (ie. it has a void return statement)
if (is_null($r)) {
continue;
}
unset($r);
}
$this->loadModuleL10N($id,$lang,'main');
$this->loadNsFile($id,$ns);
}
}
/**
This method registers a module in modules list. You should use this to
register a new module.
<var>$permissions</var> is a comma separated list of permissions for your
module. If <var>$permissions</var> is null, only super admin has access to
this module.
<var>$priority</var> is an integer. Modules are sorted by priority and name.
Lowest priority comes first.
@param name <b>string</b> Module name
@param desc <b>string</b> Module description
@param author <b>string</b> Module author name
@param version <b>string</b> Module version
@param permissions <b>string</b> Module permissions
@param priority <b>integer</b> Module priority
*/
public function registerModule($name,$desc,$author,$version,$permissions=null,$priority=1000)
{
if ($this->ns == 'admin') {
if ($permissions == '' && !$this->core->auth->isSuperAdmin()) {
return;
} elseif (!$this->core->auth->check($permissions,$this->core->blog->id)) {
return;
}
}
if ($this->id) {
$this->modules[$this->id] = array(
'root' => $this->mroot,
'name' => $name,
'desc' => $desc,
'author' => $author,
'version' => $version,
'permissions' => $permissions,
'priority' => $priority === null ? 1000 : (integer) $priority
);
}
}
/**
This method installs all modules having a _install file.
@see dcModules::installModule
*/
public function installModules()
{
$res = array('success'=>array(),'failure'=>array());
foreach ($this->modules as $id => &$m)
{
$i = $this->installModule($id,$msg);
if ($i === true) {
$res['success'][$id] = true;
} elseif ($i === false) {
$res['failure'][$id] = $msg;
}
}
return $res;
}
/**
This method installs module with ID <var>$id</var> and having a _install
file. This file should throw exception on failure or true if it installs
successfully.
<var>$msg</var> is an out parameter that handle installer message.
@param id <b>string</b> Module ID
@param msg <b>string</b> Module installer message
@return <b>boolean</b>
*/
public function installModule($id,&$msg)
{
try {
$i = $this->loadModuleFile($this->modules[$id]['root'].'/_install.php');
if ($i === true) {
return true;
}
} catch (Exception $e) {
$msg = $e->getMessage();
return false;
}
return null;
}
/**
This method will search for file <var>$file</var> in language
<var>$lang</var> for module <var>$id</var>.
<var>$file</var> should not have any extension.
@param id <b>string</b> Module ID
@param lang <b>string</b> Language code
@param file <b>string</b> File name (without extension)
*/
public function loadModuleL10N($id,$lang,$file)
{
if (!$lang || !isset($this->modules[$id])) {
return;
}
$lfile = $this->modules[$id]['root'].'/locales/%s/%s';
if (l10n::set(sprintf($lfile,$lang,$file)) === false && $lang != 'en') {
l10n::set(sprintf($lfile,'en',$file));
}
}
/**
Returns all modules associative array or only one module if <var>$id</var>
is present.
@param id <b>string</b> Optionnal module ID
@return <b>array</b>
*/
public function getModules($id=null)
{
if ($id && isset($this->modules[$id])) {
return $this->modules[$id];
}
return $this->modules;
}
/**
Returns true if the module with ID <var>$id</var> exists.
@param id <b>string</b> Module ID
@return <b>boolean</b>
*/
public function moduleExists($id)
{
return isset($this->modules[$id]);
}
/**
Returns root path for module with ID <var>$id</var>.
@param id <b>string</b> Module ID
@return <b>string</b>
*/
public function moduleRoot($id)
{
return $this->moduleInfo($id,'root');
}
/**
Returns a module information that could be:
- root
- name
- desc
- author
- version
- permissions
- priority
@param id <b>string</b> Module ID
@param info <b>string</b> Information to retrieve
@return <b>string</b>
*/
public function moduleInfo($id,$info)
{
return isset($this->modules[$id][$info]) ? $this->modules[$id][$info] : null;
}
/**
Loads namespace <var>$ns</var> specific files for all modules.
@param ns <b>string</b> Namespace name
*/
public function loadNsFiles($ns=null)
{
foreach ($this->modules as $k => $v) {
$this->loadNsFile($k,$ns);
}
}
/**
Loads namespace <var>$ns</var> specific file for module with ID
<var>$id</var>
@param id <b>string</b> Module ID
@param ns <b>string</b> Namespace name
*/
public function loadNsFile($id,$ns=null)
{
switch ($ns) {
case 'admin':
$this->loadModuleFile($this->modules[$id]['root'].'/_admin.php');
break;
case 'public':
$this->loadModuleFile($this->modules[$id]['root'].'/_public.php');
break;
case 'xmlrpc':
$this->loadModuleFile($this->modules[$id]['root'].'/_xmlrpc.php');
break;
}
}
private function loadModuleFile($________)
{
if (!file_exists($________)) {
return;
}
self::$_k = array_keys($GLOBALS);
foreach (self::$_k as self::$_n) {
if (!in_array(self::$_n,self::$superglobals)) {
global ${self::$_n};
}
}
return require $________;
}
private function sortModules($a,$b)
{
if ($a['priority'] == $b['priority']) {
return strcasecmp($a['name'],$b['name']);
}
return ($a['priority'] < $b['priority']) ? -1 : 1;
}
}
?>