How to pass data to view only if it is defined? - php

As you can see in my piece of code below, $similarImages is being passed to the view, however, it is possible that there are no other similar images which means I'll pass an undefined variable. This is why I need to pass 'similarImages' => $similarImages only if $similarImages exists.
$tag = Tag::whereHas('images', function($q) use ($id) {
return $q->where('image_id', $id);
})->first();
if (!empty($tag)) {
$tagId = $tag->id;
}
$recentImages = Image::where('user_id', $authorId)->orderBy('created_at', 'desc')->limit(9)->get();
if (!empty($tagId)) {
$similarImages = Image::whereHas('tags', function($q) use ($tagId) {
return $q->where('tag_id', $tagId);
})->orderBy('created_at', 'desc')->limit(9)->get();
}
return view('specificImage', ['image' => $image, 'recentImages' => $recentImages, 'similarImages' => $similarImages, 'author' => $author, 'comments' => $comments]);

Make use of the null-coalescing operator to have a default value:
[ .. 'similarImages' => $similarImages ?? collect(), .. ]
This will use $similarImages if it is defined and not null otherwise it will assign an empty collection created by collect().
I like the idea of it always being a collection, but that's just me.

$array is always pass to the view
and if isset $similarImages, just prepend the $similarImages into $array
if not isset $similarImages just return $array (in this case $similarImages won't exists in blade)
here also you can use array_add($array, 'similarImages', $similarImages)
$tag = Tag::whereHas('images', function($q) use ($id) {
return $q->where('image_id', $id);
})->first();
if (!empty($tag)) {
$tagId = $tag->id;
}
$recentImages = Image::where('user_id', $authorId)->orderBy('created_at', 'desc')->limit(9)->get();
if (!empty($tagId)) {
$similarImages = Image::whereHas('tags', function($q) use ($tagId) {
return $q->where('tag_id', $tagId);
})->orderBy('created_at', 'desc')->limit(9)->get();
}
$array = [
'image' => $image,
'recentImages' => $recentImages,
'author' => $author,
'comments' => $comments
];
if (isset($similarImages))
{
$array = array_prepend($array, $similarImages, 'similarImages')
}
return view('specificImage', $array);

Related

How to pass variable to $callback Collection::map($callback) in CakePHP 4.2?

I'm not an expert of Collections concept in CakePhp 4, and I don't know how to pass a variable in Collection::map()
$item = [
'attributes' => [
'class' => 'mon-li-{{id}}',
'data-truc' => 'li-{{id}}'
],
'linkAttrs' => ['class' => 'mon-lien', 'style' => 'text-transform: uppercase']
];
$id = 5;
$item = collection($item)
->map(function ($value, $key){
return preg_replace('/{{id}}/', $id, $value); // $id is undefined
})
->toArray();
It gives : Notice (8): Undefined variable: id
How can I do for my function to be able to know $id ?
The use keyword helps with this:
$item = collection($item)
->map(function ($value, $key) use ($id) { // <-- See `use`
return preg_replace('/{{id}}/', $id, $value);
})
->toArray();
PHP Manual: Anonymous Functions

Laravel multiple filter with search

I want to search service providers and products, and filter by location and by service, or by location and by-products. i am using below code` $results = new ClientProfile;
if (request()->has('service-provider')) {
$results = $results->where('jobsc_id', request('service-provider'));
} elseif(request()->has('product')) {
$results = $results->where('product_id', request('product'));
} elseif(request()->has('city')){
$results = $results->where('divsec_id', request('city'));
} else {
$results = ClientProfile::searched();
}
$results = $results->where('profile_state', 'active')->paginate(10)->appends([
'service-provider' => request('service-provider'),
'product' => request('product'),
'city' => request('city'),
]);
return view('results')->with('results', $results);`
although it shows URL as domain.com/results?product=2&city=78 it shows all products without filter by city
You use if elseif therefore it when finding one, in the second also does not come.
use when instead if else
$results = new ClientProfile::when(request()->has('service-provider'), function($q){
$q->where('jobsc_id', request('service-provider'));
})
->when(request()->has('product'), function($q){
$q->where('product_id', request('product'));
})
->when(request()->has('city'), function($q){
$q->where('divsec_id', request('city'));
})
->when(count($request->all()) === 0, function($q){
$q->searched();
})
->where('profile_state', 'active')->paginate(10)->appends([
'service-provider' => request('service-provider'),
'product' => request('product'),
'city' => request('city'),
]);
return view('results')->with('results', $results);`
This code worked for me
$results = ClientProfile::when(request()->has('service-provider'), function($q){
$q->where('jobsc_id', request('service-provider'));
})->when(request()->has('product'), function($q){
$q->where('product_id', request('product'));
})->when(request()->has('city'), function($q){
$q->where('divsec_id', request('city'));
})->when(count(request()->all()) === 0, function($q){
$q->searched();
})->where('profile_state', 'active')->paginate(10)->appends([
'service-provider' => request('service-provider'),
'product' => request('product'),
'city' => request('city'),
]);

Laravel Eloquent use the orWhere query in my search system request

I tried to code a request with search system. Here the code:
$search = request()->get('search');
if(Auth::user()->hasRole('admin') || true)
{
list($orderBy, $orderDirection) = explode('.', request()->get('sort_by'));
$prestations = Prestation::with(
'service:id,name',
'facility:id,name'
)
->orWhere('service:name', 'regexp', "/$search/i")
->orderBy($orderBy, $orderDirection)
->simplePaginate(50);
$res = [
'results' => $prestations,
'total' => Prestation::all()->count(),
];
return $res;
}
The problem is that I don't know how to do something like I tried with the orWhere -> get all service name (from the relationship "with") which are equal to my $search.
Thank you.
Try this query.
$prestations = Prestation::with(
[
'service' => function($service) use($search){
$service->select(['id','name'])->where('name', $search);
},
'facility' => function($facility) {
$facility->select(['id','name'])
}
]
);

How to see matches of search in SQL?

I have a search line where a user enters query divided by commas. I need to find at least 1 matches in the SQL-table. But I need to mark the matches in each found object too. How can I do this?
Working search (Laravel Eloquent (PostgreSQL) without marking matches):
public function searchOfAuthor(Request $request)
{
$search = array_map('trim', explode(',', $request->get('search')));
$columns = [
'city',
'phone',
'email',
'skype',
'icq',
'vk'
];
$authors = AuthorMask::where(function ($query) use ($columns, $search) {
foreach ($search as $searchKey) {
if (!empty($searchKey)) {
$query->orWhere('name', 'ILIKE', '%'.$searchKey.'%');
foreach ($columns as $column) {
$query->orWhere($column, 'ILIKE', $searchKey);
}
}
}
})
->with('author')
->orderByRaw('company_id = ? desc', Auth::user()->company_id)
->paginate(5);
if (empty($authors->items())) {
return response()->json([
'data' => null,
'error' => 'Authors Have Not Been Found'
], 404);
}
return response()->json([
'data' => [
'authors' => $authors
],
'error' => null
], 200);
}
Sorry for my English.
There are nothing condition like ILIKE in laravel or Mysql. There should be LIKE. There are two lines of codes have ILIKE.
$query->orWhere('name', 'ILIKE', '%'.$searchKey.'%');
$query->orWhere($column, 'ILIKE', $searchKey);
Remove I from ILIKE of above two lines. After removing I from ILIKE it should look like
$query->orWhere('name', 'LIKE', '%'.$searchKey.'%');
$query->orWhere($column, 'LIKE', $searchKey);
Did it. Just created new array for mark of matches. Another question: who know how to append array to the object in pagination?
$matches = [];
foreach ($authors->items() as $author) {
$matches[$author->id]['name'] = 0;
foreach ($columns as $column) {
$matches[$author->id][$column] = 0;
}
foreach ($search as $searchKey) {
if (!empty($searchKey)) {
foreach ($author->toArray() as $key => $attribute) {
if (!strcasecmp($searchKey, $attribute)) {
$matches[$author->id][$key] = 1;
}
}
}
}
}
return response()->json([
'data' => [
'authors' => $authors,
'matches' => $matches
],
'error' => null
], 200);

Use array in pagination conditions [CakePHP 3]

I want to use an array of ids as a condition to my paginate function, but I get this error 'Cannot convert value to integer', I understand that a array is not an integer, but how could I make the condition look for all the values in the array.
$friendsid = explode(',', $this->Auth->user('friends'));
$this->paginate = [
'conditions' => [
'Users.id' => $friendsid,
]
];
$this->set('users', $this->paginate($this->Users));
$this->set('_serialize', ['users']);
You could try it:
$friendsid = explode(',', $this->Auth->user('friends'));
$query = $this->Users->find()
->where(function ($exp, $q) use ($friendsid) {
return $exp->in('Users.id', $friendsid);
});
$this->set('users', $this->paginate($query));
$this->set('_serialize', ['users']);

Categories