Laravel request->all() is empty - laravel

In Laravel 8, $request->all() is not showing dynamic path parameters.
Steps to reproduce:
Start a new Laravel project with composer, Laravel version 8.61.0.
Define a route in routes/api.php as follows:
Route::get('/first/{first}/second/{second}', function (Request $request) {
return $request->all();
});
Run php artisan serve and direct the browser to http://localhost:8000/api/first/hello/second/world
Expect something like the following response: {"first":"hello","second":"world"}. Instead we simply see [].
Change the route to:
Route::get('/first/{first}/second/{second}', function (Request $request) {
return [
'first'=>$request->first,
'second'=>$request->second,
];
});
Then we see the expected {"first":"hello","second":"world"}
So...why isn't $request->all() giving me this response?

I looked at Laravel doc
Retrieving All Input Data
You may retrieve all of the incoming request's input data as an
array using the all method. This method may be used regardless of
whether the incoming request is from an HTML form or is an XHR
request
Means $request->all() equal to $request->input('name', 'email', ....)
instead of $request->all() you can try this
Route::get('/first/{first}/second/{second}', function (Illuminate\Http\Request $request, $first, $second) {
return [
'first'=> $first,
'second'=> $second,
];
});
UPDATE
You can do it too with (splat operator in PHP)
Route::get('/first/{first}/second/{second}', function (Illuminate\Http\Request $request, ...$all) {
return $all;
});
// returns
[
"hello",
"world"
]
I hope this helped you,
Happy Coding.

Have you tried dd($request->all()) statement in Controller, not in closure. In previous Laravel version (version 5 or version 7), that state works in that versions.

don't know why $request->all() is empty, but I used $request->getContent() and it returned the data in the body of the request I was looking for.
Credit:
Laravel empty request

Related

Laravel HTTP Client dynamic call HTTP Method

I want to make all requests dynamic rather than defining Http in each function followed by httpMethod like this.
Http::post()
Http::put()
Http::delete()
what i tried.
function send($method, $url) {
Http::withToken($token)->{$method}($url)
}
function x() {
return $this->send('GET', 'url')
}
My code above works fine and i dont know if call a function from variable output like {$method} is best practice. but I want something similar like Guzzle.
(new Client)->request($method, $url, $options)
you need to accept that param like
function send($method,$url) {
retrun Http::withToken($token)->{$method}($url)
}
if you take a look at the source code here https://github.com/illuminate/http/blob/a28981924d318272053b87712740868d9b44899e/Client/PendingRequest.php laravel is using Guzzle. so basicly Http Client is Guzzle.
and every function like POST PUT etc call a function name send
so you can just direct call send function like this.
Http::withToken($token)
->send('POST', 'url', [
'headers' => [...]
'form_params' => [
...
]
])

Symfony\Component\HttpKernel\Exception\MethodNotAllowedHttpException The POST method is not supported for this route. Supported methods: GET, HEAD

these are my codes for route and controller
routes:
Route::get('/form/create','MyformController#create')->name('form');
Route::post('form', 'MyformController#store');
controller:
public function create()
{
return view('formsubmitted');
//i have put form.create as shown in a laravel tutorial
//but it was showing an error that view form.create is not found, hence i
//changed it to formsubmitted(i created that form)
}
public function store(Request $request)
{
$validateData = $request->validate(
[
'Full Name'=>'required',
'Email'=>'required',
'Feedback'=>'required',
]);
form::create($request->all());
}
I am new to laravel and doing the task of creating a feedback form and storing user info and answer to a database.
I hope to hear from you guys soon. Thank you
/form/create/ and form are two different routes. If you want the same route for the GET and POST function, the routes have to be the same.
Route::get('/form/create','MyformController#create')->name('form');
Route::post('/form/create', 'MyformController#store');
If it is rest api then it might me authentication issue
goto VerifyCsrfToken.php and add there your url for eception
for eg.
protected $except = [
'/anyotherurl',
'/api/userlist'
];

How to change response in Laravel?

I have RESTful service that is available by endpoints.
For example, I request api/main and get JSON data from server.
For response I use:
return response()->json(["categories" => $categories]);
How to control format of response passing parameter in URL?
As sample I need this: api/main?format=json|html that it will work for each response in controllers.
One option would be to use Middleware for this. The below example assumes that you'll always be returning view('...', [/* some data */]) i.e. a view with data.
When the "format" should be json, the below will return the data array passed to the view instead of the compiled view itself. You would then just apply this middleware to the routes that can have json and html returned.
public function handle($request, Closure $next)
{
$response = $next($request);
if ($request->input('format') === 'json') {
$response->setContent(
$response->getOriginalContent()->getData()
);
}
return $response;
}
You can use for this Response macros. For example in AppServiceProvider inside boot method you can add:
\Response::macro('custom', function($view, $data) {
if (\Request::input('format') == 'json') {
return response()->json($data);
}
return view($view, $data);
});
and in your controller you can use now:
$data = [
'key' => 'value',
];
return response()->custom('your.view', $data);
If you run now for example GET /categories you will get normal HTML page, but if you run GET /categories?format=json you will get Json response. However depending on your needs you might need to customize it much more to handle for example also redirects.
With your format query parameter example the controller code would look something like this:
public function main(Request $request)
{
$data = [
'categories' => /* ... */
];
if ($request->input('format') === 'json') {
return response()->json(data);
}
return view('main', $data);
}
Alternatively you could simply check if the incoming request is an AJAX call via $request->input('format') === 'json' with $request->ajax()

How to send PUT request with a file and an array of data in Laravel

I am programing a web app using Laravel as API and Angularjs as frontend. I have a form to update product using PUT method with a array of informations and a file as product image. But I couldn't get the input requests in the controller, it was empty.
Please see the code below :
web.php ( route )
Route::group(['prefix' => 'api'], function()
{
Route::put('products/{id}', 'ProductController#update');
});
My angularjs product service :
function update(productId, data, onSuccess, onError){
var formData = new FormData();
formData.append('imageFile', data.imageFile);
formData.append('image', data.image);
formData.append('name', data.name);
formData.append('category_id', data.category_id);
formData.append('price', data.price);
formData.append('discount', data.discount);
Restangular.one("/products", productId).withHttpConfig({transformRequest: angular.identity}).customPUT(formData, undefined, undefined, {'Content-Type': undefined}).then(function(response) {
onSuccess(response);
}, function(response){
onError(response);
}
);
}
My ProductController update function
public function update(Request $request, $id) {
// Just print the request data
dd($request->all());
}
This is what I see in Chrome inspectmen
Please share your experiences on this problem. Thanks.
what you need is Only normal POST request with new field named _method=put then your code will work normally:
You can't do that, according to this discussion. What you should do instead is to 'fake' the PUT request by using Form Method Spoofing
Try this method:
public update(Request $request, $id)
{
$request->someVar;
$request->file('someFile');
// Get variables into an array.
$array = $request->all();
Also, make sure you're using Route::put or Route::resource for your route.

How to Read Request Input from Route?

Okay so i am having some trouble. I am trying to read the Input Values from the Post Form in Laravel. However i am getting a Method Not Allowed.
My Routes:
Route::get('/', function () {
return View::make('pages/home');
});
Route::post('/summoner/data', function (Request $request) {
return redirect()->url($request->region .'/'. $request->summonername);
});
Error:
[![Error I am getting][1]][1]
As you can see from above code i am trying to send my details to an Api. I am not sure if this is the best way of doing it though so i am open to suggestions. But at the moment i cannot read any Input Data from the Form.
You can easily do this assuming you already injected the Request
// Request is injected to the closure
Route::post('/summoner/data', function (Request $request) {
// To see the whole POST body
$bodyContent = $request->getContent();
dd($bodyContent);
// Get fullname input
echo $request->get('fullname')
});

Resources