In Laravel how do i create a query string? - laravel

This will be obvious to someone else
I have a route that works and goes to the correct controller
Route::get('v1/holidays/{country}/{year}/{month}/{official?}',
'retrieveHolidayController#test'
so if i go to
http://example.com/v1/holidays/US/2014/03/01
it will go where I want to go
however I want the link to look like
http://example.com/v1/holidays?country=US&year=2014&month=03&official=01
How can I do this please ?

You redefine your route to
Route::get('v1/holidays', 'retrieveHolidayController#test');
Then in your controller you can get the param values with $request
public function test(Request $request)
{
if ( $request->has('country') && $request->country != '') {
$country = $request->country;
}
if ( $request->has('year') && $request->year != '') {
$year = $request->year;
}
.... // and the others. Then you can query like this
$holidays = Holiday::when($country, function($query) use ($country) {
return $query->where('country', $country);
})
->when($year, function($query) use ($year) {
return $query->where('year', $year);
})
->get();
//Using 'when' only executes the closure if the variable exists
}
Now, you can use your URL just the way you wanted: http://example.com/v1/holidays?country=US&year=2014&month=03&official=01

Make country,year and monthalso optional:-
Route::get('v1/holidays/{country?}/{year?}/{month?}/{official?}', 'retrieveHolidayController#test')

Route::get('v1/holidays', 'retrieveHolidayController#test');
Route::get('v1/holidays/{country}/{year}/{month}/{official?}', function($country){
return redirect()->to(action('retrieveHolidayController#test', ["country"=>$country,......]));
});
access to http://example.com/v1/holidays/US/2014/03/01
redirect to http://example.com/v1/holidays?country=US&year=2014&month=03&offical=01
if official param is null redirect param offical= param is nullable
not feel good
so
isset($official){
$paramArry["official"] = $official;
}

Related

error when try to open route without parameter in Laravel 9

I have a problem when trying to access any route without parameter:
When I wrte any route without {uname} parameter like this or any other one:
http://127.0.0.1:8000/login/
show me this error :
and it is in the home in another controller?
These is my routes:
Route::get('/{uname?}', [HomeController::class, 'home'])->name('home');
Route::get('/info/{uname?}', [HomeController::class, 'info'])->name('info.me');
Route::get('/skills/{uname?}', [HomeController::class, 'skills'])->name('skills');
Route::get('/education/{uname?}', [HomeController::class, 'education'])->name('education');
Route::get('/achievements/{uname?}', [HomeController::class, 'achievements'])->name('achievements');
Route::get('/services/{uname?}', [HomeController::class, 'services'])->name('services');
Route::get('/contact/{uname?}', [HomeController::class, 'contact'])->name('contact');
Route::post('/send-email', [HomeController::class, 'sendEmail'])->name('send-email');
Route::get('/dashboard/index', [DashboardController::class, 'index'])->name('dashboard.index');
Route::resource('/dashboard/about', AboutController::class);
Route::resource('/dashboard/skills', SkillsController::class);
Route::resource('/dashboard/education', EducationController::class);
and here is my HomeController:
class HomeController extends Controller
{
function home($uname) {
$user = User::where('name', '=', $uname)->first();
$about = $user->about;
return view('home', compact('user', 'about'));
}
function info($uname) {
$user = User::where('name', '=', $uname)->first();
$about = $user->about;
return view('info', compact(['user', 'about']));
}
function skills($uname) {
$user = User::where('name', '=', $uname)->first();
$about = $user->about;
$skills = $user->skills;
return view('skills', compact(['skills', 'user', 'about']));
}
I have already tried those and nothing changed:
PHP artisan route: cache
PHP artisan cache:clear
Your home route is a catch-all route as you have an optional parameter right after your first dash (/). This will always catch first and stop any other routes from running because it will always match your current url. To solve this you need to put this kind of route as your last route.
As for your error it's because your not finding any user. If ->first() doesn't find a matching row it will return null, and if it's null you will get an error if you're treating it as an object. You either need to check if $user is null and set $about based on that or use firstOrFail and then create a response for that error.
Your error on line 13 of HomeController...
can't find user with your condition and return null and you in line 14 want get about from null....
you have to choose :
1 :
function home($uname) {
$user = User::where('name', '=', $uname)->first();
$about = $user->about ?? null ;
return view('home', compact('user', 'about'));
}
2:
function home($uname) {
$user=$about=null;
if(isset($uname)){
$user = User::where('name', '=', $uname)->first();
$about = $user->about ?? null ;
}
return view('home', compact('user', 'about'));
}
also you can change first() to firstOrFaill() in first method to get 404 page
$uname is an optional parameter. When it's not available no user could be found. You should check if $user is not null and return an error page or something like that, when $user is null.
if ($user !== null) {
$about = $user->about;
return view('home', compact('user', 'about'));
} else {
return view('error');
}

How to perform looping in laravel search controller?

In a search controller of Laravel, I am trying to split a string '$travelIdea->tags' into an array '$listtags', and then perform searching to each $listtags[$i], but failed to do so (in "Else" part of if($scope == 'Destination')).
I know that what I should do is similar to a for-loop.
Could anyone give me some suggestion on this?
public function search(Request $request)
{
$search = $request->get('search');
$partialsearch = $request->get('partialsearch');
$scope = $request->get('scope');
if($scope == 'Destination'){
if($partialsearch)
$travelIdea=TravelIdea::where('destination','LIKE','%'.$search."%")->get();
else $travelIdea=TravelIdea::where('destination','%'.$search."%")->get();
}
else {
$listtags = explode(',', $travelIdea->tags);
$foreach($i as $i){
if($partialsearch)
$travelIdea=TravelIdea::where('listtags[$i]','LIKE','%'.$search."%")->get();
else $travelIdea=TravelIdea::where('listtags[$i]','%'.$search."%")->get();
return view('travelIdea.search', compact('travelIdea'));
});
}
}

How to check if user email is null?

I'm trying to authenticate 2 users by inheritance in a Laravel project.
In my migration I have only 1 column that can be null, that column is email.
With that column I'm expecting to double authenticate professors and alumns, I have also 2 types of registers, one has the input email and the other not.
In my database I have 2 users, one is professor, and the other alumn, professor has email, and the other has email also, because they belong to the same table but that email is NULL in alumn row.
I'm trying to check when I login if that user with email column is null, my view returns alumn.
If it's not null my view returns professor.
I tried to check if email is null in my Laravel controller.
This is my code
public function index()
{
$user = User::where('email', '=', Input::get('email'))->first();
if ($user == 'NULL'){
return ('alumn');
}
if ($user != 'null'){
return ('professor');
}
}
And my Laravel router looks like this.
Route::get('/home', 'HomeController#index')->name('home');
I also tried this function in my controller instead the other one.
if (User::where('email', '=', Input::get('email'))->count() > 0) {
// user found
}
And with exists() instead of count().
If you are wondering, I'm returning just a string right now for testing purposes.
The issue you are having is within your conditionals. ($user == 'NULL') and ($user != 'null'). What you are checking for currently if the User object is the follow string: "NULL".
These are not how you check for null. There are many options that will work.
if (empty($user)){
return view('alumn');
}
// OR
if (!$user) {
return view('alumn');
}
// OR
if (is_null($user)) {
return view('alumn');
}
Would work. You could also use is_null. If you wanted to check that user equals null you cannot put quotation marks around null.
The first() method will return null if there's no data so use is_null() instead like :
if ( is_null($user) ) {
return view('alumn');
}else{
return view('professor');
}
FYI, first() will return you null when there is no data in the database, so I hope this will help you
public function index()
{
$user = User::where('email', '=', Input::get('email'))->first();
if ( is_null($user) ) {
return view('alumn');
} else {
return view('professor');
}
}
All the answers above didn't work in my case.
So i did this to make it worth.
public function index()
{
$user = Auth::user();
if ($user->email == ''){
return ('alumne');
}
else{
return ('professor');
}
print_r(Auth::user());
}
First i printed my Auth::user to check if all was working right, then i tried to save the authentification in a variable called user.
Then i checked with a conditional and all worked fine.
public function index() {
$user = User::where('email', '=', Input::get('email'))->first();
if (empty($user)) {
return view('alumn');
} else {
return view('professor');
}
}

Passing several, optional, key/value pairs in URL with Laravel

I am making a project management application in Larvel. TaskController#index queries the db and return tasks. To be efficient and elegant, I want to be able to pass it several, optional, key/value pairs in the URL, like /tasks/org_id/36/status/open or /tasks/proj_id/1557/status/closed, and have it return the tasks based on those variables. My code is below, but the problem is getting the route to be able to receive the optional key/value pairs. Also, they shouldn't all have to all be submitted all of the time if they aren't needed.
Route/web.php:
Route::get('/tasks/status/{status}/proj_id/{proj_id}/user_id/{user_id}/org_id/{org_id}
/creator_id/{creator_id}', 'TaskController#index')->name('tasks.index');
Route::resource('tasks', 'TaskController')->except([
'tasks.index'
]);
Controller:
class TaskController extends Controller
{
public function index($proj_id = null, $recipient_id = null, $org_id = null, $creator_id = null, $status = null)
{
$tasks = Task::where('recipient_id', auth()->user()->id)
->when($status, function ($query, $status) {
return $query->where('status', $status);
})
->when($recipient_id, function ($query, $recipient_id) {
return $query->where('recipient_id', $recipient_id);
})
->when($public, function ($query, $public) {
return $query->where('public', $public);
})
->get();
return view('tasks.index', compact('tasks'));
}
How do I get the route to be able to accept a variety of optional key/value pairs?
For your convenience, work with GET (?status=...&...=...) parameters and work through them in a global middleware. It will possibly eliminate a lot of confusion as your project grows.
In the middleware you could do something like this:
public function handle($request, Closure $next)
{
$params = array();
//OR look them up individually:
$params['status'] = $request->query('status');
$params['proj_id'] = $request->query('proj_id');
$params['org_id'] = $request->query('org_id');
//OR get all query requests at once:
$params = $request->query();
//and set them as a session value
$request->session()->put('params', $params);
return $next($request);
}
Access the possible values anywhere in the project with the helper session('params')['status']. If there is no value in the url, it's defaulted to null.
Addition: to help you out building the query params for the url you may want to have a look at the PHP function http_build_query()
try this:
i think fix your problem
Route::resource('tasks', 'TaskController')->except([
'index'
]);
Route::get('/tasks/status/{status}/proj_id/{proj_id}/user_id/{user_id}/org_id/{org_id}
/creator_id/{creator_id}', 'TaskController#index');
i hope help you
https://laracasts.com/discuss/channels/laravel/routeresource-parameters

Routing to controller with optional parameters

I'd like to create a route that takes a required ID, and optional start and end dates ('Ymd'). If dates are omitted, they fall back to a default. (Say last 30 days) and call a controller....lets say 'path#index'
Route::get('/path/{id}/{start?}/{end?}', function($id, $start=null, $end=null)
{
if(!$start)
{
//set start
}
if(!$end)
{
//set end
}
// What is the syntax that goes here to call 'path#index' with $id, $start, and $end?
});
There is no way to call a controller from a Route:::get closure.
Use:
Route::get('/path/{id}/{start?}/{end?}', 'Controller#index');
and handle the parameters in the controller function:
public function index($id, $start = null, $end = null)
{
if (!$start) {
// set start
}
if (!$end) {
// set end
}
// do other stuff
}
This helped me simplify the optional routes parameters (From Laravel Docs):
Occasionally you may need to specify a route parameter, but make the presence of that route parameter optional. You may do so by placing a ? mark after the parameter name. Make sure to give the route's corresponding variable a default value:
Route::get('user/{name?}', function ($name = null) {
return $name;
});
Route::get('user/{name?}', function ($name = 'John') {
return $name;
});
Or if you have a controller call action in your routes then you could do this:
web.php
Route::get('user/{name?}', 'UsersController#index')->name('user.index');
userscontroller.php
public function index($name = 'John') {
// Do something here
}
I hope this helps someone simplify the optional parameters as it did me!
Laravel 5.6 Routing Parameters - Optional parameters
I would handle it with three paths:
Route::get('/path/{id}/{start}/{end}, ...);
Route::get('/path/{id}/{start}, ...);
Route::get('/path/{id}, ...);
Note the order - you want the full path checked first.
Route::get('user/{name?}', function ($name = null) {
return $name;
});
Find more details here (Laravel 7) : https://laravel.com/docs/7.x/routing#parameters-optional-parameters
You can call a controller action from a route closure like this:
Route::get('{slug}', function ($slug, Request $request) {
$app = app();
$locale = $app->getLocale();
// search for an offer with the given slug
$offer = \App\Offer::whereTranslation('slug', $slug, $locale)->first();
if($offer) {
$controller = $app->make(\App\Http\Controllers\OfferController::class);
return $controller->callAction('show', [$offer, $campaign = NULL]);
} else {
// if no offer is found, search for a campaign with the given slug
$campaign = \App\Campaign::whereTranslation('slug', $slug, $locale)->first();
if($campaign) {
$controller = $app->make(\App\Http\Controllers\CampaignController::class);
return $controller->callAction('show', [$campaign]);
}
}
throw new \Symfony\Component\HttpKernel\Exception\NotFoundHttpException;
});
What I did was set the optional parameters as query parameters like so:
Example URL:
/getStuff/2019-08-27?type=0&color=red
Route:
Route::get('/getStuff/{date}','Stuff\StuffController#getStuff');
Controller:
public function getStuff($date)
{
// Optional parameters
$type = Input::get("type");
$color = Input::get("color");
}
Solution to your problem without much changes
Route::get('/path/{id}/{start?}/{end?}', function($id, $start=null, $end=null)
{
if(empty($start))
{
$start = Carbon::now()->subDays(30)->format('Y-m-d');
}
if(empty($end))
{
$end = Carbon::now()->subDays(30)->format('Y-m-d');
}
return App\Http\Controllers\HomeController::Path($id,$start,$end);
});
and then
class HomeController extends Controller
{
public static function Path($id, $start, $end)
{
return view('view');
}
}
now the optimal approach is
use App\Http\Controllers\HomeController;
Route::get('/path/{id}/{start?}/{end?}', [HomeController::class, 'Path']);
then
class HomeController extends Controller
{
public function Path(Request $request)
{
if(empty($start))
{
$start = Carbon::now()->subDays(30)->format('Y-m-d');
}
if(empty($end))
{
$end = Carbon::now()->subDays(30)->format('Y-m-d');
}
//your code
return view('view');
}
}

Resources