• 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
Route call wrong method

#1
I have this routes:

PHP Code:
$routes->group('admin', function ($routes) {

    
$routes->group('media', [
        
'filter'         => 'permission:manage-media',
        
'namespace'        => 'App\Controllers',
        
'controller'    => 'Media',
        
'except'        => 'show'
    
], function ($routes) {

        
$routes->get('/''Media::index');
        
$routes->delete('(:any)''Media::delete/$1');
        
$routes->post('move''Media::move');

        
$routes->get('(:any)/details''Media::details/$1');
        
$routes->get('filter''Media::filter');

        
$routes->get('directory''Media::directory');
        
$routes->post('directory''Media::directory');
        
$routes->delete('directory/(:any)''Media::directory/$1');
    });
}); 

this is what CI returns:

[Image: YtUQs06.png]

now if I call a delete method for admin/media/1 all works as expected, but when I call admin/media/directory/1

using:

PHP Code:
$.ajax({
    url: `<?= route_to('admin/media/directory') ?>/1`,
    method'DELETE',
}).
done((datatextStatusjqXHR) => {
    Toast.fire({
        icon'success',
        titlejqXHR.statusText,
    });
}).
fail((error) => {
    Toast.fire({
        icon'error',
        titleerror.responseJSON.messages.error,
    });
}) 

this will call the method delete() of the Media controller instead of call the method directory, why?
Reply

#2
It is obvious.
admin/media/directory === admin/media/(:any)
admin/media/directory !== admin/media/directory/(:any)
Reply

#3
(05-03-2021, 12:01 PM)iRedds Wrote: It is obvious.
admin/media/directory === admin/media/(:any)
admin/media/directory !== admin/media/directory/(:any)

So based on your hint, the issue is related to this route:

PHP Code:
$routes->delete('(:any)''Media::delete/$1'); 

what do you suggest to keep directory inside media group routes?
Reply

#4
I found another weird issue, I have this route:

[Image: P9OQOUo.jpg]

if I call it using:

PHP Code:
url: `<?= route_to('admin/media/files') ?>/${$(this).attr('data-id')}/details

in $.ajax, I wil get only "${$(this).attr('data-id')}/details`", so actually route_to return an empty value. But if I do:


PHP Code:
url: `<?= base_url() ?>/admin/media/files/${$(this).attr('data-id')}/details`, 

I get the correct url, why route_to is returning me an empty value?
Reply

#5
Sorry. I’m completely blind.

The problem is that under the route
$routes->delete('(:any)', 'Media::delete/$1');
fits
DELETE admin/media and DELETE admin/media/directory

You need to change the order of the routes.

first
$routes->delete('directory/(:any)', 'Media::directory/$1');
next
$routes->delete('(:any)', 'Media::delete/$1');

You're using
route_to('admin/media/files')
But the route is completely different
admin/media/files/(:any)/details

The route_to function does not find it.
In addition, you have an undefined segment, so route_to will also throw an exception.

With your route, it is more correct to define the route alias.
for example
PHP Code:
$routes->get('admin/media/files/(:any)/details''Controller::method', ['as' => 'files.details']);
// and call 
route_to('files.details'123); // admin/media/files/123/details 

But since your segment is dynamic and the code is executed on the client, you cannot use route_to().
And it is better to form the URL manually.
Reply

#6
using restfull api route like bellow 
and define new filter for controller auth and service to handel route accessablity by user rule


PHP Code:
<?php

/*
 * Myth:Auth routes file.
 */

$routes->group('api', ['namespace' => 'CoreSite\Controllers'], function ($routes) {

    $routes->group('auth', function ($routes) {

        $routes->post('login''Auth::login');
        $routes->get('logout''Auth::logout');
        $routes->post('register''Auth::register');
        $routes->post('forgot''Auth::forgot');
        $routes->post('reset-password-email''Auth::resetPasswordViaEmail');
        $routes->post('reset-password-sms''Auth::resetPasswordViaSms');
        $routes->get('activate-account-email''Auth::activateAccountViaEmail');
        $routes->get('send-activate-email''Auth::sendActivateCodeViaEmail');
        $routes->post('activate-account-sms''Auth::activateAccountViaSms');
        $routes->post('send-activate-sms''Auth::sendActivateCodeViaSms');
        $routes->post('forgot''Auth::forgot');
    });
    $routes->resource('profile');
    $routes->resource('chatContact');
    $routes->resource('chatRoom');
    $routes->resource('chatRoomMedia');
    $routes->resource('chatPrivate');
    $routes->resource('chatPrivateMedia');
    $routes->resource('dashboard');

    $routes->resource('user');
    $routes->resource('group');
    $routes->resource('setting');
    $routes->resource('visitor');
    $routes->resource('contact');
    $routes->resource('contactMedia');
    $routes->resource('newsCategory');
    $routes->resource('newsSubCategory');
    $routes->resource('newsPost');
    $routes->resource('newsComment');
    $routes->resource('newsMedia');
    $routes->resource('viewOption');
    $routes->resource('viewMedia');
    $routes->resource('advertisement');
    $routes->resource('advertisementMedia');


}); 
Reply

#7
(05-04-2021, 10:45 AM)iRedds Wrote: Sorry. I’m completely blind.

The problem is that under the route
$routes->delete('(:any)', 'Media::delete/$1');
fits
DELETE admin/media and DELETE admin/media/directory

You need to change the order of the routes.

first
$routes->delete('directory/(:any)', 'Media::directory/$1');
next
$routes->delete('(:any)', 'Media::delete/$1');

You're using
route_to('admin/media/files')
But the route is completely different
admin/media/files/(:any)/details

The route_to function does not find it.
In addition, you have an undefined segment, so route_to will also throw an exception.

With your route, it is more correct to define the route alias.
for example
PHP Code:
$routes->get('admin/media/files/(:any)/details''Controller::method', ['as' => 'files.details']);
// and call 
route_to('files.details'123); // admin/media/files/123/details 

But since your segment is dynamic and the code is executed on the client, you cannot use route_to().
And it is better to form the URL manually.

Thanks for the answer, I have changed my routes in this configuration now:

PHP Code:
$routes->group('media', [
        
'filter'         => 'permission:manage-media',
        
'namespace'        => 'App\Controllers',
        
'controller'    => 'Media',
        
'except'        => 'show'
    
], function ($routes) {

        
$routes->get('/''Media::index');
        
$routes->get('(:num)''Media::details/$1');
        
$routes->get('filter''Media::filter');
        
$routes->delete('(:num)''Media::delete/$1');
        
$routes->post('move''Media::move');
        
$routes->put('(:any)''Media::update/$1');

        
// meta
        
$routes->get('meta/(:any)''Media::getMeta/$1', ['as' => 'media.meta']);

        
// directory
        
$routes->get('directory''Media::directory');
        
$routes->post('directory''Media::directory');
        
$routes->delete('directory/(:any)''Media::directory/$1');
    }); 

now the only problem that I get is on meta/(:any), so if I do this:

PHP Code:
url: `<?= base_url('admin/media/meta') ?>/${type}`, 

everything works fine, but if I do this:


PHP Code:
url: `<?= route_to('admin/media/meta') ?>/${type}`, 

the function route_to return an empty string
Reply

#8
The thing to keep in mind when using (:any) is that it is a catch all route.
So like @iRedds stated the order of (:any) is very important, this always gets new users.

(:any routes should also be place at the very end of the routes and in order to be safe.
What did you Try? What did you Get? What did you Expect?

Joined CodeIgniter Community 2009.  ( Skype: insitfx )
Reply


Digg   Delicious   Reddit   Facebook   Twitter   StumbleUpon  


  Theme © 2014 iAndrew  
Powered By MyBB, © 2002-2021 MyBB Group.