Anuj TBE
Anuj TBE

Reputation: 9790

CakePHP 3 : display data from other model and pass parameter in url from action

I'm working on a project using CakePHP 3.x.

I have UserAddress, ServiceRequests, Service models.

There is a button on service/view/$id which when clicked will ask user to select address from service-requests/serviceArea which has a list of addresses added by user. service-requests/serviceArea view will contain a select button which when clicked will call add action in ServiceRequests controller with passing two parameters serviceId and userAddressId

This is the serviceArea function created by me.

public function serviceArea($id = null)
    {
        public $uses = array('UserAddress');
        $service = $id;
        $query = $userAddresses->find('all')
          ->where(['UserAddresses.user_id =' => $this->Auth->user('id')]);



        $this->set(compact('userAddresses'));
        $this->set('_serialize', ['userAddresses']);
    }

How to display the address and also pass the $service parameter to the serviceArea view.

I am new to CakePHP, so if you think question is incomplete any edit to it will be appreciated instead of down-voting.

Thank You.


Edit 2

Thank for your answer @jazzcat

After changing my code according to yours and visiting http://domain.com/service-requests/service-area/$id. It is showing error as Record not found in table "service_requests"

and pointing to the ServiceRequestsController on line no 33

The ServiceRequestController as containing line no 33 is

<?php
namespace App\Controller;

use App\Controller\AppController;

/**
 * ServiceRequests Controller
 *
 * @property \App\Model\Table\ServiceRequestsTable $ServiceRequests
 */
class ServiceRequestsController extends AppController
{

    /**
    * isAuthorized method
    *
    */
    public function isAuthorized($user)
    {
      $action = $this->request->params['action'];

      // The add and index actions are always allowed.
      if(in_array($action, ['index', 'add', 'serviceRequests'])) {
        return true;
      }
      // All other actions require an id.
      if (empty($this->request->params['pass'][0])) {
        return false;
      }

      // Check that the service request belongs to the current user.
      $id = $this->request->params['pass'][0];
      $serviceRequest = $this->ServiceRequests->get($id);  // line : 33
      if($serviceRequest->user_id == $user['id']) {
        return true;
      }
      return parent::isAuthorized($user);
    }

        /* Other actions */
}
?>

Upvotes: 0

Views: 1076

Answers (2)

Anuj TBE
Anuj TBE

Reputation: 9790

This worked for me.

Just added the serviceArea action name in the isAuthorized method

if(in_array($action, ['index', 'add', 'serviceArea'])) {
        return true;
}

and it's working fine as expected.

Upvotes: 1

JazzCat
JazzCat

Reputation: 4573

There is alot wrong with your code. Please read the docs

Is the table named user_addresses or user_address ? You seem to mix the both.

The following would be the correct way to do it assuming your table is named user_addresses

public function serviceArea($id = null)
{
        $this->loadModel('UserAddresses');

        $userAddresses = $this->UserAddresses->find('all')
            ->where(['UserAddresses.user_id =' => $this->Auth->user('id')]);

        // If you want to filter on the serviceArea ID aswell
        if($id)
            $userAddresses->andWhere(['id' => $id]);

        // Setting SerivceArea ID to compact makes it available in view.
        $serviceAreaId = $id;

        $this->set(compact('userAddresses', 'serviceAreaId'));
        $this->set('_serialize', ['userAddresses']);
}

This snippet:

$id = $this->request->params['pass'][0];
$serviceRequest = $this->ServiceRequests->get($id);  // line : 33

Just checks if the first parameter passed to the method exists in ServiceRequests.

(That parameter could be anything, you have to keep that in mind when creating all your methods in that controller, that is to say the least.. bad)

I'm assuming that the service_requests table is associated with the users table and an user_id column exists in the service_requests table.

If that is the case this should work:

public function isAuthorized($user)
{
      $action = $this->request->params['action'];

      // The add and index actions are always allowed.
      if(in_array($action, ['index', 'add'])) {
        return true;
      }

      // Is not authorized if an argument is not passed to the method.
      // Don't know why you'd want this , but sure.
      if (empty($this->request->params['pass'][0])) {
        return false;
      }

      // Check that the service request belongs to the current user.
      $user_id = $this->Auth->user('id');
      $serviceRequest = $this->ServiceRequests->find()->where(['ServiceRequests.user_id' => $user_id])->first();
      if(!empty($serviceRequest)) {
        return true;
      }
      return parent::isAuthorized($user);
}

Upvotes: 0

Related Questions