Routing with codeigniter - ID not passed - php

I've recently picked up Codeigniter as a fun little side project, now I'm trying to make my routes to be as follows;
http://localhost/c/show/ID
should translate into
http://localhost/c/ID
I do it in routes in config like so;
$route['c/:any'] = "c/show/$1";
However, the ID is simply passed as plaintext, which means the ID passed to my show() function is $1, and not whatever ID is set to.
Am I going about this wrong? I've simply looked around in their documentation and even tried copy&replace to make sure it's not something that I typed wrong.
Now I fear I might have missunderstood something but I cannot phatom what that could be.
Really grateful for any and all help!

":any" should be in brackets, like this:
$route['c/(:any)'] = "c/show/$1";
Btw if ID is numeric, it's better to use:
$route['c/(:num)'] = "c/show/$1";

Related

Codeigniter complex wildcard Routing

Hi guys I am trying to achieve something that I hope is possible but couldn't find the right way to find.
I am using codeigniter 2.2.0
I want to use an url in codeigniter like
domain/username/controller/method/$args
Let me explain When user types an url like
domain/mike/job/editJob/12/urgent/
Here "mike" is someone's user name
"job" will be a controller alias
"editJob" will be a method
"12" and "urgent" will be parameter of editJob method.
editJob method will have three parameters.
I want "mike" as 1st parameter,
then "12" and "urgent" as second and third parameter.
So far what I have done in my routes
$route['(:any)/job/(:any)'] = 'job_c/$2/$1';
When I type in the url
domain/mike/job/editJob/12/urgent
in Job controller I get
"12" as first parameter
"urgent" as second parameter
and "mike" as third parameter
**
Is there any possible way to get "mike" as first parameter and then the rest is okay**
Edited:
One more thing if I pass three parameters after method then I am not
getting the username!!
I need to have the username as first parameter because there may have multiple parameters in any method and there is a possibility to have conditional parameters as well.
One more thing I want to know. Is it possible to make such route that will work the same as my given route but the controller alias will also be wildcard. Or if there is any way to check if a segment in url is a controller then one route and if not a controller then something else should happen.
I am not a well describer still tried to keep it simple. If anyone knows something that will help me a lot.
Thanks
UPDATE
Is there any way to keep the username "mike" in session from routes.php file thus I don't have to pass this as a parameter.
Updating Again
I have solved the issue somehow.
I am using
$route['(:any)/garage/([^/]*)/([^/]*)/(.*)'] = '$2/$3/$1/$4';
Here garage is nothing but a simple identifier for the route. This route will work when it gets garage as a second segment in url. It will work like
domain/user/garage/anyControler/anyMethod/manyParameters
It's completely dynamic only the garage is used as identifier. If you want you can use your controller name instead of using any identifier. then you don't have to declare same thing multiple times for multiple controllers but it will work fine. It will work for any controller and any method. In addition it supports dynamic number of parameters.
I don't know if there is any better way to do this but it solves my issue. If anyone know something better then this then please share.
I think what is happening is that you are accessing
domain/mike/job/editJob/12/urgent
and its being parsed like:
job_c/editJob/12/urgent/mike
Because:
$route['(:any)/job/(:any)'] = 'job_c/$2/$1';
$2 = (:any)/job/(:any) = editJob/12/urgent
$1 = (:any)/job/(:any) = mike
Substituting:
job_c/editJob/12/urgent/mike
You could try to keep your route as similar as your current one:
$route['(:any)/job/(:any)/(:any)'] = 'job_c/$2/$1/$3';
This will allow you to match $2 to any method name, and have $1 as the first parameter and $3 as the rest of params.
But, I would suggest, if this is a very specific route, substituting the $2 :any, with the actual method name and the expected type of the params, otherwise, you might receive unexpected values to every method in the matching controller.
I would use something like:
$route['(:any)/job/editJob/(:num)/(:any)'] = 'job_c/editJob/$1/$2/$3';
Hope this helps.
Update:
For the controller matching: Code Igniter uses the form controller/method/param1/param2/...
As long as you create routes that matches controllers, methods and params in that order, you can do anything.
$route['(:any)/(:any)/(:any)'] = '$1/$2/$3';
or just
$route['(:any)'] = '$1';
and hopefully it will contain a controller and method and the required params.
I think this will totally be missing the point of having a routing system.

Access URL param from Input::get() with laravel

I have a route like this:
Route::get('demo/{system?}', 'MonitorController#demo');
I am using it like so because I would like my url to look like so:
mysite.com/demo/spain-system
Where spain-system will be the variable I need to get.
Right now, I'm getting it like this:
public function demo($systemName = null){
}
But I would like to be able to access to it as if it were a URL parameter with Input::get('system') so I can access to it from other methods or even from other controllers such as BaseController.php.
Is there any way to achieve this?
I've played around with Route::input('system') but then it doesn't work when I pass it as a get parameter (in other Ajax calls and so on)
Update
In PHP we can get URL params by using the $_GET function and laravel provides the function Input::get() to do so as well.
If there were no routes in laravel, I would make use of .htaccess rewrite rules to change this:
mysite.com/demo/?system=spain-system
To this:
mysite.com/demo/spain-system
And I could still retrieve the variable system as a GET parameter by using $_GET["system"].
That's kind of what I would expect of laravel, but it seems it is just treating it as the parameter of the demo method and not really as a URL variable.
Is there any way to keep treating it as a URL variable and at the same time use it in a pretty URL without the ?system= ?
So you actually just want to get an url like this? mysite.com/demo/spain-system instead of mysite.com/demo/?system=spain-system? Laravel provides that by default?
Look, When you want to get the router variable {system?} to be accesible you'll need to do this:
In your router:
Route::get('demo/{system}', 'MonitorController#demo');
Then you have an controller where this noods to stand in:
public function demo($system)
{
//your further system
//You are be able to access the $system variable
echo $system; //just to show the idea of it.
}
When you now go to to localhost/demo/a-system-name/, You'll see a blank page with a-system-name.
Hope this helps, because your question is abit unclear.

Custom route not working | Codeigniter Routing

I am working on an API via which I embed images of country flags on my website & several others.
I am taking in 3 parameters i.e
Country (Name of Country - ISO Code or Full Name)
Size (Dimension of Image)
Type (Styles like flat flag, shiny round flag etc...)
Now, have everything setup correctly but stuck in handling URI.
Controller -> flags.php
Function -> index()
What I have now is :
http://imageserver.com/flags?country=india&size=64&style=round
What I want
http://imageserver.com/flag/india/64/round
I went through some articles and made this route but all of them failed
$route['flag/(:any)/(:num)/(:any)'] = "welcome/index/country/$1/size/$2/style/$3";
$route['flag/(:any)/(:num)/(:any)'] = "welcome/index/$1/$2/$3";
$route['flag/(:any)/(:num)/(:any)'] = "welcome/index?country=$1&size=$2&style=$3";
I have also been having trouble with routes while writing my custom cms. Reading through your question, I see a couple issues that might very well be the answer you are looking for.
For starters, let's look at the routes you have tried:
$route['flag/(:any)/(:num)/(:any)'] = "welcome/index/country/$1/size/$2/style/$3";
$route['flag/(:any)/(:num)/(:any)'] = "welcome/index/$1/$2/$3";
$route['flag/(:any)/(:num)/(:any)'] = "welcome/index?country=$1&size=$2&style=$3";
If you want to run the index method from your flags class, which it looks like you do, you don't want to route to the welcome class at all. Currently, however, you are. Your routes should look like:
$route['flag/(:any)/(:num)/(:any)'] = "flags/index";
That way, Codeigniter will run the index method from your flags class. You don't have to worry about the country, size, or style/type in the route. The best option there would be to use the URI segment function like this:
$country = $this->uri->segment(2); //this would return India as per your uri example.
$size = $this->uri->segment(3); //this would return 64 as per your uri example.
$style = $this->uri->segment(4); //this would return round as per your uri example.
You could then use those variables to query your database and get the correct flag or whatever else you need to do with them.
So to restate my answer with a little more explanation as to why:
The routes you have currently are running the welcome controller/class and the index function/method of that controller/class. This, obviously, is not what you want. So you need to make sure your routes are pointing to the correct controller and function like I did above. The extra segments of the URI don't need to be in your route declaration, so you would then just use the uri_segment() function to get the value of each segment and do what you need with them.
I hope this helps you. I may not have found an answer for my problem, but at least I could provide an answer for someone else. If this seems confusing to you, check out the user guide at http://ellislab.com/codeigniter/user-guide. The main links you need for this are:
http://ellislab.com/codeigniter/user-guide/libraries/uri.html
and
http://ellislab.com/codeigniter/user-guide/general/routing.html
Let me know if you need more help or if this helped solve your problem.

CodeIgniter route overridden by controller/method

I have in my routes.php:
$route['ctrller1/method1/video/(:num)'] = 'ctrller2/method2/$1';
I also have a controller that is named ctrller1 that has a method:
function method1 ($str = NULL) {
// do something
}
The problem is I have to use controller2 coz I can't or shouldn't edit controller1. What I want is seemingly simple but, apparently, CI doesn't want to work with me.
When the url:
domain.com/ctrller1/method1/edit
is invoked, I want the method inside ctrller1 to be called, if domain.com/ctrller1/method1/videos/1
is invoked I want the method in ctrller2 called.
It all seems correct to me but it won't work. So, I must be missing something. I've tried adding this to the routing:
$route['ctrller1/method1/(edit)'] = 'ctrller1/method1/($1)';
But it's a no go. Anyone see anything wrong here?
At any time when you work with routes, just like permissions (firewall, etc;) order is important. Typically you want to organize your routes in this order:
MOST DEFINED
LESS DEFINED
GENERAL / FALLBACK
To clarify, that means your order for routes should be like this:
$route['ctrller1/method1/videos/view/(:num)'] = 'ctrller2/method3/$1';
$route['ctrller1/method1/videos/(:num)'] = 'ctrller2/method2/$1';
$route['ctrller1/(:num)'] = 'ctrller2/method1/$1';
When the URL is called, the route table goes through and finds the FIRST closest match, ELSE it traverses to the next route.
In this case what you want is something like this:
domain.com/ctrller1/method1/videos/1
domain.com/ctrller1/method1/edit
Reasoning for that is, the video's route is more specific, and also is a SPECIAL CASE, as you route it to another controller behind the scenes.
Here is what your routes should look like then (not tested, but should be it):
$route['ctrller1/method1/videos/(:num)'] = 'ctrller2/method2/$1';
$route['ctrller1/method1/edit'] = 'ctrller1/method1';
As a side, note, I am curious why you format it ctrller1/method1/videos/ and not something like ctrller1/videos/view/12355 or ctrller1/videos/edit/12355, the method1 seems confusing. But again I don't have all the details here.
Hope that works for you, if not comment, and I will revisit your question if you clarify it a little more.
Well you have video on one place and videos on another?
Either change to
$route['ctrller1/method1/videos/(:num)'] = 'ctrller2/method2/$1';
or try url: domain.com/ctrller1/method1/video/1

simple cakephp problem

I know this is a really simple thing that I really should know but I'm trying to learn cakephp without having done much php before. I've been told thats a stupid idea, but I'm doing it for fun and so I'm doing it.
I want to pass an array from one controller action to another controllers action and then pass it to the view. I have:
sponges_controller.php
$info = $this->data;
$this->redirect(array('controller'=>'baths', 'action'=>'dashboard', $info));
baths_controller.php
function dashboard($info) {
$this->set('info', $info);
}
and then
<?php echo debug($info); ?>
in the view for dashboard.
I've tried various ways but can't make it work. All it does is print out Array()
Plz help me! :) Julia
You can't pass data that way from one controller to the other as far as I know, at most you can concat a string to the action, like an ID for view or editing.
If you want to pass the info you could try setting it in the SESSION variable in the following way:
$this->Session->write('Info', $info);
And in your other controller you can check for it:
$this->Session->read('Info');
It looks like cake will not let you pass an array into a controller action. I set up a simple example and I got an 'array to string conversion error'. Is there a specific reason why you aren't just posting the data to baths/dashboard? I can think of a workaround for your problem, but it is quite messy.
8vius's solution above will definitely work.
Here is another way, but using sessions is probably a lot better
$str = http_build_query($info);
$this->redirect('/baths/dashboard?'.$str);
So then in your baths/dashboard action, you will have access to your data using the php $_GET array.
So if you originally had this->data['name'] you can access it with $_GET['name']
I'm not sure about the passing data in different controllers but within the same controller we can do it just like a function call by writing something like this.
$this->function_name($info);
This will perfectly work as intended. I've not tried this type of data passing in different controllers function.

Categories