Skip to content
This repository has been archived by the owner on Jan 8, 2020. It is now read-only.

ZF2.4 Breaks 'Count' via \Zend\Db\Sql\Expression on IBM i & DB2 #7400

Closed
kingharrison opened this issue Apr 1, 2015 · 27 comments
Closed

ZF2.4 Breaks 'Count' via \Zend\Db\Sql\Expression on IBM i & DB2 #7400

kingharrison opened this issue Apr 1, 2015 · 27 comments

Comments

@kingharrison
Copy link

When trying to use the paginator adapter an error is returned:

Undefined class constant 'self::TYPE_SELECT'

This originates from Zend/Paginator/Adapter/DbSelect.php line 149 which is:

$countSelect->columns(array(self::ROW_COUNT_COLUMN_NAME => new Expression('COUNT(1)')));

@samsonasik
Copy link
Contributor

I and @kingharrison tried in ZF 2.3 and worked, but not work in 2.4

@samsonasik
Copy link
Contributor

/cc @ralphschindler @turrsis

@Martin-P
Copy link
Contributor

Martin-P commented Apr 1, 2015

Undefined class constant 'self::TYPE_SELECT'

This originates from Zend/Paginator/Adapter/DbSelect.php line 149 which is:

Can you post the complete error message including class/file/line, because there is no self::TYPE_SELECT in the file you mention. For easier reference the exact link to Zend\Paginator\Adapter\DbSelect line 149.

@kingharrison
Copy link
Author

Excuse my newb-ness, but I assume this is what you mean:

16 Zend\Paginator\Adapter\DbSelect::getSelectCount() /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Adapter/DbSelect.php:149
15 Zend\Paginator\Adapter\DbSelect::count() /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Adapter/DbSelect.php:120
14 Zend\Paginator\Paginator::_calculatePageCount() /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Paginator.php:874
13 Zend\Paginator\Paginator::setItemCountPerPage([...]) /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Paginator.php:557
12 Suppliers\Controller\SupplierMaintenanceController::indexAction() /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/module/Suppliers/src/Suppliers/Controller/SupplierMaintenanceController.php:124
11 Zend\Mvc\Controller\AbstractActionController::onDispatch([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
10 Zend\Mvc\Controller\AbstractActionController::call_user_func([...])
9 Zend\EventManager\EventManager::triggerListeners([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
8 Zend\EventManager\EventManager::trigger([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
7 Zend\Mvc\Controller\AbstractController::dispatch([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
6 Zend\Mvc\DispatchListener::onDispatch([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
5 Zend\Mvc\DispatchListener::call_user_func([...])
4 Zend\EventManager\EventManager::triggerListeners([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
3 Zend\EventManager\EventManager::trigger([...]) /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
2 Zend\Mvc\Application::run() /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/data/cache/classes.php.cache:2
1 {main} /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/public/index.php:20

@turrsis
Copy link
Contributor

turrsis commented Apr 2, 2015

@kingharrison can you give code from Suppliers\Controller\SupplierMaintenanceController::indexAction() (where paginator is called) ?

@Martin-P
Copy link
Contributor

Martin-P commented Apr 2, 2015

The stack trace is helpful, but the message Undefined class constant 'self::TYPE_SELECT' also says: in [file] on line [line]. Without that info it is not clear which file contains the error 😉

@kingharrison
Copy link
Author

Here is where I call paginator in Suppliers\Controller\SupplierMaintenanceController::indexAction()

   $paginator = $this->getSUPLIERTable()->fetchAllSuppliers($data, true);
    $page = $this->params()->fromQuery('page');
    $paginator->setCurrentPageNumber($page);
    $paginator->setItemCountPerPage($itemsPerPage);
    $paginator->setPageRange($pageRange);

   return new ViewModel(array(
        'paginator' => $paginator,
    ));

Here is fetchAllSuppliers from my TableGateway:
// create a new Select object for the table album
$select = new Select ('K_SUPLIER');
// create a new result set based on the Album entity
$resultSetPrototype = new ResultSet ();
$resultSetPrototype->setArrayObjectPrototype(new SUPLIER ());
// create a new pagination adapter object
$paginatorAdapter = new DbSelect (
// our configured select object
$select->where($data),
// the adapter to run it against
$this->tableGateway->getAdapter(),
// the result set to hydrate
$resultSetPrototype);
$paginator = new Paginator ($paginatorAdapter);
return $paginator;

This does work when I turn the system version back to 2.3.7

@kingharrison
Copy link
Author

@Martin-P I think this is what you needed:
PHP Error [select all]
Undefined class constant 'self::TYPE_SELECT'
Function information [select all]
Zend\Paginator\Adapter\DbSelect::getSelectCount()

This line, 149, seems to be the issue.
Zend\Db\Sql\Select::getSelectCount() at /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Adapter/DbSelect.php: 149

@kingharrison
Copy link
Author

For possible reference things work a bit different in DB2. There are no LIMIT or OFFSET commands, so to get paginator working originally they had to adjust some code. Here is my original reported issue on pagination and DB2 which did get fixed:

#6165

@Maks3w
Copy link
Member

Maks3w commented Apr 2, 2015

@kingharrison Please download again ZF 2.4.0. Seems you have a modified version of DbSelect.php

@Martin-P
Copy link
Contributor

Martin-P commented Apr 2, 2015

No, sorry, that is not the info. The error message you will see, is this (where [filename] and [line number] contain the crucial info):

Fatal error: Undefined class constant 'self::TYPE_SELECT' in [filename] on line [line number]

The message you post looks like some 3rd party plugin which messes up the actual error message. Please deativate it and post the real message. You could also look for it in the PHP error log.

@turrsis
Copy link
Contributor

turrsis commented Apr 2, 2015

@Martin-P "3rd party plugin" in the log - this is only controller. Or not?

@kingharrison
Copy link
Author

I am using ZRay to help debug it. This is from my php log access through Zend Server. Here is my trying to run it a couple times in a row.

[01-Apr-2015 20:35:32 America/Phoenix] PHP Fatal error: Undefined class constant 'self::TYPE_SELECT' in /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Adapter/DbSelect.php on line 149
[01-Apr-2015 21:01:51 America/Phoenix] PHP Fatal error: Undefined class constant 'self::TYPE_SELECT' in /usr/local/zendsvr6/var/libraries/Zend_Framework_2/2.4.0/library/Zend/Paginator/Adapter/DbSelect.php on line 149

@kingharrison
Copy link
Author

@Maks3w I used the updater in Zend Server. Besides redeploying how do I download a standard version? Is there a place I can download the ZPK and deploy it that way? IBM i boxes are locked down pretty tight so I would need to deploy through Zend Server.

@kingharrison
Copy link
Author

I think it has to do with the count function. I found another page throwing the error that was not pagination. This line of code:
'COUNT' => new \Zend\Db\Sql\Expression ( 'COUNT(SO_SOQTYPE)' )

In something I called AgendaTable was producing this error:
[01-Apr-2015 20:35:14 America/Phoenix] PHP Fatal error: Undefined class constant 'self::TYPE_SELECT' in /usr/local/zendsvr6/var/apps/http/10.6.49.11/7272/docroot/module/K3sbase/src/K3sbase/Table/AgendaTable.php on line 20

That line was on line 20. Count seems to be broken on DB2?

@Martin-P
Copy link
Contributor

Martin-P commented Apr 2, 2015

This shows the error is not in ZF2, but in K3sbase\Table\AgendaTable on line 20. What is the code of line 15 to 20 in K3sbase\Table\AgendaTable? It looks like you use self::TYPE_SELECT directly in that file which causes the error.

@kingharrison
Copy link
Author

Here is the entire file (again this all works without error in ZF 2.3.7):

<?php
namespace K3sbase\Table;
use Zend\Db\TableGateway\TableGateway;
use Zend\Db\Sql\Select;

class AgendaTable {
    protected $tableGateway;
    public function __construct(TableGateway $tableGateway) {
        $this->tableGateway = $tableGateway;
    }

    public function agendaTotalCount($data) {
        $rowset = $this->tableGateway->select ( function (Select $select) use($data) {
            $select->where ( $data )->columns ( array (
                    'COUNT' => new \Zend\Db\Sql\Expression ( 'COUNT(SO_SOQTYPE)' ) //This is line 20 throwing the error. 
            ) );
            $select->where->nest->equalTo ( 'SO_SOQTYPE', 'ND' )->or->equalTo ( 'SO_SOQTYPE', 'FB' )->or->equalTo ( 'SO_SOQTYPE', 'FR' )->or->equalTo ( 'SO_SOQTYPE', 'RE' )->or->equalTo ( 'SO_SOQTYPE', 'FC' )->or->equalTo ( 'SO_SOQTYPE', 'SO' )->unnest->and->where->notEqualTo ( 'SO_USERA1', '0' );
        } );
        $entities = array ();
        foreach ( $rowset as $row ) {
            $entity = array (
                    "count" => $row->COUNT 
            );
            $entities [] = $entity;
        }
        return $entities;
    }
}

@kingharrison
Copy link
Author

As pagination uses Count as well this would make sense that pagination breaks. Should I change the title of this issue? It seems to be Count on the IBM i that breaks.

@kingharrison kingharrison changed the title ZF2.4 Breaks Pagination on IBM i & DB2 ZF2.4 Breaks 'Count' via \Zend\Db\Sql\Expression on IBM i & DB2 Apr 2, 2015
@Martin-P
Copy link
Contributor

Martin-P commented Apr 2, 2015

The strange thing here is you get an error about Zend\Paginator\Adapter\DbSelect and K3sbase\Table\AgendaTable but both classes do not even contain the code self::TYPE_SELECT. Also Zend\Db\Sql\Expression and the class it extends (Zend\Db\Sql\AbstractExpression) do not use it (AbstractExpression only defines it).

'COUNT' => new \Zend\Db\Sql\Expression ( 'COUNT(SO_SOQTYPE)' )

What if you use COUNT(1) as is also used in Zend\Paginator\Adapter\DbSelect? What if you let Zend\Paginator\Adapter\DbSelect do the counting for you? It accepts a Select as parameter and does the counting part for you.

@kingharrison
Copy link
Author

If I change it to COUNT(1) as in Zend\Paginator\Adapter\DbSelect it still produces the same error.

@ralphschindler
Copy link
Member

To make sure of something, can you turn down or off the optimization level for zend optimizer and try to load that page again after a restart?

@kingharrison
Copy link
Author

@ralphschindler I turned of Zend OpCache completely and tried and got the same error.

@weierophinney
Copy link
Member

I've just grepped through ZF 2.4.0. The constant TYPE_SELECT is used in exactly two places:

  • Zend\Db\Sql\ExpressionInterface, which defines the constant, and
  • Zend\Db\Sql\AbstractExpression, which uses the value when defining its $allowedTypes array.

Line 149 of Zend\Paginator\Adapter\DbSelect is creating a "meta" column to select for the count:

$countSelect->columns(array(self::ROW_COUNT_COLUMN_NAME => new Expression('COUNT(1)')));

This operation (columns()) simply sets two properties on the $countSelect instance.

In other words, stepping through the code invoked, I am at a loss as to how that would even reference the given constant, much less fail a lookup on it.

My gut tells me there's a code caching issue somehow, and that you're getting old code and/or a mix of old and new code which conflict. You indicated that you're using the Zend Server library support; IIRC, we have some functionality in the bootstrap to ensure you get the latest version from that, but perhaps you could send that code? I would need to see the files init_autoloader.php and public/index.php.

@kingharrison
Copy link
Author

I assume this is where you want me to post @weierophinney

init_autoloader.php
// Composer autoloading
if (file_exists('vendor/autoload.php')) {
$loader = include 'vendor/autoload.php';
}

$zf2Path = false;

if (is_dir('vendor/ZF2/library')) {
$zf2Path = 'vendor/ZF2/library';
} elseif (getenv('ZF2_PATH')) { // Support for ZF2_PATH environment variable or git submodule
$zf2Path = getenv('ZF2_PATH');
} elseif (get_cfg_var('zf2_path')) { // Support for zf2_path directive value
$zf2Path = get_cfg_var('zf2_path');
}

if ($zf2Path) {
if (isset($loader)) {
$loader->add('Zend', $zf2Path);
} else {
include $zf2Path . '/Zend/Loader/AutoloaderFactory.php';
Zend\Loader\AutoloaderFactory::factory(array(
'Zend\Loader\StandardAutoloader' => array(
'autoregister_zf' => true
)
));
}
}

if (!class_exists('Zend\Loader\AutoloaderFactory')) {
throw new RuntimeException('Unable to load ZF2. Run php composer.phar install or define a ZF2_PATH environment variable.');
}

public/index.php

chdir(dirname(DIR));

// This was added for the EdpSuperluminal module. This creates ultra fastness feelings inside.
define('ZF_CLASS_CACHE', 'data/cache/classes.php.cache'); if (file_exists(ZF_CLASS_CACHE)) require_once ZF_CLASS_CACHE;

// Decline static file requests back to the PHP built-in webserver
if (php_sapi_name() === 'cli-server' && is_file(DIR . parse_url($_SERVER['REQUEST_URI'], PHP_URL_PATH))) {
return false;
}

// Setup autoloading
require 'init_autoloader.php';

// Run the application!
Zend\Mvc\Application::init(require 'config/application.config.php')->run();

@samsonasik
Copy link
Contributor

@kingharrison I though it because of the EdpSuperLuminal, could you turn off the EdpSuperluminal ( commented the ) :

define('ZF_CLASS_CACHE', 'data/cache/classes.php.cache'); if (file_exists(ZF_CLASS_CACHE)) require_once ZF_CLASS_CACHE;

?

@kingharrison
Copy link
Author

@weierophinney @samsonasik
That was it. Fixed.

@samsonasik
Copy link
Contributor

@kingharrison awesome ;), please close it then ;). sorry for can't solve it yesterday and direct you here ;)

Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
None yet
Projects
None yet
Development

No branches or pull requests

7 participants