PHP/Laravel, url with multiples arguments - php

I'm building a Laravel app, and I need to use an URL that looks like that :
/api/ads?page=Actuel&formatsQuery[]=side&formatsQuery[]=leaderboard&deviceQuery=mobile
I have 3 parameters (page, formatsQuery (as an array), and deviceQuery).
Do you now how to hold his in routing and controller in order to have the correct value inside the controller's fonction?
I tried this :
routes/api.php
//request to get ads for given parameters
Route::get('/ads', [MediaController::class, 'findAds']);
and this (MediaController.php) :
public function findAds($page, $formatsQuery, $deviceQuery) {
echo $page;
if(sizeof($formatsQuery) <= 0 || sizeof($formatsQuery) > 3){
return $this->unvalidParametersError();
}
//transform format to position depending on deviceQuery
$position = [];
$res = [];
foreach ($formatsQuery as $format) {
$res = Media::where('position', $format)->inRandomOrder()->first()->union($res);
}
echo $res;
return $res;
}
then I test it with this :
public function test_findAds()
{
$ads = Ad::factory()
->has(Media::factory()->count(3), 'medias')
->count(3)->create();
$response = $this->get('/api/ads?page=Actuel&formatsQuery[]=side&formatsQuery[]=leaderboard&deviceQuery=mobile');
$response->assertStatus(200);
}

You are using a GET request to fetch your data. GET request is a type of request that you send parameters in URL using ? after URL and separating parameters with &. You can find out more about HTTP methods here.
In laravel using request parameters is so simple. First of all you need to add Request $request to your method prototype like this:
use Illuminate\Http\Request;
public function findAds(Request $request)
Then you can simply use $request->parameter to get the values. So you need to change your code like this:
public function findAds(Request $request){
$page = $request->page;
$formatsQuery = $request->formatsQuery;
$deviceQuery = $request->deviceQuery;
// Your code
}
And as #matiaslauriti mentioned in the comments you don't need to put [] after formatsQuery[] to send an array in GET request. Using the same key more than one time automatically makes an array for you.

Related

DB::select procedure return empty array from input request

I created this function in my controller:
public function productInvoiceListTest(Request $request){
$var = $request->client_id;
$date = "2019-12-30";
$sql = 'CALL proc_invoice_product_list("'.$var.'","i.invoice_date","2019-12-30","","")';
$productinvoice = DB::select($sql);
var_dump($productinvoice);
}
When i run the code its return empty array, but when i hardcode value of $var it works:
public function productInvoiceListTest(Request $request){
$var = 'dasdsdasdsadsadsa';
$date = "2019-12-30";
$sql = 'CALL proc_invoice_product_list("'.$var.'","i.invoice_date","2019-12-30","","")';
$productinvoice = DB::select($sql);
var_dump($productinvoice);
}
Why when i use input from request can't call my procedure? How do i read from input request?
You may need to first confirm the client_id is being passed to your productInvoiceListTest method by using the dd helper.
public function productInvoiceListTest(Request $request){
dd($request->all());
}
If the client_id is part of the the request instance passed in your productInvoiceListTest method, then you can access it using $request->input('client_id') method. If it is not part of the request instance, ensure that from the method calling or redirecting to productInvoiceListTest, the client_id is passed.

Passing Optional parameters not calling to the correct one

Little stuck with Parameters, market and sort are optional
Route::get('Category/{title}/{market?}/{sort?}', 'HomeController#productList');
But when i do this in the URI
url: Category/title/?sort=3
it doesn't register as 3 for sort but goes in as the market paramater
of course if the URI was Category/title/Makert/3 it will return what i want
public function productList($title, $market = null, $sort = null)
{
// Gets the Categories with its Markets
$categorys= Product::cats();
$brands = Product::CategoryWithMarket($title, $market)->groupBy('Brand')->get();
$subCat = Product::where('Category', $title)->groupBy('Market')->orderBy('Market', 'ASC')->get();
if (!$market) {
$marketList = Product::where('Category', $title)->orderBy('Brand', 'ASC')->orderBy('Label', 'ASC')->paginate(15);
$brands = Product::where('Category', $title)->groupBy('Brand')->orderBy('Brand', 'ASC')->get();
$mainTitle = ucfirst($title);
}
else {
// Gets the list of products with the catery and market attributes arranged by the brand of product
$marketList = Product::CategoryWithMarket($title, $market)->paginate(15);
$mainTitle = ucfirst($title) . ' ' . ucfirst($market) ;
}
return $sort;
In theroy it should pass back the sort parameter which is 3 but it doesnt return anything, so my question is how do i get sort to return its value 3 rather than being null
Router only uses the path to match the routes and only path parameteres are injected to the controller. So if you you want sort to be passed to the controller from the router you need to put that in the path (/{sort?}), not in the query (?sort=3).
If you want to access query parameters in your controller, you can do this via $request object (if it's your action's argument) or Request facade:
public function someAction() {
echo Request::query('sort');
}

Access query string values from Laravel

Does anyone know if it's possible to make use of URL query's within Laravel.
Example
I have the following route:
Route::get('/text', 'TextController#index');
And the text on that page is based on the following url query:
http://example.com/text?color={COLOR}
How would I approach this within Laravel?
For future visitors, I use the approach below for > 5.0. It utilizes Laravel's Request class and can help keep the business logic out of your routes and controller.
Example URL
admin.website.com/get-grid-value?object=Foo&value=Bar
Routes.php
Route::get('get-grid-value', 'YourController#getGridValue');
YourController.php
/**
* $request is an array of data
*/
public function getGridValue(Request $request)
{
// returns "Foo"
$object = $request->query('object');
// returns "Bar"
$value = $request->query('value');
// returns array of entire input query...can now use $query['value'], etc. to access data
$query = $request->all();
// Or to keep business logic out of controller, I use like:
$n = new MyClass($request->all());
$n->doSomething();
$n->etc();
}
For more on retrieving inputs from the request object, read the docs.
Yes, it is possible. Try this:
Route::get('test', function(){
return "<h1>" . Input::get("color") . "</h1>";
});
and call it by going to http://example.com/test?color=red.
You can, of course, extend it with additional arguments to your heart's content. Try this:
Route::get('test', function(){
return "<pre>" . print_r(Input::all(), true) . "</pre>";
});
and add some more arguments:
http://example.com/?color=red&time=now&greeting=bonjour`
This will give you
Array
(
[color] => red
[time] => now
[greeting] => bonjour
)
Query params are used like this:
use Illuminate\Http\Request;
class ColorController extends BaseController{
public function index(Request $request){
$color = $request->query('color');
}
public function fetchQuery(Request $request){
$object = $request->query('object');
$value = $request->query('value');
}

get post parameters in zend framework in "put" method

I am getting get parameters using this
$this->params()->fromQuery('KEY');
I found two way to get POST parameters
//first way
$this->params()->fromPost('KEY', null);
//second way
$this->getRequest()->getPost();
Both of this working in "POST" method but now in a "PUT" method if I pass values as a post parameters.
How I can get post parameters in "PUT" method?
I guess the right way of doing that is by using Zend_Controller_Plugin_PutHandler:
// you can put this code in your projects bootstrap
$front = Zend_Controller_Front::getInstance();
$front->registerPlugin(new Zend_Controller_Plugin_PutHandler());
and then you can get your params via getParams()
foreach($this->getRequest()->getParams() as $key => $value) {
...
}
or simply
$this->getRequest()->getParam("myvar");
You need to read the request body and parse it, something like this:
$putParams = array();
parse_str($this->getRequest()->getContent(), $putParams);
This will parse all params into the $putParams-array, so you can access it like you would access the super globals $_POST or $_GET. For instance:
// Get the parameter named 'id'
$id = $putParams['id'];
// Loop over all params
foreach($putParams as $key => $value) {
echo 'Put-param ' . $key . ' = ' . $value . PHP_EOL;
}
I had trouble using PUT data sent from AngularJS and found the best way was to use a custom Zend plugin
class Web_Mvc_Plugin_JsonPutHandler extends Zend_Controller_Plugin_Abstract {
public function preDispatch(Zend_Controller_Request_Abstract $request) {
if (!$request instanceof Zend_Controller_Request_Http) {
return;
}
if ($this->_request->isPut()) {
$putParams = json_decode($this->_request->getRawBody());
$request->setParam('data', $putParams);
}
}
}
Which can then be accesses via getParams as a PHP object
$data = $this->getRequest()->getParam('data');
$id = $data->id;

How does codeigniter know how to pass parameters from controller to the model

I am starting to learn codeigniters active record and i am querying my database using parameters passed from the controller to the model.
First i am passing the id from the controller to the model and that works.
Controller
function bret($id){
$this->load->model('school_model');
$data = $this->school_model->get_city_and_population($id);
foreach ($data as $row)
{
echo "<b>Name Of The City</b>...........". $row['Name'];
echo "<br/>";
echo "<b>Total Population</b>...........".$row['Population'];
}
}
Model
function get_city_and_population($id){
$this->db->select('Name,Population');
$query = $this->db->get_where('city', array('ID'=>$id));
return $query->result_array();
}
I went ahead and put in multiple parameters expecting to fail but this works but i am not so sure why it worked or what worked.
Controller
public function parameters($id,$name,$district){
$this->load->model('school_model');
$data = $this->school_model->multiple_parameters($id,$name,$district);
foreach ($data as $row)
{
echo "<b>Total Population</b>...........".$row['Population'];
}
}
Model
function multiple_parameters($id,$name,$district){
$this->db->select('Population');
$query = $this->db->get_where('city', array('ID'=>$id,'Name'=>$name,'District'=>$district));
return $query->result_array();
}
In my multiple parameters example i visited http://example.com/env/at/index.php/frontpage/parameters/7/Haag/Zuid-Holland/
Here,i know the name Haag is in id 7 and the district is Zuid-Holland
Here are my questions.How does codeigniter know how to pass the parameters from the url to the model and secondly,what if i was slightly wrong like 7/Haag/Zuid-Hollandes/,how would i show the user that,that url is wrong and fallback to a default value instead of showing blank when the parameters are wrong?.
//In codeiginter URI contains more then two segments they will be passed to your function as parameters.
//if Url: http://example.com/env/at/index.php/frontpage/parameters/7/Haag/Zuid-Holland/
//Controller: forntpage
public function parameters($id,$name,$district){
echo $id.'-'$name.'-'.$district;
}
//and if you are manually getting url from segment & want to set default value instead of blank then use following:
public function parameters(
$this->load->helper("helper");
$variable=$this->uri->segment(segment_no,default value);
//$id=$this->uri->segment(3,0);
}
//or
//Controller: forntpage
public function parameters($id='defaultvalue',$name='defaultvalue',$district='defaultvalue'){
echo $id.'-'$name.'-'.$district;
}
That's just simple uri mapping in CI, or uri param binding if you will.
When you have a method like:
public function something($param1, $param2) {
// get from: controller/something/first-param/second-param
}
That means your uri segments are passed as arguments to your controller method.
The above method could be written as:
public function something() {
$param1 = $this->uri->segment(3);
$param2 = $this->uri->segment(4);
// segment 1 is the controller, segment 2 is the action/method.
}
You need to understand that you have to manually check if the uri segments are exactly what you want them to be, as CI doesn't do anything else than this mapping.
Next, if you want to have some defaults, following statement is true:
public function something($param1 = 'some default value', $param2 = 'other value') {
// get from: controller/something/first-param/second-param
}
That is, if a url like: /controller/something is passed along, you will still get your default values back. When controller/something/test is passed, your first param is overridden by the one from the url (test).
That's pretty much it.

Categories