Reputation: 311
I'm having trouble with this very confusing error. I have a class and an extended class. If my extended file name starts with a capital B then it cannot find my database class. If I name anything else, literally anything else it works.
My database class looks like so
class Database
{
public $db;
public function __construct()
{
if (DATABASE == true)
{
$this->db = new mysqli(HOSTNAME, USERNAME, PASSWORD, DBNAME);
if ($this->db->connect_error)
{
exit('Some of the database login credentials seem to be wrong.' . '-' . $this->db->connect_error);
}
}
}
}
my extended class is like so
class BlogModel extends Database
{
public function getBlogPosts()
{
$query = array();
if ($result = $this->db->query('SELECT * FROM blog'))
{
while ($row = $result->fetch_assoc())
{
$query[] = $row;
}
$result->free();
}
return $query;
$mysqli->close();
}
}
The filename BlogModel.php causes the error.
Fatal error: Class 'Database' not found in C:\wamp\www\website\app\model\BlogModel.php on line 4
If I change it to blogModel.php it works. I don't mind just changing the filename but in the interest of understanding and learning I'd like to know why this is happening.
Edit: This is how I include the files
define('ROOT', str_replace('\\', '/', $_SERVER['DOCUMENT_ROOT']));
define('HOST', $_SERVER['HTTP_HOST']);
define('URL', $_SERVER['REQUEST_URI']);
define('APP', ROOT . '/app/');
define('MODEL', ROOT . '/app/model/');
define('VIEW', APP . '/view/');
define('CONTROLLER', ROOT . '/app/controller/');
$models = array_diff(scandir(MODEL), array('.', '..'));
foreach ($models as $m)
{
require_once MODEL . $m;
}
Upvotes: 0
Views: 108
Reputation: 7911
To use an autoloader that is PSR compliant you would need to restructure your directory tree.
The code I use is a (not fully) PSR-4 compliant code:
<?php
#cn is class name
#fn is file name
#ns is namespace
#np is namespace pointer
class Loader{
public function load($class){
$cn = ltrim($class, '\\');
$fn = '';
$ns = '';
if($np = strrpos($cn, '\\')){
$ns = substr($cn, 0, $np);
$cn = substr($cn, $np + 1);
$fn = str_replace('\\', DIRECTORY_SEPARATOR, $ns) . DIRECTORY_SEPARATOR;
}
require ($fn .= strtolower(str_replace('_', DIRECTORY_SEPARATOR, $cn)) . '.php');
}
public function __construct(){
spl_autoload_register([$this, 'load']);
}
}
new Loader;
?>
It will load files in a lower case filename, if you do not use namespaces it will attempt to load from the document root if the object does not exist.
If you are using namespaces, aka:
$var = new \path\to\ObjeCt();
It would attempt to load object.php
from webroot\path\to\
How one would use this is simple, just include this file and the next time you create an object keep the namespace valid to the path.
Upvotes: 2