Event handler ‚Database::initialize‘ is not callable. (CD-collection s vyuzitim MySQL)

Upozornění: Tohle vlákno je hodně staré a informace nemusí být platné pro současné Nette.
Endrju
Člen | 147
+
0
-

Ahoj, s Nette se teprve seznamuji a drive jsem s zanym PHP frameforkem nemel zadnou zkusenost.

Predesilam, ze jsem si precetl serial na „Začínáme s Nette Framework“ na serveru „Zdroják“.

Na foru nebo v ukazkovych aplikacich postradam nejakou kompletni ukazku prace s MySQL databazi pres modely s vyuzitim dibi. Nasel jsem jen utrzky kodu, ze kterych jsem si ale nedokazal poskladat funkcni aplikaci. Predem dekuji za pomoc.

Chci vytvorit rozzsahlejsi aplikaci s vyuzitim Nette a hned na zacatku jsem narazil na problem s vyuzitim MySQL databaze. Snazim se upravit CD-collection z examples, pro pouziti s MySQL db a nedari se mi to. Zkusel jsem pouzit ruzne navrhy reseni tady na foru, ale zda se, ze nekde delam chybu.

Chyba, kteru mi zobrazuje Ladicka:

InvalidStateException
Event handler 'Database::initialize' is not callable.
1. Nette/Object.php (110) source ►  ObjectMixin:: call (arguments ►)
2. <PHP inner-code>  Object-> __call (arguments ►)
3. Application/Application.php (118) source ►  Application-> onStartup (arguments ►)
Line 111:            do {
Line 112:                try {
Line 113:                    if (count($this->requests) > self::$maxLoop) {
Line 114:                        throw new ApplicationException('Too many loops detected in application life cycle.');
Line 115:                    }
Line 116:
Line 117:                    if (!$request) {
Line 118:                        $this->onStartup($this);
Line 119:
Line 120:                        // default router
Line 121:                        $router = $this->getRouter();
Line 122:                        if ($router instanceof MultiRouter && !count($router)) {
Line 123:                            $router[] = new SimpleRouter(array(
Line 124:                                'presenter' => 'Default',
Line 125:                                'action' => 'default',
4. app/bootstrap.php (35) source ►  Application-> run ()
5. document_root/index.php (19) source ►  require (arguments ►)

Adresarova struktura v root directory:

app/
	models/
		Database.php
	presenters/
		DefaultPresenter.php
	temp/
	templates/
		@layout.phtml
		Default.default.phtml
	bootstrap.php
	config.ini
document_root/
	index.php
libs/
	dibi/
	Nette/

Ted jak vypada obsah jednotlivych souboru:

document_root/index.php

<?php
define('WWW_DIR', dirname(__FILE__));

define('APP_DIR', WWW_DIR . '/../app');

define('LIBS_DIR', WWW_DIR . '/../libs');

require APP_DIR . '/bootstrap.php';
?>

app/models/Database.php

<?php
class Database extends Object
{
	private $connection;

	public static function initialize()
	{
		dibi::connect(Environment::getConfig('database'));
	}

	public function __construct()
	{
		$this->connection = dibi::getConnection();
	}
}
?>

app/bootstrap.php

Nevim, zda musim nekde nacitat soubor Database.php, kdyz pak tridu Databse volam v metode onStartup volam$application->onStartup[] = 'Database::initialize';. Nevim, zda Nette samo nacita soubory dusledkem volani Metod a trid, ktere jsou v techto souborech (a ty jsou umistene ve spravnych adresarich). TOhle jsem se nikde nedocetl (nebo jsem byl nepozorny).

<?php

require LIBS_DIR . '/Nette/loader.php';

require LIBS_DIR . '/dibi/dibi/dibi.php';


Debug::enable();

Environment::loadConfig();

$application = Environment::getApplication();

$application->onStartup[] = 'Database::initialize';

$router = $application->getRouter();

$router[] = new Route('index.php', array(
	'presenter' => 'Default',
	'view' => 'default',
), Route::ONE_WAY);

$router[] = new Route('<presenter>/<view>/<id>', array(
	'presenter' => 'Default',
	'view' => 'default',
	'id' => NULL,
));

$application = Environment::getApplication();
$application->run();
?>

app/config.ini

[common]
set.date-timezone = "Europe/Prague"
set.iconv-internal_encoding = "%encoding%"
set.mbstring-internal_encoding = "%encoding%"

database.driver = mysql
database.host = localhost
database.username = root
database.password = pass
database.database = databasename
database.charset = utf8
database.lazy = TRUE

; Production site configuration data
[production < common]
set.include_path = "%appDir%/libs;%modelsDir%/;%presentersDir%/"

; Staging site configuration data inherits from production and
; overrides values as necessary
[development < production]

SW, ktery pouzivam:

  • WampServer 2.0
  • aktualne pouzivam PHP 5.2.9–2, ale mam k dispozici i PHP 5.3
  • apache 2.2.11
  • MySQL 5.1.36
  • Nette 0.9-PHP-5.2
  • dibi-1.2

Nechal jsem take spustit „Requirements-Checker“ z adresare tools, ktery prosel s jedinou vystrahou, a to „ImageMagick library – Disabled (ImageMagick server library is absent. You will not be able to use Nette\ImageMagick.)“

Snad jsem vam dal k dospozici vsechny potrebne informace..

Dekuji za vasi pomoc s resenim problemu.


EDIT:
Zrejme jsem chybu prozatim vyresil. Problem byl v tom, ze trida Database se nenacitala automaticky. Prisel jsem na to po prostudovani prikladu Akrabat – https://wiki.nette.org/…ialy/akrabat

Stezejni upravu kodu jsem provedl v souboru bootstrap.php pridanim Robotloaderu, ktery zajisti automaticke nacitani trid (v kodu je to bod 2d):

<?php

// Step 1: Load Nette Framework and Dibi
// this allows load Nette Framework classes automatically so that
// you don't have to litter your code with 'require' statements
require LIBS_DIR . '/Nette/loader.php';
require LIBS_DIR . '/dibi/dibi.php';



// Step 2: Configure environment
// 2a) enable Nette\Debug for better exception and error visualisation
Debug::enable();

// 2b) load configuration from config.ini file
Environment::loadConfig();

// 2c) check if directory /app/temp is writable
if (@file_put_contents(Environment::expand('%tempDir%/_check'), '') === FALSE) {
	throw new Exception("Make directory '" . Environment::getVariable('tempDir') . "' writable!");
}

// 2d) enable RobotLoader - this allows load all classes automatically
$loader = new RobotLoader();
$loader->addDirectory(APP_DIR);
$loader->addDirectory(LIBS_DIR);
$loader->register();



// Step 3: Configure application
// 3a) get and setup a front controller
$application = Environment::getApplication();

// 3b) establish database connection
$application->onStartup[] = 'Database::initialize';



// Step 4: Setup application router
$router = $application->getRouter();

// mod_rewrite detection
if (function_exists('apache_get_modules') && in_array('mod_rewrite', apache_get_modules())) {
	$router[] = new Route('index.php', array(
		'presenter' => 'Default',
		'action' => 'default',
	), Route::ONE_WAY);

	$router[] = new Route('<presenter>/<action>/<id>', array(
		'presenter' => 'Default',
		'action' => 'default',
		'id' => NULL,
	));

} else {
	$router[] = new SimpleRouter('Default:default');
}



// Step 5: Run the application!
$application->run();
?>

Editoval Endrju (2. 11. 2009 2:09)