<file_sep><?php


Auth::routes();


// front content
Route::get('/', 'FrontController@index')->name('index');
Route::get('cart', 'FrontController@cart')->name('cart');
Route::get('/product/{id}', 'FrontController@view')->name('view');
Route::get('/catalog/{id?}', 'FrontController@catalog')->name('catalog');
Route::get('add-to-cart/{id}', 'FrontController@addToCart')->name('addToCart');
Route::get('search', 'FrontController@search')->name('search');

// for ajax
Route::patch('update-cart', 'FrontController@update');
Route::delete('remove-from-cart', 'FrontController@remove');

Route::get('/home', 'HomeController@index')->name('home');


// edit group
Route::group(['middleware' => ['auth']], function () {

    Route::group(['prefix' => 'edit-product'], function () {
        Route::get('/', 'Backend\ProductsController@index')->name('edit-product.index');
        Route::post('/', 'Backend\ProductsController@store')->name('edit-product.store');
        Route::get('/{id}', 'Backend\ProductsController@edit')->name('edit-product.edit');
        Route::patch('/{id}', 'Backend\ProductsController@update')->name('edit-product.update');
        Route::delete('/{id}', 'Backend\ProductsController@destroy')->name('edit-product.delete');
    });

    Route::group(['prefix' => 'edit-categories'], function () {
        Route::get('/', 'Backend\CategoriesController@index')->name('edit-categories.index');
        Route::post('/', 'Backend\CategoriesController@store')->name('edit-categories.store');
        Route::get('/{id}', 'Backend\CategoriesController@edit')->name('edit-categories.edit');
        Route::patch('/{id}', 'Backend\CategoriesController@update')->name('edit-categories.update');
        Route::delete('/{id}', 'Backend\CategoriesController@destroy')->name('edit-categories.delete');
    });

});


<file_sep><?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Category extends Model
{
    protected $guarded = ['_token', 'id'];

    static function TakeParent($id = 0)
    {
        $result = self::where('parentId', $id)->get();
        return $result;
    }

    public function takeBreadcrumb()
    {
        $temp = ($this->parentId !== 0) ? $this->recursia($this->parentId) : [];
        return $temp;
    }

    public function recursia($id, $array = [])
    {
        var_dump($id);
        $temp = Category::where('id', $id)->first();
        echo $temp->name;
        if ($temp) {
            array_unshift( $array,[
                $temp->name,
                $temp->id
            ]);
            if ($temp->parentId !== 0) {
                $array = $this->recursia($temp->parentId, $array);
            }
            return $array;
        }
    }

    public function ProductCategory(){
        return $this->hasMany($this, 'parentId');
    }

    public function rootCategories(){
        return $this->where('parentId', 0)->with('ProductCategory')->get();
    }

    public function products()
    {
        return $this->hasMany(Product::class, 'category_id', 'id');
    }

    public function categories()
    {
        return $this->hasMany(Category::class, 'parentId', 'id');
    }


}
<file_sep><?php

use Illuminate\Database\Seeder;
use App\User;
use Illuminate\Support\Facades\DB;

class UsersTableSeeder extends Seeder
{

    public function run()
    {
        DB::table('users')->insert([
            'name' => 'test',
            'email' => '<EMAIL>',
            'password' => bcrypt('<PASSWORD>'),
        ]);

        $users = factory(User::class, 20)->create();
    }
}
<file_sep><?php

namespace App\Http\Controllers\Backend;

use App\Http\Requests\StoreCategoryRequest;
use App\Models\Category;
use App\Models\Product;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;

class CategoriesController extends Controller
{
    public function __construct()
    {
        $this->middleware('auth');
    }

    public function index()
    {
        $data = new Category();
        $action = route('edit-categories.store');
        return view('backend.categories.index')->with(compact('data', 'action'));
    }

    public function store(StoreCategoryRequest $request)
    {
        $data = new Category($request->toArray());
        if (!$data) {
            abort(404);
        }
        $data->save();
        return back();
    }

    public function update(StoreCategoryRequest $request)
    {
        $data = Category::find($request->id);
        if (!$data) {
            abort(404);
        }
        $data->name = $request->name;
        $data->parentId = $request->parentId;
        $data->save();
        return redirect(route('edit-categories.index'));
    }

    public function destroy(Request $request)
    {
        $data = Category::find($request->id);
        if (!$data) {
            abort(404);
        }
        $data->delete();
        return back();
    }

    public function edit($id)
    {
        $data = Category::find($id);
        $action = route('edit-categories.update', ['id' => $id]);
        return view('backend.categories.index')->with(compact('data', 'action'));
    }
}
<file_sep><?php

use App\Models\Product;
use Faker\Generator as Faker;

$factory->define(Product::class, function (Faker $faker) {
    return [
        'name' => $faker->name(10),
        'description' => $faker->text(110),
        'price' => rand(1, 10),
        'category_id' => rand(1, 10),
    ];
});
<file_sep><?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model;

class Product extends Model
{
    protected $guarded = ['_token', 'id'];

    public static function search($search, $category)
    {
        $data = Product::where('name', 'LIKE', "%{$search}%")->where('category_id', 'LIKE', $category)->get();

        return $data;
    }
}
<file_sep><?php

namespace App\Http\Controllers;

use App\Models\Category;
use App\Models\Product;
use Illuminate\Http\Request;

class FrontController extends Controller
{
    public function index()
    {
        $products = Product::paginate(9);
        return view('front/main', compact('products'));
    }

    public function view($id)
    {
        $product = Product::find($id);
        if (!$product) {
            abort(404);
        }
        return view('front/view', compact('product'));
    }

    public function cart()
    {
        return view('front/cart');
    }

    public function catalog(Request $request)
    {
        $result = null;
        $name = '';
        $products = [];
        $breadcrumb = [];
        if (isset($request->id)) {
            $temp = Category::where('id', $request->id)->first();
            $name = ' - ' . $temp->name;
//            $result = $temp->categories();
//            $products = $temp->products();
            // Рилейшены чего-то не работали я сделал так не обессудьте


            $result = Category::where('parentId', $temp->id)->get()->toArray();
            $products = Product::where('category_id', $temp->id)->get()->toArray();
            $breadcrumb = $temp->takeBreadcrumb();

        } else {
            $result = Category::TakeParent()->toArray();
        }
        $data = (object)[
            'name' => $name,
            'catalogs' => $result,
            'products' => $products,
            'breadcrumb' => $breadcrumb,
        ];

        return view('front/categories', compact('data'));
    }

    public function addToCart($id)
    {
        $product = Product::find($id);
        if (!$product) {
            abort(404);
        }
        $cart = session()->get('cart');

        // если корзина пуста, то это первый товар
        if (!$cart) {
            $cart = [
                $id => [
                    "name" => $product->name,
                    "quantity" => 1,
                    "price" => $product->price,
                ]
            ];
            session()->put('cart', $cart);
            return redirect()->back()->with('success', 'Product added to cart successfully!');
        }

        // если корзина не пуста, проверяет , существует ли этот товар, затем увеличьте количество
        if (isset($cart[$id])) {
            $cart[$id]['quantity']++;
            session()->put('cart', $cart);
            return redirect()->back()->with('success', 'Product added to cart successfully!');
        }

        // если товара нет в корзине, добавьте в корзину с количеством = 1
        $cart[$id] = [
            "name" => $product->name,
            "quantity" => 1,
            "price" => $product->price,
        ];
        session()->put('cart', $cart);
        return redirect()->back()->with('success', 'Product added to cart successfully!');
    }

    public function update(Request $request)
    {
        if ($request->id and $request->quantity) {
            $cart = session()->get('cart');
            $cart[$request->id]["quantity"] = $request->quantity;
            session()->put('cart', $cart);
            session()->flash('success', 'Cart updated successfully');
        }
    }

    public function remove(Request $request)
    {
        if ($request->id) {
            $cart = session()->get('cart');
            if (isset($cart[$request->id])) {
                unset($cart[$request->id]);
                session()->put('cart', $cart);
            }
            session()->flash('success', 'Product removed successfully');
        }
    }

    public function search(Request $request)
    {
        $search = $request->input('search');
        $category = $request->input('category_id');
        $products = Product::search($search, $category);
//        $products = $query->paginate(6)->withQueryString();
        return view('front.search', compact('products', 'search'));
    }
}
<file_sep><?php

namespace App\Http\Controllers\Backend;

use App\Http\Requests\StoreProfuctRequest;
use App\Models\Product;
use Illuminate\Http\Request;
use App\Http\Controllers\Controller;

class ProductsController extends Controller
{
    public function __construct()
    {
        $this->middleware('auth');
    }

    public function index()
    {
        $data = new Product;
        $action = route('edit-product.store');
        return view('backend.products.index')->with(compact('data', 'action'));
    }

    public function store(StoreProfuctRequest $request)
    {
        $data = new Product($request->toArray());
        if (!$data) {
            abort(404);
        }
        $data->save();
        return back();
    }

    public function update(StoreProfuctRequest $request)
    {
        $data = Product::find($request->id);
        if (!$data) {
            abort(404);
        }
        $data->name = $request->name;
        $data->description = $request->description;
        $data->price = $request->price;
        $data->category_id = $request->category_id;
        $data->save();
        return redirect(route('edit-product.index'));
    }

    public function destroy(Request $request)
    {
        $data = Product::find($request->id);
        if (!$data) {
            abort(404);
        }
        $data->delete();
        return back();
    }

    public function edit($id)
    {
        $data = Product::find($id);
        $action = route('edit-product.update', ['id' => $id]);
        return view('backend.products.index')->with(compact('data', 'action'));
    }


}
