3

I'm using CakePHP 3.x, my application has add/edit pages, in edit action I'm using this code.

 $patient = $this->Patients->get($patientId);

to get record of patient.

Now I want to modify value of some field after find operation, let say I want to convert dob field (date_of_birth) into different date format, in CakePHP 2.x it's possible in afterFind callback but in CakePHP 3.x here in last paragraph it state that,

If you need to modify the results after they have been fetched you should use a Modifying Results with Map/Reduce function to modify the results. The map reduce features replace the ‘afterFind’ callback found in previous versions of CakePHP.

I had also use MapReduce but it won't work for me.

Oops D'oh
  • 941
  • 1
  • 15
  • 34
Dr Magneto
  • 981
  • 1
  • 8
  • 18
  • "_doesn't work_" is not a proper problem description. Please be more specific as to what _exactly_ the problem is with your attempts. – ndm Feb 12 '16 at 12:00

1 Answers1

3

Map/reduce is kind of an overkill for such a simple task, I'd suggest to use a result formatter instead, ie Query::formatResults().

In order to use any of this, ie a mapper/reducer or a formatter, you must use Table::find() instead of Table::get(), as the latter doesn't return a query, but the result, and the options do not support mappers/reducers or formatters.

However, depending on where you need the formatted value, a helper, a virtual field, or just formatting when necessary might be the better option.

Anyways, here's a basic example:

$patient = $this->Patients
    ->find();
    ->where([
        'id' => $patientId
    ])
    ->formatResults(function($results) {
        /* @var $results \Cake\Datasource\ResultSetInterface|\Cake\Collection\CollectionInterface */
        return $results->map(function($row) {
            // note that now `dob` is a string!
            $row['dob'] = $row['dob']->i18nFormat('dd. MMMM yyyy');
            return $row;
        });
    })
    ->firstOrFail();

See also

ndm
  • 59,784
  • 9
  • 71
  • 110