I am trying to query two tables in a database but its returning this error.
I am trying to implement a search through multiple tables. The project is an online store with 3 distinctive tables, Products, Categories and Brands. I can only search through the Products table but can't seem to get the same search field from my blade file to search either the categories or the brands and return results of the associated products.
QLSTATE[23000]: Integrity constraint violation: 1052 Column 'status' in where clause is ambiguous (SQL: select * from `categories` inner join `products` on `products`.`category_id` = `categories`.`id` where `name` LIKE %Television% and `status` = 1)
My Search function
public function searchProducts(Request $request) {
$product = $request->input('product');
$categories = Category::with('categories')->where(['parent_id' => 0])->get();
$productsAll = Category::query()->join('products', 'products.category_id', '=', 'categories.id')
->where('name', 'LIKE', "%{$product}%")
->where('status', 1)->get();
$breadcrumb = "<a href='/'>Home</a> / ".$product;
return view('pages.results')->with(compact('categories','productsAll','product','breadcrumb'));
}
My Category Model
class Category extends Model implements Searchable
{
protected $table = 'categories';
protected $fillable = [
'name'
];
public function categories(){
return $this->hasMany('App\Category','id');
}
public function products(){
return $this->hasMany('App\Product','id');
}
}
My Products Model
class Product extends Model implements Searchable
{
public function category() {
return $this->hasMany('App\Category', 'id') ;
}
public function attributes(){
return $this->hasMany('App\Product','id');
}
}
You have status column in more than one table.
Change this
->where('status', 1)->get();
to this
->where('products.status', 1)->get();
I was able to solve it by modifying my search function as follows.
public function searchProducts(Request $request) {
$product = $request->input('product');
$categories = Category::with('categories')->where(['parent_id' => 0])->get();
$productsAll = Category::query()->join('products', 'products.category_id', '=', 'categories.id')
->where('categories.name', 'LIKE', "%{$product}%")
->orWhere('products.product_name', 'LIKE', "%{$product}%")
->where('products.status', 1)->get();
$breadcrumb = "<a href='/'>Home</a> / ".$product;
return view('pages.results')->with(compact('categories','productsAll','product','breadcrumb'));
}
Related
I have 3 table products, details and
detail_colors
I want select max "stock" from "detail_colors" and
max "price" from "details"
$products = Product::
join('details', function (JoinClause $join) {
$join->on('products.id', '=', 'details.product_id');
})
->join('detail_colors', function (JoinClause $join) {
$join->on('products.id', '=', 'detail_colors.product_id');
})
->select('products.*', DB::raw('max(details.price) as price'), DB::raw('max(detail_colors.stock) as stock'))
and its not working.
I use laravel 8.*
Can't you use aggregate functions on relationships?
$products = Product::query()
->withMax('details', 'price')
->withMax('detail_colors', 'stock')
Or you can define the relationship as such:
public function details()
{
return $this->hasOne(Details::class)->ofMany('price', 'max');
}
public function details()
{
return $this->hasOne(DetailColors::class)->ofMany('stock', 'max');
}
For a small chat purpose, I am using below relationship
Model
class Chat extends Model
{
protected $table = 'chats';
protected $primaryKey = 'chat_id';
protected $filllable = [
'chat_id',
'sender_id',
'reciever_id',
'content',
'sender_type',
'reciever_type',
'view_status'
];
class Admin extends Authenticatable
{
public function chats()
{
return $this->hasMany(Chat::class, 'sender_id', 'admin_id');
}
}
but the issue is both user's are in the same table some times it is sender_id sometimes it is reciever_id so I want to return the above relationship with the condition (if the receiver type in chat table is 1 it should be reciever_id else it should be the sender_id)
Controller
$seller_id = auth()->guard('seller')->user()->seller_id;
$chatLists = Admin::whereHas('chats', function ($q) {
$q->where('reciever_type', 2);
$q->orWhere('sender_type', 2);
})
->with(['chats' => function ($q) {
$q->where('reciever_type', 2);
$q->orWhere('sender_type', 2);
}])
->orderBy('created_at', 'desc')
->get();
return view('seller.chat.index', compact('chatLists'));
}
sender_type and receiver_type don't seem to do much.
If you retrieve $seller_id and intend to get all chats from $seller_id,
both chats with $seller_id as sender
and chats with $seller_id as receiver
Then your query could look like this.
$seller_id = auth()->guard('seller')->user()->seller_id;
$chatLists = Admin::whereHas('chats', function ($q) use ($seller_id) {
$q->where('receiver_id', $seller_id)
->orWhere('sender_id', $seller_id);
})
->with(['chats' => function ($q) use ($seller_id) {
$q->where('receiver_id', $seller_id)
->orWhere('sender_id', $seller_id);
}])
->latest()
->get();
I am trying to return a view with 2 tables, orders and order_menu. What I want to do is to display what orders the customer ordered based on order_id to my view.
Here is the database table for orders and this is database table for order_menu.
I've tried using join table in my controller but it won't work. Here is my controller:
public function show(Order $order)
{
$data = DB::table('order_menu')
->join('menus', 'menus.id', '=', 'order_menu.menu_id')
->join('orders', 'orders.id', '=', 'order_menu.order_id')
->select('orders.*', 'menus.name', 'order_menu.quantity')
->get();
return view('admin.order.detail')->with([
'order' => $order,
'data' => $data,
]);
}
Is there any solutions to solve this?
You just need to add a filter for order id in your query, I assume $order is the instance of model and has order data
$data = DB::table('order_menu')
->join('menus', 'menus.id', '=', 'order_menu.menu_id')
->join('orders', 'orders.id', '=', 'order_menu.order_id')
->select('orders.*', 'menus.name', 'order_menu.quantity')
->where('orders.id', $order->id)
->get();
Or if you already have relations in place in your model then using eloquent you can query the data as
class Order extends Model
{
public function menus()
{
return $this->belongsToMany(Menu::class, 'order_menu ', 'order_id', 'menu_id')->withPivot('quantity');
}
}
class Menu extends Model
{
public function orders()
{
return $this->belongsToMany(Order::class, 'order_menu ', 'menu_id','order_id');
}
}
$data = Order::with('menus')->find($order->id);
public function show(Order $order)
{
$data = DB::table('orders*')
->join('order_menu*', 'order_menu.id', '=', 'orders.id')
->groupBy('orders.id')
->get();
return view('admin.order.detail')->with([
'data' => $data,
]);
}
Is there the best way/the simplest way to get all data where pivot?
I tried this $article = Article::with('category')->wherePivot('category_id', $category)->get(); but i got error
SQLSTATE[42S22]: Column not found: 1054 Unknown column 'pivot' in 'where clause' (SQL: select * from `articles` where `pivot` = category_id)
The relation is many to many
Article
id
content
public function category(){
return $this->belongsToMany(Category::class, 'articles_has_categories', 'article_id', 'category_id');
}
Articles_Has_Categories
id
article_id
category_id
public function article ()
{
return $this->belongsTo(Article::class,'article_id');
}
public function category ()
{
return $this->belongsTo(Category::class,'category_id');
}
Category
id
name
public function article(){
return $this->belongsToMany(Article::class, 'articles_has_categories', 'category_id', 'article_id');
}
Please try this:
$article = Article::with(['category' => function($query) use ($category) {
$query->where('category_id', $category);
}
])->get();
$article = Article::with(['category' => function($query) use ($category) {
$query->whereHas('category_id', $category);
}
])->get();
If you use $category as array the use $query->whereHas('category_id', $category); or else if you use $category is a single id $query->where('category_id', $category);
I have a product model with versioned data and I got a category model that can have one or many products. When I want to delete a category the code has to check if there are products related to the category. How to define the relation so that it goes to the products_version table to check if the category_id exists here before deleting it?
Here is my product model:
use Versionable, SoftDeletes;
protected $fillable = ['product_name', 'supplier', 'unit', 'pieces', 'desired_stock', 'current_stock', 'category_id', 'price'];
public $timestamps = true;
public $versioned = ['category_id', 'product_name', 'supplier','unit','desired_stock','current_stock','price','pieces', 'deleted_at'];
public function parent()
{
return $this->belongsTo('App\Category');
}
Versioning for products is working. I used the following code for it: https://github.com/ProAI/eloquent-versioning
My category model:
public function products()
{
return $this->hasMany('App\Product');
}
The code I used to check if there are products related to the category:
public function destroy($id)
{
// delete
$category = Category::withCount('products')->where('id', '=', $id)->first();
if ($category->products_count > 0) {
Session::flash('message', 'Can not delete category');
} else {
$category->delete();
// redirect
Session::flash('success', 'Category deleted');
}
return Redirect::to('categories');
}
The error message I get:
SQLSTATE[42S22]: Column not found: 1054 Unknown column
'products.category_id' in 'where clause' (SQL: select categories.,
(select count() from products inner join products_version on
products.id = products_version.ref_id and
products_version.version = products.latest_version where
categories.id = products.category_id and
products_version.deleted_at is null) as products_count from
categories where id = 1 limit 1)
You may need something like has many through relationship
public function products()
{
return $this->hasManyThrough('App\Product', 'App\ProductVersion');
}
So it will link Category to a Product through ProductVersion because 'category_id' exists only in ProductVersion
Check Laravel Docs for more info
P.S. You may need to create ProductVersion model for products_version table
This might work:
$category = Category::withCount('products' => function($q) {
$q->where('id', '=', $id);
})->first();