blob: 621d22631d0672f7ab920015a1880f93efcc0a83 [file] [log] [blame]
Andrey Andreevc5536aa2012-11-01 17:33:58 +02001<?php
Derek Jones8dca0412010-03-05 13:01:44 -06002/**
3 * CodeIgniter
4 *
Phil Sturgeon07c1ac82012-03-09 17:03:37 +00005 * An open source application development framework for PHP 5.2.4 or newer
Derek Jones8dca0412010-03-05 13:01:44 -06006 *
Derek Jonesf4a4bd82011-10-20 12:18:42 -05007 * NOTICE OF LICENSE
Andrey Andreev83d15052011-12-22 13:35:42 +02008 *
Derek Jonesf4a4bd82011-10-20 12:18:42 -05009 * Licensed under the Open Software License version 3.0
Andrey Andreev83d15052011-12-22 13:35:42 +020010 *
Derek Jonesf4a4bd82011-10-20 12:18:42 -050011 * This source file is subject to the Open Software License (OSL 3.0) that is
12 * bundled with this package in the files license.txt / license.rst. It is
13 * also available through the world wide web at this URL:
14 * http://opensource.org/licenses/OSL-3.0
15 * If you did not receive a copy of the license and are unable to obtain it
16 * through the world wide web, please send an email to
17 * licensing@ellislab.com so we can send you a copy immediately.
Derek Jones8dca0412010-03-05 13:01:44 -060018 *
19 * @package CodeIgniter
20 * @author EllisLab Dev Team
Greg Aker0defe5d2012-01-01 18:46:41 -060021 * @copyright Copyright (c) 2006 - 2012, EllisLab, Inc. (http://ellislab.com/)
Derek Jonesf4a4bd82011-10-20 12:18:42 -050022 * @license http://opensource.org/licenses/OSL-3.0 Open Software License (OSL 3.0)
Derek Jones8dca0412010-03-05 13:01:44 -060023 * @link http://codeigniter.com
24 * @since Version 1.0
25 * @filesource
26 */
Andrey Andreevc5536aa2012-11-01 17:33:58 +020027defined('BASEPATH') OR exit('No direct script access allowed');
Derek Jones8dca0412010-03-05 13:01:44 -060028
Derek Jones8dca0412010-03-05 13:01:44 -060029/**
30 * CodeIgniter Driver Library Class
31 *
32 * This class enables you to create "Driver" libraries that add runtime ability
33 * to extend the capabilities of a class via additional driver objects
34 *
35 * @package CodeIgniter
36 * @subpackage Libraries
37 * @category Libraries
38 * @author EllisLab Dev Team
Barry Mienydd671972010-10-04 16:33:58 +020039 * @link
Derek Jones8dca0412010-03-05 13:01:44 -060040 */
41class CI_Driver_Library {
42
Timothy Warren0688ac92012-04-20 10:25:04 -040043 /**
44 * Array of drivers that are available to use with the driver class
45 *
46 * @var array
47 */
48 protected $valid_drivers = array();
Andrey Andreev56454792012-05-17 14:32:19 +030049
Timothy Warren0688ac92012-04-20 10:25:04 -040050 /**
51 * Name of the current class - usually the driver class
52 *
53 * @var string
54 */
Darren Hillc4e266b2011-08-30 15:40:27 -040055 protected $lib_name;
Barry Mienydd671972010-10-04 16:33:58 +020056
Darren Hill6fbf6bd2011-08-31 14:15:35 -040057 /**
58 * Get magic method
59 *
Darren Hillc4e266b2011-08-30 15:40:27 -040060 * The first time a child is used it won't exist, so we instantiate it
61 * subsequents calls will go straight to the proper child.
Darren Hill6fbf6bd2011-08-31 14:15:35 -040062 *
63 * @param string Child class name
64 * @return object Child class
65 */
Darren Hillc4e266b2011-08-30 15:40:27 -040066 public function __get($child)
Andrey Andreev2e3e2302012-10-09 15:52:34 +030067 {
Darren Hill6fbf6bd2011-08-31 14:15:35 -040068 // Try to load the driver
dchill42c5872252012-07-30 14:53:11 -040069 return $this->load_driver($child);
Darren Hill6fbf6bd2011-08-31 14:15:35 -040070 }
Darren Hillc4e266b2011-08-30 15:40:27 -040071
Darren Hill6fbf6bd2011-08-31 14:15:35 -040072 /**
73 * Load driver
74 *
Darren Hillc4e266b2011-08-30 15:40:27 -040075 * Separate load_driver call to support explicit driver load by library or user
Darren Hill6fbf6bd2011-08-31 14:15:35 -040076 *
77 * @param string Child class name
78 * @return object Child class
79 */
Darren Hillc4e266b2011-08-30 15:40:27 -040080 public function load_driver($child)
Derek Jones8dca0412010-03-05 13:01:44 -060081 {
Pascal Kriete14287f32011-02-14 13:39:34 -050082 if ( ! isset($this->lib_name))
Derek Jones8dca0412010-03-05 13:01:44 -060083 {
Barry Mienydd671972010-10-04 16:33:58 +020084 $this->lib_name = get_class($this);
Derek Jones8dca0412010-03-05 13:01:44 -060085 }
86
87 // The class will be prefixed with the parent lib
88 $child_class = $this->lib_name.'_'.$child;
Andrey Andreev83d15052011-12-22 13:35:42 +020089
Phil Sturgeoneb2dcda2011-04-02 14:44:58 +010090 // Remove the CI_ prefix and lowercase
Darren Hill4d1cd4c2011-08-31 13:59:09 -040091 $lib_name = ucfirst(strtolower(str_replace('CI_', '', $this->lib_name)));
92 $driver_name = strtolower(str_replace('CI_', '', $child_class));
Andrey Andreev83d15052011-12-22 13:35:42 +020093
Phil Sturgeoneb2dcda2011-04-02 14:44:58 +010094 if (in_array($driver_name, array_map('strtolower', $this->valid_drivers)))
Derek Jones8dca0412010-03-05 13:01:44 -060095 {
96 // check and see if the driver is in a separate file
97 if ( ! class_exists($child_class))
98 {
99 // check application path first
Phil Sturgeon02d45b52011-08-14 09:56:47 -0600100 foreach (get_instance()->load->get_package_paths(TRUE) as $path)
Derek Jones8dca0412010-03-05 13:01:44 -0600101 {
Phil Sturgeoneb2dcda2011-04-02 14:44:58 +0100102 // loves me some nesting!
103 foreach (array(ucfirst($driver_name), $driver_name) as $class)
Derek Jones8dca0412010-03-05 13:01:44 -0600104 {
Greg Aker3a746652011-04-19 10:59:47 -0500105 $filepath = $path.'libraries/'.$lib_name.'/drivers/'.$class.'.php';
Derek Jones8dca0412010-03-05 13:01:44 -0600106
Phil Sturgeoneb2dcda2011-04-02 14:44:58 +0100107 if (file_exists($filepath))
108 {
109 include_once $filepath;
Darren Hillc4e266b2011-08-30 15:40:27 -0400110 break 2;
Derek Jones8dca0412010-03-05 13:01:44 -0600111 }
112 }
113 }
Barry Mienydd671972010-10-04 16:33:58 +0200114
Derek Jones8dca0412010-03-05 13:01:44 -0600115 // it's a valid driver, but the file simply can't be found
116 if ( ! class_exists($child_class))
117 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300118 log_message('error', 'Unable to load the requested driver: '.$child_class);
119 show_error('Unable to load the requested driver: '.$child_class);
Derek Jones8dca0412010-03-05 13:01:44 -0600120 }
121 }
122
123 $obj = new $child_class;
124 $obj->decorate($this);
125 $this->$child = $obj;
126 return $this->$child;
127 }
Barry Mienydd671972010-10-04 16:33:58 +0200128
Derek Jones8dca0412010-03-05 13:01:44 -0600129 // The requested driver isn't valid!
Darren Hillc4e266b2011-08-30 15:40:27 -0400130 log_message('error', 'Invalid driver requested: '.$child_class);
131 show_error('Invalid driver requested: '.$child_class);
Derek Jones8dca0412010-03-05 13:01:44 -0600132 }
Derek Jones8dca0412010-03-05 13:01:44 -0600133
Derek Jones8dca0412010-03-05 13:01:44 -0600134}
Derek Jones8dca0412010-03-05 13:01:44 -0600135
Timothy Warren0688ac92012-04-20 10:25:04 -0400136// --------------------------------------------------------------------------
Derek Jones8dca0412010-03-05 13:01:44 -0600137
138/**
139 * CodeIgniter Driver Class
140 *
141 * This class enables you to create drivers for a Library based on the Driver Library.
142 * It handles the drivers' access to the parent library
143 *
144 * @package CodeIgniter
145 * @subpackage Libraries
146 * @category Libraries
147 * @author EllisLab Dev Team
Barry Mienydd671972010-10-04 16:33:58 +0200148 * @link
Derek Jones8dca0412010-03-05 13:01:44 -0600149 */
150class CI_Driver {
Barry Mienydd671972010-10-04 16:33:58 +0200151
Timothy Warren0688ac92012-04-20 10:25:04 -0400152 /**
153 * Instance of the parent class
154 *
155 * @var object
156 */
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300157 protected $_parent;
Derek Jones8dca0412010-03-05 13:01:44 -0600158
Timothy Warren0688ac92012-04-20 10:25:04 -0400159 /**
160 * List of methods in the parent class
161 *
162 * @var array
163 */
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300164 protected $_methods = array();
Andrey Andreev56454792012-05-17 14:32:19 +0300165
Timothy Warren0688ac92012-04-20 10:25:04 -0400166 /**
167 * List of properties in the parent class
168 *
169 * @var array
170 */
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300171 protected $_properties = array();
Derek Jones8dca0412010-03-05 13:01:44 -0600172
Timothy Warren0688ac92012-04-20 10:25:04 -0400173 /**
174 * Array of methods and properties for the parent class(es)
175 *
Andrey Andreev5fd3ae82012-10-24 14:55:35 +0300176 * @static
177 * @var array
Timothy Warren0688ac92012-04-20 10:25:04 -0400178 */
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300179 protected static $_reflections = array();
Derek Jones8dca0412010-03-05 13:01:44 -0600180
181 /**
182 * Decorate
183 *
184 * Decorates the child with the parent driver lib's methods and properties
185 *
Derek Jones8dca0412010-03-05 13:01:44 -0600186 * @param object
187 * @return void
188 */
Greg Akera9263282010-11-10 15:26:43 -0600189 public function decorate($parent)
Derek Jones8dca0412010-03-05 13:01:44 -0600190 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300191 $this->_parent = $parent;
Barry Mienydd671972010-10-04 16:33:58 +0200192
Derek Jones8dca0412010-03-05 13:01:44 -0600193 // Lock down attributes to what is defined in the class
194 // and speed up references in magic methods
Barry Mienydd671972010-10-04 16:33:58 +0200195
Derek Jones8dca0412010-03-05 13:01:44 -0600196 $class_name = get_class($parent);
Barry Mienydd671972010-10-04 16:33:58 +0200197
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300198 if ( ! isset(self::$_reflections[$class_name]))
Derek Jones8dca0412010-03-05 13:01:44 -0600199 {
200 $r = new ReflectionObject($parent);
Barry Mienydd671972010-10-04 16:33:58 +0200201
Derek Jones8dca0412010-03-05 13:01:44 -0600202 foreach ($r->getMethods() as $method)
203 {
204 if ($method->isPublic())
205 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300206 $this->_methods[] = $method->getName();
Derek Jones8dca0412010-03-05 13:01:44 -0600207 }
208 }
209
Pascal Kriete14287f32011-02-14 13:39:34 -0500210 foreach ($r->getProperties() as $prop)
Derek Jones8dca0412010-03-05 13:01:44 -0600211 {
212 if ($prop->isPublic())
213 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300214 $this->_properties[] = $prop->getName();
Derek Jones8dca0412010-03-05 13:01:44 -0600215 }
216 }
Barry Mienydd671972010-10-04 16:33:58 +0200217
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300218 self::$_reflections[$class_name] = array($this->_methods, $this->_properties);
Derek Jones8dca0412010-03-05 13:01:44 -0600219 }
220 else
221 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300222 list($this->_methods, $this->_properties) = self::$_reflections[$class_name];
Derek Jones8dca0412010-03-05 13:01:44 -0600223 }
224 }
Barry Mienydd671972010-10-04 16:33:58 +0200225
Derek Jones8dca0412010-03-05 13:01:44 -0600226 // --------------------------------------------------------------------
Barry Mienydd671972010-10-04 16:33:58 +0200227
Derek Jones8dca0412010-03-05 13:01:44 -0600228 /**
229 * __call magic method
230 *
231 * Handles access to the parent driver library's methods
232 *
Derek Jones8dca0412010-03-05 13:01:44 -0600233 * @param string
234 * @param array
235 * @return mixed
236 */
237 public function __call($method, $args = array())
238 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300239 if (in_array($method, $this->_methods))
Derek Jones8dca0412010-03-05 13:01:44 -0600240 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300241 return call_user_func_array(array($this->_parent, $method), $args);
Derek Jones8dca0412010-03-05 13:01:44 -0600242 }
243
244 $trace = debug_backtrace();
245 _exception_handler(E_ERROR, "No such method '{$method}'", $trace[1]['file'], $trace[1]['line']);
246 exit;
247 }
248
249 // --------------------------------------------------------------------
Barry Mienydd671972010-10-04 16:33:58 +0200250
Derek Jones8dca0412010-03-05 13:01:44 -0600251 /**
252 * __get magic method
253 *
254 * Handles reading of the parent driver library's properties
255 *
Derek Jones8dca0412010-03-05 13:01:44 -0600256 * @param string
257 * @return mixed
258 */
Greg Akera9263282010-11-10 15:26:43 -0600259 public function __get($var)
Derek Jones8dca0412010-03-05 13:01:44 -0600260 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300261 if (in_array($var, $this->_properties))
Derek Jones8dca0412010-03-05 13:01:44 -0600262 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300263 return $this->_parent->$var;
Derek Jones8dca0412010-03-05 13:01:44 -0600264 }
265 }
266
267 // --------------------------------------------------------------------
Barry Mienydd671972010-10-04 16:33:58 +0200268
Derek Jones8dca0412010-03-05 13:01:44 -0600269 /**
270 * __set magic method
271 *
272 * Handles writing to the parent driver library's properties
273 *
Derek Jones8dca0412010-03-05 13:01:44 -0600274 * @param string
275 * @param array
276 * @return mixed
277 */
Greg Akera9263282010-11-10 15:26:43 -0600278 public function __set($var, $val)
Derek Jones8dca0412010-03-05 13:01:44 -0600279 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300280 if (in_array($var, $this->_properties))
Derek Jones8dca0412010-03-05 13:01:44 -0600281 {
Andrey Andreev8486e9c2012-03-26 20:24:12 +0300282 $this->_parent->$var = $val;
Derek Jones8dca0412010-03-05 13:01:44 -0600283 }
284 }
Barry Mienydd671972010-10-04 16:33:58 +0200285
Derek Jones8dca0412010-03-05 13:01:44 -0600286}
Derek Jones8dca0412010-03-05 13:01:44 -0600287
288/* End of file Driver.php */
Andrey Andreev2e3e2302012-10-09 15:52:34 +0300289/* Location: ./system/libraries/Driver.php */