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

Need some help with rest-api

https://github.com/phalcon/rest-api

How to deal with Pagination and Searching in this project? Could you please give some examples?

I want to modify the line 137 to below code: https://github.com/phalcon/rest-api/blob/8328c2b6b94284e057bfe571113ae12340e2cd5a/library/Traits/QueryTrait.php#L137

    /**
     * Runs the builder query if there is no cached data
     *
     * @param Config       $config
     * @param Client       $cache
     * @param Builder      $builder
     * @param array        $where
     *
     * @return ResultsetInterface
     */
    private function getResults(
        Config $config,
        Client $cache,
        Builder $builder,
        array $where = []
    ): ResultsetInterface {
        /**
         * Calculate the cache key
         */
        $phql     = $builder->getPhql();
        $params   = json_encode($where);
        $cacheKey = sha1(sprintf('%s-%s.cache', $phql, $params));
        if (true !== $config->path('app.devMode') && true === $cache->exists($cacheKey)) {
            /** @var ResultsetInterface $data */
            $data = $cache->get($cacheKey);
        } else {
            // use Phalcon\Paginator\Adapter\QueryBuilder;
            $paginator = new QueryBuilder(['builder' => $builder, 'limit' => 5, 'page' => 1]);
            $data      = $paginator->paginate();                        
            //$data = $builder->getQuery()->execute();          <==========================  Originally, Line 137
            $cache->mset($cacheKey, $data);
        }

        return $data;
    }

It got error:

BaseController::getRecords() must implement interface Phalcon\Mvc\Model\ResultsetInterface, instance of Phalcon\Paginator\Repository returned


8.4k
edited Dec '20

you need to create the pagination after getting the results from getResults()

and in this case ( using cache ) you may want to convert the results to an array and use Phalcon\Paginator\Adapter\NativeArray instead

the return type of getResults() (as shown in declaration) must be an instance of ResultsetInterface

edited Dec '20

Well, the error kind of tells you what the problem is. The function definition is saying the method must return ResultsetInterface, but you're returning an instance of Phalcon\Paginator\Repository, which is what $paginator->paginate() returns.

You could change the method definition, but there'll probably be upstream problems with code expecting ResultsetInterface. My recommendation would be to not use the paginator, and just build the paging functionality into your query. getResults() is receiving a Phalcon\Mvc\Model\Query\Builder as a parameter, so you could just keep the original code, but add a limit() call:

} else {
    $builder->limit(5,0);
    $data = $builder->getQuery()->execute();
    $cache->mset($cacheKey, $data);
}

Your code isn't keeping track of the limit or the offset anywhere, but I imagine you're just wanting to get any paging working first before you take care of that.



31.1k

Thanks!

The rest-api project is a well formed sample project of Phalcon api maintained by @niden @Jeckerson @sergeyklay and somebody else, but I've no idea how to paginate.

The example of Fractal after returning data:

use League\Fractal\Resource\Collection;
use League\Fractal\Pagination\PhalconFrameworkPaginatorAdapter;
use Phalcon\Mvc\Model\Query\Builder;
use Phalcon\Paginator\Adapter\QueryBuilder;
use Acme\Model\Book;
use Acme\Transformer\BookTransformer;

$builder = new Builder();
$builder->addFrom(Book::class);

$params = [
    'builder' => $builder,
    'limit'   => 10,
    'page'    => 2,
];

$paginator = new QueryBuilder($params);
$books     = $paginator->getPaginate();

/** $books->items has the data */
$resource = new Collection($books->items, new BookTransformer());
$resource->setPaginator(new PhalconFrameworkPaginatorAdapter($books));