We are moving our forum in GitHub Discussions. For questions about Phalcon v3/v4 you can visit here and for Phalcon v5 here.

Namespace in query builder is not working with Phalcon 2.0 (but it works well with 1.3.4)

Dear experts,

This is my code snippet that works in Phalcon 1.3.4:

$marketings = $this->modelsManager->createBuilder()
    ->columns('Som\Models\Employee.id, Som\Models\Person.name')
    ->from('Som\Models\Employee')
    ->join('Som\Models\Person')
    ->where('Som\Models\Employee.store_id = :store_id: AND Som\Models\Employee.rank = :rank: AND Som\Models\Employee.disable = 0', array('store_id' => $this->auth->getStoreId(), 'rank' => $this->flag->value->rank_marketing))
    ->orderBy('Som\Models\Person.name')
    ->getQuery()
    ->execute();

But in Phalcon 2.0, it didn't work :(. Have I did something wrong?

Are you getting an error or something?

Nothing. Just return empty result (it should be return non empty result).

I tried to reproduce your issue with the following code:

<?php

namespace Some;

use Phalcon\DI,
    Phalcon\Db\Column,
    Phalcon\Mvc\Model,
    Phalcon\Events\Manager as EventsManager,
    Phalcon\Db\Adapter\Pdo\Mysql as Connection,
    Phalcon\Mvc\Model\Manager as ModelsManager,
    Phalcon\Mvc\Model\Metadata\Memory as ModelsMetaData;

$eventsManager = new EventsManager();

$di = new DI();

$connection = new Connection(array(
    "host"     => "localhost",
    "username" => "root",
    "password" => "",
    "dbname"   => "phalcon_test"
));

$connection->setEventsManager($eventsManager);

$eventsManager->attach('db',
    function ($event, $connection) {
        switch ($event->getType()) {
            case 'beforeQuery':
                echo $connection->getSqlStatement(), "\n";
                break;
        }
    }
);

$modelsManager = new ModelsManager();
$modelsManager->setDi($di);
$di['db'] = $connection;
$di['modelsManager'] = $modelsManager;
$di['modelsMetadata'] = new ModelsMetadata();

class Robots extends Model
{
}

class RobotsParts extends Model
{
}

$rows = $modelsManager->createBuilder()
    ->columns('Some\RobotsParts.id, Some\Robots.name')
    ->from('Some\RobotsParts')
    ->join('Some\Robots')
    ->where('Some\RobotsParts.robots_id = :robots_id: AND Some\Robots.type = :type:',
        array('robots_id' => 1, 'type' => 'mechanical')
    )
    ->orderBy('Some\Robots.name')
    ->getQuery()
    ->execute();

foreach ($rows as $row) {
    echo $row->id, PHP_EOL;
    echo $row->name, PHP_EOL;
}

And it shows:

$ php c.php 
SELECT `robots_parts`.`id` AS `id`, `robots`.`name` AS `name` FROM `robots_parts` INNER JOIN `robots` WHERE `robots_parts`.`robots_id` = :robots_id AND `robots`.`type` = :type ORDER BY `robots`.`name`
3
Astro Boy
2
Astro Boy
1
Astro Boy
3
Robotina
2
Robotina
1
Robotina
edited Apr '15

Could it because namespace statement at the top php file?

My namespace:

namespace Some\Controllers;

@phalcon, Can you try assign the different namespace?

namespace Some\Controllers;

then the query:

$rows = $modelsManager->createBuilder()
    ->columns('Some\Models\RobotsParts.id, Some\Robots.name')
    ->from('Some\Models\RobotsParts')
    ->join('Some\Models\Robots')
    ->where('Some\Models\RobotsParts.robots_id = :robots_id: AND Some\Models\Robots.type = :type:',
        array('robots_id' => 1, 'type' => 'mechanical')
    )
    ->orderBy('Some\Models\Robots.name')
    ->getQuery()
    ->execute();

I subscribe to this discussion, because I also did not work namespace!

class in the source code (cphalcon/phalcon/mvc/model/manager.zep) I did not find the code responsible for converting a namespace and use an object model class in the query

I found a problem. She was describing the namespace name in my classes. it is necessary that a namespace inside a class and registered the namespace in the container services begin with a capital letter

Example:

String in my class:

namespace MyNameSpace\Models;

class SomeClass .....

and $loader->registerNamespaces(array( 'MyNameSpace\Models' => '/models/' ))