<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>shapeshifter.se &#187; SQL</title>
	<atom:link href="http://www.shapeshifter.se/tag/sql/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.shapeshifter.se</link>
	<description>Mostly miscellaneous technical mumbo-jumbo.</description>
	<lastBuildDate>Sat, 12 Dec 2009 12:00:49 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.6</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>DSPAM: Converting from the hash driver to MySQL driver</title>
		<link>http://www.shapeshifter.se/2009/03/03/dspam-converting-from-the-hash-driver-to-mysql-driver/</link>
		<comments>http://www.shapeshifter.se/2009/03/03/dspam-converting-from-the-hash-driver-to-mysql-driver/#comments</comments>
		<pubDate>Tue, 03 Mar 2009 21:51:46 +0000</pubDate>
		<dc:creator>fli</dc:creator>
				<category><![CDATA[Tech]]></category>
		<category><![CDATA[DSPAM]]></category>
		<category><![CDATA[hash]]></category>
		<category><![CDATA[MySQL]]></category>
		<category><![CDATA[SQL]]></category>

		<guid isPermaLink="false">http://www.shapeshifter.se/?p=422</guid>
		<description><![CDATA[&#8230;or annoyances with the DSPAM hash driver
I&#8217;ve been running DSPAM for a long time and the spam classification is great, unfortunately the maintenance tools are not as it turns out. This is the tale of why and more especially HOW I moved from the hash driver to the mysql driver as a backend for my [...]]]></description>
			<content:encoded><![CDATA[<h2>&#8230;or annoyances with the DSPAM hash driver</h2>
<p>I&#8217;ve been running DSPAM for a long time and the spam classification is great, unfortunately the maintenance tools are not as it turns out. This is the tale of why and more especially HOW I moved from the hash driver to the mysql driver as a backend for my DSPAM installation.</p>
<p><span id="more-422"></span></p>
<p>It all began a few days ago when the <a href="http://johannes.sipsolutions.net/Projects/dovecot-antispam">dovecot-antispam</a> plugin all of a sudden refused to re-classify mails. This was all very weird because I was possible to re-classify mails from the command line, but the same mail/signature failed from the plugin.</p>
<p>After some debugging and messing with the plugin code I established that it successfully called dspam to re-classify the mail but dspam failed. Hm, maybe a permission problem then&#8230;nope. Same command with same permissions worked from the command line.</p>
<p>At this point I was really puzzled (and quite annoyed), the error made no sense.  So I hacked the plugin to call dspam using a system call tracer (in this case truss which is shipped with FreeBSD) to produce a call trace of the dspam processes within the context of the plugin.</p>
<p>After comparing the outputs from a working case and a non-working case, one line stood out.</p>
<blockquote><p>mmap(0&#215;0,263332768,PROT_READ|PROT_WRITE,MAP_SHARED,4,0&#215;0) ERR#12 &#8216;Cannot allocate memory&#8217;</p></blockquote>
<p>For those who don&#8217;t speak truss. This means that the mmap() system call (map a content of file into memory) failed because of an out of memory condition.</p>
<p>WHY!? Well it obviously hit a built-in mmap limit as the system had a lot of free memory. It was not vm.max_proc_mmap (tried bumping it, didn&#8217;t work). vm.kmem_size_max is large (64-bit system) and the uid had unlimited resources (ulimit). I&#8217;m still puzzled by this.</p>
<p>As the title reveals I&#8217;m running DSPAM with the hash driver, why? mostly because it was the default back-end driver in DSPAM when I installed it (and I was young and naive).</p>
<p>Wonder why it hit the limit in the first place, a quick look in /var/db/dspam/data reveals that the hash database with tokens for this particular user had grown to ~250MB.</p>
<p>Why so big? DSPAM comes with a cleaning utility called dspam_clean to clean out unused data, I&#8217;ve been running this nightly to keep stuff neat and tidy. Well, here comes the fun part.</p>
<p>It turns out that dspam_clean doesn&#8217;t actually do anything when you&#8217;re running the hash driver, it just looks like its working and takes ages to execute. There is no mentioning of this in any user documentation I found. With the hash driver you&#8217;re supposed to run cssclean&#8230;only that this program doesn&#8217;t work either &#8211; unless you patch it. I found a patch dubbed <a href="http://www.mail-archive.com/dspam-dev@lists.nuclearelephant.com/msg00066.html">&#8220;cssclean is a redheaded stepchild&#8221;</a> sent to the (now defunct, and moved to sourceforge) dspam-dev@ list at nuclearelephant.com that took care of this. The patch missed an include (at least on FreeBSD) that caused it to crash on 64-bit platforms (64/32-bit pointer truncation). The whole patch is included at the bottom of the page.</p>
<p>To summarize it, the maintenance tools are virtually non-existing when using the hash driver.</p>
<p>Probably a good opportunity to convert to the mysql driver instead (as I&#8217;ve been meaning to do for the last year or so).</p>
<h2>Converting from the hash driver to mysql</h2>
<p>There is a tool included with the DSPAM package called dspam_2sql, but of course this didn&#8217;t work properly either. Most important, it didn&#8217;t work with virtual users and just refused to run. Also timestamps on token data were ignored. I&#8217;ve hacked together a patch to fix theses issues, it&#8217;s available at the bottom of the page.</p>
<p>I first attempted to import non-cleaned data into the SQL database&#8230;big mistake. I aborted the progress when the token table had about 8 million entries (and weren&#8217;t even done with 1 user).</p>
<h3>Quick recipe on how to do the conversion</h3>
<p>First</p>
<ul>
<li>Grab the source package for dspam-3.8.0</li>
<li>Download the patches at the bottom of this page</li>
</ul>
<p>Patch and compile the sources</p>
<blockquote><p>tar xzf dspam-3.8.0.tar.gz<br />
cd dspam-3.8.0<br />
patch -p1 &lt; dspam_cssclean.patch<br />
patch -p1 &lt; dspam_2sql_virtuser.patch<br />
cd src<br />
make</p></blockquote>
<p>The patched cssclean tools can be found in tools.hash_drv</p>
<p>Run tools.hash_drv/cssclean on all users (or users that receive a lot of mail). <strong>Backup your database (/var/db/dspam) first</strong>.</p>
<p>Example</p>
<blockquote><p>tools.hash_drv/cssclean /var/db/dspam/user@domain.tld/user@domain.tld.css</p></blockquote>
<p>You can check the number of entries with cssstat</p>
<p>Create a MySQL database and user for dspam, I&#8217;ve called mine dspam. The table defintions can be found in tools.mysql_drv</p>
<blockquote><p>mysql -D dspam -u dspam -p &lt; tools.mysql_drv/mysql_objects-speed.sql<br />
mysql -D dspam -u dspam -p &lt; tools.mysql_drv/virtual_users.sql</p></blockquote>
<p>You should now have a database with tables and a cleaned hash database, the only thing left is to convert it. dspam_2sql will output SQL statements, just feed these into MySQL.</p>
<p>For example, the conversion can be done like this</p>
<blockquote><p>tools/dspam_2sql | mysql -D dspam -u dspam -p</p></blockquote>
<p>Beaware that it probably will take a lot of time.</p>
<p>You can convert one single user with</p>
<blockquote><p>dspam_2sql &#8211;user=user@domain.tld</p></blockquote>
<p>That&#8217;s it. Modify your dspam.conf to use the MySQL driver and restart dspam.</p>
<h3>Performance</h3>
<p>The MySQL driver IS slower than the hash driver. The processing time for a message with the hash driver was around 0.1-0.2 seconds on this hardware. The MySQL driver takes between 0.2-2 seconds for a message.</p>
<p>The slowdown is not a problem for me. Things like real database consistency (some of my users had duplicated tokens with the hash driver), better maintenance tools, easier manipulation of the data (and the benefits of my MySQL replication+backup configuration) makes it well worth it.</p>
<h2>Patches</h2>
<ul>
<li><a href="http://www.shapeshifter.se/wp-content/uploads/2009/03/dspam_cssclean.patch">dspam_cssclean</a> &#8211; cssclean patch found on mailing list. Posted by Frank Cusack.</li>
<li><a href="http://www.shapeshifter.se/wp-content/uploads/2009/03/dspam_2sql_virtuser.patch">dspam_2sql_virtuser</a> &#8211; dspam_2sql patchset. Virtual user support etc.</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.shapeshifter.se/2009/03/03/dspam-converting-from-the-hash-driver-to-mysql-driver/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Generic Object Oriented SQL interface for PHP</title>
		<link>http://www.shapeshifter.se/2008/08/01/generic-object-oriented-sql-interface-for-php/</link>
		<comments>http://www.shapeshifter.se/2008/08/01/generic-object-oriented-sql-interface-for-php/#comments</comments>
		<pubDate>Fri, 01 Aug 2008 15:19:34 +0000</pubDate>
		<dc:creator>fli</dc:creator>
				<category><![CDATA[General]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[SQL]]></category>

		<guid isPermaLink="false">http://www.shapeshifter.se/?p=137</guid>
		<description><![CDATA[This is an extensible object oriented wrapper around the MySQL and MSSQL (Microsoft SQL Server) interfaces provided by PHP. I&#8217;ve been using them for a while, it&#8217;s nothing new and no rocket science but others might find them useful.

Why do this at all? why just not stick with the API provided by PHP? It&#8217;s really [...]]]></description>
			<content:encoded><![CDATA[<p>This is an extensible object oriented wrapper around the MySQL and MSSQL (Microsoft SQL Server) interfaces provided by PHP. I&#8217;ve been using them for a while, it&#8217;s nothing new and no rocket science but others might find them useful.<br />
<!-- WSA: rules for context 'adsense-post-square' did not apply --><br />
Why do this at all? why just not stick with the API provided by PHP? It&#8217;s really nothing else than a more convenient way to interact with a SQL server and exposing it&#8217;s interface in a vendor natural way. Instead of writing <em>mysql_query</em> everywhere, one simply writes <em>query</em>.</p>
<p>Having a consistent interface will obviously help if you are using multiple types of database servers or someday would like to migrate to another SQL server (of course, weird and vendor specific SQL code could be a problem in this case). Other advantages are things like automatic disconnection on object destruction etc.</p>
<p>The foundation is an abstract class called <em>SQLConnector</em> and provides the basic interface. The class will connect to the database on creation and disconnect when the object is destroyed, it also implements <em>__sleep</em> and <em>__wakeup</em> so that it&#8217;s possible to serialize a SQL connection.</p>
<p>Because <em>SQLConnector</em> is abstract one can&#8217;t create objects directly from it, we&#8217;ll create child classes for each type of SQL-server we want to connect to. These objects will share the same interface and can be used interchangeably.<br />
<span id="more-137"></span></p>
<p>File <strong>db_iface.inc</strong></p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #339933;">&lt;</span>php
abstract <span style="color: #000000; font-weight: bold;">class</span> SQLConnector
<span style="color: #009900;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_dbAddress</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">/* Address of SQL server */</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_dbAccount</span><span style="color: #339933;">;</span> <span style="color: #666666; font-style: italic;">/* Account name (username) */</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_dbPwd</span><span style="color: #339933;">;</span>     <span style="color: #666666; font-style: italic;">/* Password */</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_dbName</span><span style="color: #339933;">;</span>    <span style="color: #666666; font-style: italic;">/* Initial database */</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/* Base constructor */</span>
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">function</span> __construct<span style="color: #009900;">&#40;</span><span style="color: #000088;">$address</span><span style="color: #339933;">,</span> <span style="color: #000088;">$account</span><span style="color: #339933;">,</span> <span style="color: #000088;">$pwd</span><span style="color: #339933;">,</span> <span style="color: #000088;">$name</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbAddress</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$address</span><span style="color: #339933;">;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbAccount</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$account</span><span style="color: #339933;">;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbPwd</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$pwd</span><span style="color: #339933;">;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbName</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$name</span><span style="color: #339933;">;</span>
&nbsp;
        <span style="color: #666666; font-style: italic;">/* Call the connect method in the child class */</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">connect</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbAddress</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbAccount</span><span style="color: #339933;">,</span>
            <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbPwd</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbName</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/* Let the child disconnect when the object is destroyed */</span>
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">function</span> __destruct<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">disconnect</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/* We are about to be serialized, disconnect
     * and return data needed for serialization
     */</span>
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">function</span> __sleep<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">disconnect</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #990000;">array</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'m_dbAddress'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'m_dbAccount'</span><span style="color: #339933;">,</span>
            <span style="color: #0000ff;">'m_dbPwd'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'m_dbName'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/* We have been unserialized, re-connect */</span>
    <span style="color: #000000; font-weight: bold;">public</span> <span style="color: #000000; font-weight: bold;">function</span> __wakeup<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">connect</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbAddress</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbAccount</span><span style="color: #339933;">,</span>
            <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbPwd</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbName</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Abstract methods that needs to be implemented by child classes
     */</span>
    abstract protected <span style="color: #000000; font-weight: bold;">function</span> connect<span style="color: #009900;">&#40;</span><span style="color: #000088;">$address</span><span style="color: #339933;">,</span> <span style="color: #000088;">$account</span><span style="color: #339933;">,</span>
        <span style="color: #000088;">$pwd</span><span style="color: #339933;">,</span> <span style="color: #000088;">$name</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract protected <span style="color: #000000; font-weight: bold;">function</span> disconnect<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract <span style="color: #000000; font-weight: bold;">function</span> query<span style="color: #009900;">&#40;</span><span style="color: #000088;">$query</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract <span style="color: #000000; font-weight: bold;">function</span> fetchRow<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract <span style="color: #000000; font-weight: bold;">function</span> fetchAll<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract <span style="color: #000000; font-weight: bold;">function</span> getNumRows<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract <span style="color: #000000; font-weight: bold;">function</span> freeResult<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    abstract <span style="color: #000000; font-weight: bold;">function</span> getError<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #000000; font-weight: bold;">?&gt;</span></pre></div></div>

<p>The following class implements MySQL connectivity using the interface above</p>
<p>File: <strong>db_mysql.inc</strong></p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">&lt;?php</span>
&nbsp;
<span style="color: #b1b100;">require_once</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'db_iface.inc'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">class</span> MySQLConnector <span style="color: #000000; font-weight: bold;">extends</span> SQLConnector
<span style="color: #009900;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_dbHandle</span><span style="color: #339933;">;</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_Result</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/* 
     * Connect function, also selects correct database
     * Returns 1 upon success, otherwise 0
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> connect<span style="color: #009900;">&#40;</span><span style="color: #000088;">$address</span><span style="color: #339933;">,</span> <span style="color: #000088;">$account</span><span style="color: #339933;">,</span> <span style="color: #000088;">$pwd</span><span style="color: #339933;">,</span> <span style="color: #000088;">$name</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span> <span style="color: #339933;">=</span> <span style="color: #339933;">@</span><span style="color: #990000;">mysql_connect</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$address</span><span style="color: #339933;">,</span> <span style="color: #000088;">$account</span><span style="color: #339933;">,</span> <span style="color: #000088;">$pwd</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
        <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span> <span style="color: #339933;">!=</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #990000;">mysql_select_db</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$name</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">1</span><span style="color: #339933;">;</span>
            <span style="color: #009900;">&#125;</span>
            <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
                <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
            <span style="color: #009900;">&#125;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Disconnect function
     * Returns 1 upon success, otherwise 0
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> disconnect<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">@</span><span style="color: #990000;">mysql_close</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">!=</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">1</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
&nbsp;
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Does a mysql-query, returns 1 upon sucess otherwise 0
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> query<span style="color: #009900;">&#40;</span><span style="color: #000088;">$query</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span> <span style="color: #339933;">=</span> <span style="color: #990000;">mysql_query</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$query</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
        <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span> <span style="color: #339933;">!=</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">1</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Fetches an array row
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> fetchRow<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #990000;">mysql_fetch_array</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">function</span> fetchAll<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$row</span> <span style="color: #339933;">=</span> <span style="color: #990000;">mysql_fetch_array</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #000088;">$a_rs</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$row</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #990000;">mysql_free_result</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #000088;">$a_rs</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
    <span style="color: #666666; font-style: italic;">/*
     * Get number of rows
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> getNumRows<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #990000;">mysql_num_rows</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Free resources allocated by a query 
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> freeResult<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #990000;">mysql_free_result</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Get errorstring
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> getError<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #990000;">mysql_error</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>A (very) similar class for MSSQL connectivity<br />
File: <strong>db_mssql.inc</strong></p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #000000; font-weight: bold;">&lt;?php</span>
<span style="color: #b1b100;">require_once</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'db_iface.inc'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000000; font-weight: bold;">class</span> MSSQLConnector <span style="color: #000000; font-weight: bold;">extends</span> SQLConnector
<span style="color: #009900;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_dbHandle</span><span style="color: #339933;">;</span>
    <span style="color: #000000; font-weight: bold;">private</span> <span style="color: #000088;">$m_Result</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Connect function, also selects correct database
     * Returns 1 upon success, otherwise 0
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> connect<span style="color: #009900;">&#40;</span><span style="color: #000088;">$address</span><span style="color: #339933;">,</span> <span style="color: #000088;">$account</span><span style="color: #339933;">,</span> <span style="color: #000088;">$pwd</span><span style="color: #339933;">,</span> <span style="color: #000088;">$name</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span> <span style="color: #339933;">=</span> <span style="color: #339933;">@</span><span style="color: #990000;">mssql_connect</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$address</span><span style="color: #339933;">,</span> <span style="color: #000088;">$account</span><span style="color: #339933;">,</span> <span style="color: #000088;">$pwd</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
        <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span> <span style="color: #339933;">!=</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #990000;">mssql_select_db</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$name</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
                <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">1</span><span style="color: #339933;">;</span>
            <span style="color: #009900;">&#125;</span>
            <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
                <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
            <span style="color: #009900;">&#125;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Disconnect function
     * Returns 1 upon success, otherwise 0
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> disconnect<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #339933;">@</span><span style="color: #990000;">mssql_close</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">!=</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">1</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
    <span style="color: #666666; font-style: italic;">/*
     * Does a mssql-query, returns 1 upon success otherwise 0
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> query<span style="color: #009900;">&#40;</span><span style="color: #000088;">$query</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span> <span style="color: #339933;">=</span> <span style="color: #990000;">mssql_query</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$query</span><span style="color: #339933;">,</span> <span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
        <span style="color: #b1b100;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span> <span style="color: #339933;">!=</span> <span style="color: #cc66cc;">0</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">1</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #b1b100;">else</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #b1b100;">return</span> <span style="color: #cc66cc;">0</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Fetches an array row
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> fetchRow<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #990000;">mssql_fetch_array</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #000000; font-weight: bold;">function</span> fetchAll<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$row</span> <span style="color: #339933;">=</span> <span style="color: #990000;">mssql_fetch_array</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #000088;">$a_rs</span><span style="color: #009900;">&#91;</span><span style="color: #009900;">&#93;</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$row</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
        <span style="color: #990000;">mssql_free_result</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #000088;">$a_rs</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Get number of rows
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> getNumRows<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">return</span> <span style="color: #990000;">mssql_num_rows</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #666666; font-style: italic;">/*
     * Free resources allocated by a query
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> freeResult<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#123;</span>
        <span style="color: #990000;">mssql_free_result</span><span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_Result</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
    <span style="color: #666666; font-style: italic;">/*
     * Get errorstring
     */</span>
    <span style="color: #000000; font-weight: bold;">function</span> getError<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#123;</span>
        <span style="color: #b1b100;">return</span> mssql_error<span style="color: #009900;">&#40;</span><span style="color: #000088;">$this</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">m_dbHandle</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span>
<span style="color: #000000; font-weight: bold;">?&gt;</span></pre></div></div>

<p>So, how do one use this then? It&#8217;s quite simple</p>

<div class="wp_syntax"><div class="code"><pre class="php" style="font-family:monospace;"><span style="color: #b1b100;">require_once</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'db_mysql.inc'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #b1b100;">require_once</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'db_mssql.inc'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000088;">$c1</span> <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> MySQLConnector<span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'mysql-host'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'username'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'password'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'mydb'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #000088;">$c2</span> <span style="color: #339933;">=</span> <span style="color: #000000; font-weight: bold;">new</span> MSSQLConnector<span style="color: #009900;">&#40;</span><span style="color: #0000ff;">'mssql-host'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'username'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'password'</span><span style="color: #339933;">,</span> <span style="color: #0000ff;">'mydb'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #000088;">$c1</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">query</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;select something from somewhere&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #b1b100;">while</span> <span style="color: #009900;">&#40;</span><span style="color: #000088;">$row</span> <span style="color: #339933;">=</span> <span style="color: #000088;">$c1</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">fetchRow</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
 <span style="color: #339933;">...</span>
<span style="color: #009900;">&#125;</span>
&nbsp;
<span style="color: #000088;">$c2</span><span style="color: #339933;">-&gt;</span><span style="color: #004000;">query</span><span style="color: #009900;">&#40;</span><span style="color: #0000ff;">&quot;select somethingelse from somewhereelse&quot;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Improvements, oh yes. The connect functions should really throw an error if things doesn&#8217;t work.<br />
Also, wrappers for any SQL server should be quite easy to implement.</p>
<ul>
<li><a href='http://www.shapeshifter.se/wp-content/uploads/2008/08/db_iface.phps'>db_iface.inc</a> &#8211; Abstract interface</li>
<li><a href='http://www.shapeshifter.se/wp-content/uploads/2008/08/db_mysql.phps'>db_mysql.inc</a> &#8211; MySQL interface</li>
<li><a href='http://www.shapeshifter.se/wp-content/uploads/2008/08/db_mssql.phps'>db_mssql.inc</a> &#8211; MSSQL interface</li>
</ul>
<p>If this article was usable or otherwise helpful for you, tell a friend or put a link back from your own website/blog.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.shapeshifter.se/2008/08/01/generic-object-oriented-sql-interface-for-php/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
	</channel>
</rss>
