Newsgroup: it.comp.www.php
Titolo: [LUNGO] strutturare progetto con autoload e config

Salve a tutti,
tempo fa avevo aperto una discussione sull'autoload, ora sto cercando di 
mettere in pratica il tutto ma ho dei problemi...
struttura directory:
    /config.php <-- file di configurazione generato dall'installer
    /lib <-- contiene tutte le classi
    /modules <--contiene i .php
    /themes <--contiene i template di smarty
ora, per usare l'autoload, dovrei creare un file su lib/, chiamiamolo 
common.php che fa l'autoload:
    function __autoload($class_name) {
        require_once $class_name . '.lib.php';
    }
e una libreria d'esempio config.lib.php fatta cosi':
    class config
    {
	static $perc;
	function __construct()
	{
		require(dirname(__FILE__)."/../config.php");
		self::$perc=$perc;
	}
    	static function defpath()
    	{    		return self::$perc;
    	}
    }
ed un file config.php
    $perc="ciao";
ora, essendo config una classe statica, io dovrei poter creare un file 
test.php di questo tipo:
    include (dirname(__FILE__)."/../lib/common.php");
    echo config::defpath();
ma... non mi funziona :( mentre, se creo l'istanza della classe tutto va 
regolarmente...
domande:
1) e' corretta una struttura di questo tipo? vorrei arrivare ad includere in 
tutti i file del progetto un solo file (common.php) e caricare solo le 
classi che verranno poi utilizzate
2) nel caso di classi che hanno bisogno di un minimo di config, come ad 
esempio smarty che mi richiede i percorsi dove glieli inserisco? faccio un 
if nell'autoload?
3) avrei bisogno di avere disponibili i parametri della configurazione, ad 
esempio config::dir_del_progetto(), e' sufficiente l'autoload e la classe 
sopra indicata?
ho scritto un poema lo so, ma vorrei ristrutturare un po' il progetto e 
vorrei farlo nel modo giusto! Ringrazio tutti coloro che saranno arrivati a 
leggere fino qui :)
Dade 

 classe sopra indicata?
Non credo di aver capito benissimo cosa intendi, ma azzardo che quello che 
hai (opportunamente sistemato come dicevo sopra) sia sufficiente.
Bye.

 Bye.
grazie 1000!!!
 


ehmm mi sa che mi sfugge qualcosa...
ho applicato il singleton alla classe config:
class config
{
	private static $instance = null;
	public static $defpath;
   public static function getInstance()
   {
      if(self::$instance == null)
      {
         $c = __CLASS__;
         self::$instance = new $c;
      }
      return self::$instance;
   }
	function __construct()
	{
		if(is_file(dirname(__FILE__)."/../config.php")){
			require(dirname(__FILE__)."/../config.php");
		}else{
			die(); //Installation...
		}
		self::$defpath=$perc;
	}
}
ora mi aspetto che facendo da uno script:
require_once("config.lib.php); <-- in realta' c'ho l'autoloading, 
funzionante, verificato con is_object ;-)
$test=new config;
echo $test->defpath;
mi stampi il valore di defpath... invece non stampa nulla pur venendola 
correttamente riempita...
altra domandina per capire meglio il singleton... praticamente si crea 
un'unica istanza per ogni utente... se quindi ho 2 utenti connessi alla 
classe, avro' 2 istanze giusto?
grazie 1000
Dade 

 classe, avro' 2 istanze giusto?
Parzialmente esatto, ma questo perche` hai due istanze del tuo software in 
esecuzione (ogni utente, anzi, ogni pagina ha il SUO script PHP in 
esecuzione).
Un utente puo` avere anche 100 istanze di singleton, se apre 100 pagine 
contemporaneamente.
La frase corretta e` "ogni script ha una sola istanza del singleton".
Lo script muore appena prima che tu veda la pagina sul browser, e con lui 
muore il singleton e tutte le variabili dello script stesso.
Bye.

 Bye.
scusami ma sono un po' cocciuto...  grazie tantissimo per le spiegazioni
 

 1 giusto?
Dipende da tutto il resto dell'applicazione. In linea di massima si`, ma 
potresti anche non aver bisogno del singleton.
Il singleton si usa molto poco, a dire il vero. Io lo uso per la config e 
per il front-controller, per esempio.
Per i DB non l'ho praticamente mai usato: piuttosto si usa un factory, per 
ottenere l'astrazione dal DB.
Per esempio:
$db = new Database($username, $password, $dbname);
$listanews = $db->fetchAll("news");
$listaprodotti = $db->fetchAll("prodotti");
Come vedi c'e` una sola istanza ceh fa query su diverse tabelle. Non serve 
il singleton.
Bye.

 Bye.
grazie 1000!!!
 

 singleton possa essere utile!
Attenzione, pero`: rischi di sovrascrivere i risultati con un'altra query, 
prima di recuperarli. Stai attento alla "concorrenza" (anche se in questo 
caso non e` vera concorrenza).
L'ideale sarebbe avere una classe per la connessione al DB che, alla 
query, ritorna una classe diversa (creata apposta) con la lista dei 
risultati. In questo modo puoi avere la classe per il DB come singleton, e 
oggetti multipli per i risultati ottenuti.
Uno degli errori piu` comuni quando si programma a oggetti (ci sono 
cascato anche io, cosa credi? ;) ) e` di fare troppo poche classi, e 
delegare a una sola piu` compiti possibili.
L'errore opposto (farne troppe) e` comunque meno deleterio, perche` 
impatta quasi solo sulle prestazioni. Si migliora con l'esperienza. :)
Bye.

 wrote in message 
news:5mhl3fF...@mid.individual.net...

Giusto hai ragione! Beh, in teoria problemi di "concorrenza" non dovrei 
averne, pero' onde evitare di pastrocchi lascio tutto com'e' che per ora va 
piu' che bene :) Se poi scopro che questo mi appesantisce troppo, tiro fuori 
il risultato dalla classe :)
grazie 1000!!!
Dade 


Fatal error: Cannot redeclare __autoload() (previously declared in 
common.php:3) in common.php on line 5
:(((((  Mi sa che la mia struttura fa acqua da qualche parte...
 

 :(((((  Mi sa che la mia struttura fa acqua da qualche parte...
require_once("common.php");
Ma controlla perche` viene incluso piu` di una volta.
Lo devi includere solo nelle pagine, non nelle classi, per esempio.
Bye.

 wrote in message 
news:5mhq27F...@mid.individual.net...

ehmm ultima domandina poi non rompo piu' con il singleton... promesso :)
come uso una classe con un parametro nel costruttore?
$test=config("\blablabla\blablabla")::getInstance();
 

 $test=config("\blablabla\blablabla")::getInstance();
Non la usi.
Passi il parametro in seguito
$test = config::getInstance();
$test->setParametro("\blablabla...");
Una volta settato, e` li` anche al successivo getInstance, non serve 
assegnarlo ogni volta, solo la prima.
Bye.