I can't figured it out how can I make following. User can see details of his order. I want to make button for a user to be able to leave a review of the product which he purchased.
When he left review for a product I want to change the button from "submit review" to "edit review". Problem is how to do this if he purchased 2 or more items? I want to be able to leave review for each item separately.
In the controller I have this function:
public function orderView($orderId)
{
$order = Order::where('order_id', $orderId)->where('user_id', Auth::user()->user_id)->first();
$reviews = Review::where('user_id', Auth::user()->user_id)->first();
return View::make('site.users.orders_view', [
'order' => $order,
'reviews' => $reviews
]);
}
So, here I select his orders and reviews for authenticated user. Where I show button on the view "submit review", "edit review" I've tried this
@forelse($reviews as $review)
@if($review->product_id == $item->product_id)
@if($review->rating_published == 0)
<a>Waiting</a>
@else
<a href="">Edit</a>
@endif
@else
<a href="">Add</a>
@endif
@empty
<a href="">Add</a>
@endforelse
If user has 2 products in that order and left only for one of them review both buttons are changed to Edit Review
.
What I want to do is if user has 2 products in that order and review for 1 of the products to have one button "edit review" and one "submit review"
After adding the relationships in the Product model and Review model you can edit the Controller code as follow :
public function orderView($orderId)
{
$order = Order::where('order_id', $orderId)->where('status', 1)
->where('user_id', Auth::user()->user_id)
->first();
$productIds = $order->getOrderProductIds();
$reviews = Review::with('item')
->whereHas('item', function($q) use($productIds){
$q->whereIn('product_id', $productIds);
})
->where('user_id', Auth::user()->user_id)
->get();
return View::make('site.users.orders_view', [
'order' => $order,
'reviews' => $reviews
]);
}
Then add this hepler method in the Product model :
public static function hasReview($reviews, $product_id)
{
foreach ($reviews as $review) {
if ($review->item->product_id == $product_id) {
return $review;
}
}
return null;
}
And in the view you should do this :
<?php $review = \App\Product::hasReview($reviews, $item->product_id)?>
@if($review != null)
@if($review->rating_published == 0)
<a class="btn btn-warning btn-xs">Waiting for Approval ID: {{$item->product_id }}</a>
@else
<a class="btn btn-warning btn-xs" href="{{ URL::to('/users/review/' . $item->product_id . '?_token=' . csrf_token()) }}">Edit Review ID: {{$item->product_id }}</a>
@endif
@else
<a class="btn btn-warning btn-xs" href="{{ URL::to('/users/review/' . $item->product_id . '?_token=' . csrf_token()) }}">Leave Review ID: {{$item->product_id }}</a>
@endif
PS : Think of adding :
- Many to Many relationship between Product and Order => it will helps you in many things especially queries.
- Helper class witch will contains the helper methods like
hasReview
You can make something better, with retrieving order's reviews.
So in your model Product, you make:
public function reviews()
{
return $this->hasMany('App\Review'); //depends from namespace of your model Review
}
And in your model Review:
public function product()
{
return $this->belongsTo('App\Product'); //depends from namespace of your model Product
}
And after in your controller:
public function orderView($orderId)
{
$order = Order::where('order_id', $orderId)->where('user_id', Auth::user()->user_id)->first();
return View::make('site.users.orders_view', [
'order' => $order
]);
}
And then in your view:
@foreach($order->product->reviews as $review)
@if($review->user_id == Auth::user()->user_id)
<a class="btn btn-warning btn-xs" href="">Edit Review</a></li>
@else
<a class="btn btn-warning btn-xs" href="">Submit Review</a></li>
@endif
@endforeach