Hi,

Tried to post this as a comment on the wiki, but its slow/dying or dead.

One thing I think that could simplify some of this, is telling the back end
where to put values, rather than ask for them and having to juggle them
about. Especially when have to deal with joins and particularly self joins,
as each set of fields can be bound to their own scope.

The also an added advantage is that PDO & MySQLi backends can be told where
to put column values, so PDOStatement::fetch(PDO::FETCH_BOUND) or
MySQLI_STMT::fetch() respectively can do most of the actual mapping. 

A crude example (which is all kinds of wrong in other aspects... ) is
below..

Jared


<?php

function query(PDO $pdo, $sql, array $refs = null, array $params = null)
{
    $query = $pdo->prepare($sql);
    if ($query->execute($params))
    {
        if ($refs)
        {
            $i = 1;
            foreach($refs as &$ref)
                $query->bindColumn($i++, $ref);
        }
        return function() use ($query)
            {
                return $query->fetch(\PDO::FETCH_BOUND);
            };
    }
    return false;
}

function findAllAndBoss(PDO $pdo)
{
    $e = array();
    $b = array();

    $iterator = query($pdo, 'SELECT e.id, e.name, e.email, 
                                b.id, b.name, b.email FROM "Employee" e LEFT
JOIN "Employee" b ON e.boss = b.id')
                array(
                    &$e['id'], &$e['name'], &$e['email'],
                    &$b['id'], &$b['name'], &$b['email']));
    return function() use (&$e, &$b, $iterator)
        {
            if ($iterator())
            {
                // IdentityMap lookup omitted...
                $employee = new Employee();
                $employee->setState($e);

                // IdentityMap lookup omitted...

                if (isset($b['id']))
                {
                    $boss = new Employee();
                    $boss->setState($b);
                }
                else
                    $boss = null;
                
                return array($employee, $boss);
            }
            return false;
        };
}

Reply via email to