<p>Below I present three options for simplifying my database access when only a single connection is involved (this is often the case for the web apps I work on).</p>

<p>The general idea is to make the DB connection transparent, such that it connects the first time my script executes a query, and then it remains connected until the script terminates.</p>

<p>I'd like to know which one you think is the best and why.  I don't know the names of any design patterns that these might fit so sorry for not using them.  And if there's any <em>better</em> way of doing this with PHP5, please share.</p>

<p>To give a brief introduction: there is a DB_Connection class containing a query method.  This is a third-party class which is out of my control and whose interface I've simplified for the purpose of this example.  In each option I've also provided an example model for an imaginary DB "items" table to give some context.</p>

<p>Option 3 is the one that provides me with the interface I like most, but I don't think it's practical unfortunately.</p>

<p>I've described the pros and cons (that I can see) of each in the comment blocks below.</p>

<p>At the moment I lean towards Option 1 since the burden is put on my DB wrapper class instead of on the models.</p>

<p>All comments appreciated!</p>

<p>Note: For some reason, the Stack Overflow preview is showing an encoded HTML entity instead of underscores.  If the post comes through like that, please take this into account.</p>

<pre><code>&lt;?php

/**
 * This is the 3rd-party DB interface I'm trying to wrap.
 * I've simplified the interface to one method for this example.
 *
 * This class is used in each option below.
 */
class DB_Connection {
    public function &amp;query($sql) { }
}

/**
 * OPTION 1
 *
 * Cons: Have to wrap every public DB_Connection method.
 * Pros: The model code is simple.
 */
class DB {
    private static $connection;
    private static function &amp;getConnection() {
        if (!self::$connection) {
            self::$connection = new DB_Connection();
        }
        return self::$connection;
    }
    public static function &amp;query($sql) {
        $dbh = self::getConnection();
        return $dbh-&gt;query($sql);
    }
}

class Item {
    public static function &amp;getList() {
        return DB::query("SELECT * FROM items");
    }
}

/**
 * OPTION 2
 *
 * Pros: Don't have to wrap every DB_Connection function like in Option 1
 * Cons: Every function in the model is responsible for checking the connection
 */

class DB {
    protected static $connection = null;
    public function connect() {
        self::$connection = new DB_Connection();
    }
}

class Item extends DB {
    public static function &amp;getList() {
        if (!self::$connection) $this-&gt;connect();
        return self::$connection-&gt;query("SELECT * FROM items");
    }
}

/**
 * OPTION 3
 *
 * Use magic methods
 *
 * Pros: Simple model code AND don't have to reimplement the DB_Connection interface
 * Cons: __callStatic requires PHP 5.3.0 and its args can't be passed-by-reference.
 */
class DB {
    private static $connection = null;

    public static function &amp;getConnection() {
        if (!self::$connection) {
            self::$connection = new DB_Connection();
        }
        return self::$connection;
    }

    public static function __callStatic($name, $args) {
        if (in_array($name, get_class_methods('DB_Connection'))) {
            return call_user_func_array(
                array(self::getConnection(), $name), $args);
        }
    }
}
</code></pre>

[{'answer_id': 53399, 'author': 'Dhaust', 'author_id': 242, 'author_profile': 'https://Stackoverflow.com/users/242', 'pm_score': 4, 'selected': True, 'text': "<p>Doh! Someone else here at work figured this out.  It was really simple and I should have been able to sort it, but hey, that's how it goes sometimes.</p>\n\n<p>Here the fix:<br>\nOn the web server, copy the 'aspnet_client' folder from 'C:\\Inetpub\\wwwroot' to 'C:\\Inetpub\\wwwroot\\your-website-name'.  </p>\n\n<p>That's all we did and it's now working.  </p>\n\n<p>Hope this saves someone from all the fuss I just went through.</p>\n"}, {'answer_id': 997321, 'author': 'Emad Gabriel', 'author_id': 120885, 'author_profile': 'https://Stackoverflow.com/users/120885', 'pm_score': 2, 'selected': False, 'text': '<p>Another solution is to simply create a new virtual directory in your web site and point it to "C:/Inetpub/wwwroot/aspnet_client"</p>\n'}, {'answer_id': 1887814, 'author': 'shine jose', 'author_id': 229618, 'author_profile': 'https://Stackoverflow.com/users/229618', 'pm_score': 2, 'selected': False, 'text': "<p>Try this<br>\nOn the web server, copy the 'aspnet_client' folder from 'C:\\Inetpub\\wwwroot'  and past inside your website folder.(where form folder,app_data folder etc will be there)</p>\n"}, {'answer_id': 2735773, 'author': 'Zappos', 'author_id': 328654, 'author_profile': 'https://Stackoverflow.com/users/328654', 'pm_score': 0, 'selected': False, 'text': "<p>I took over maintaining some code produced by another developer who had left and suffered this issue too. In my case the compiled report was looking for the images in the crystalreportview115 folder which existed in my local development path and therefore worked locally. The only folder on on the target server was the CrystalReportWebFormViewer4 (I assume from a previous server installation or site deployment). Simply adding the ...115 folder sorted the problem out for me. </p>\n\n<p>The root cause for us would appear to be the version of Crystal installed on the developers machine. Not sure that helps anyone but thought I'd mention it!</p>\n"}, {'answer_id': 3873935, 'author': 'Syed Nasir Abbas', 'author_id': 468116, 'author_profile': 'https://Stackoverflow.com/users/468116', 'pm_score': 0, 'selected': False, 'text': '<p>Upload aspnet_client folder from c:\\inetpub\\wwwroot folder of your local computer to the httpdocs folder of your web hosting server. Good Luck!!!</p>\n'}]
['https://Stackoverflow.com/questions/53353', 'https://Stackoverflow.com', 'https://Stackoverflow.com/users/-1/']