diff --git a/app/Http/Controllers/Web/BookmarkController.php b/app/Http/Controllers/Web/BookmarkController.php new file mode 100644 index 0000000..5ae24cc --- /dev/null +++ b/app/Http/Controllers/Web/BookmarkController.php @@ -0,0 +1,29 @@ +user(); + $user->savedJobs()->toggle($job->id); + + if ($request->wantsJson()) { + $bookmarked = $user->savedJobs()->where('job_id', $job->id)->exists(); + return response()->json(['bookmarked' => $bookmarked]); + } + + return back(); + } + + public function index(Request $request) + { + $jobs = $request->user()->savedJobs()->latest('user_saved_jobs.created_at')->paginate(20); + return view('jobs.bookmarks', compact('jobs')); + } +} \ No newline at end of file diff --git a/app/Providers/AppServiceProvider.php b/app/Providers/AppServiceProvider.php index 452e6b6..33e33e8 100644 --- a/app/Providers/AppServiceProvider.php +++ b/app/Providers/AppServiceProvider.php @@ -2,23 +2,30 @@ namespace App\Providers; +use Illuminate\Support\Facades\Auth; +use Illuminate\Support\Facades\View; use Illuminate\Support\ServiceProvider; class AppServiceProvider extends ServiceProvider { - /** - * Register any application services. - */ public function register(): void { // } - /** - * Bootstrap any application services. - */ public function boot(): void { - // + View::composer('components.job-card', function ($view) { + static $bookmarkedIds = null; + + if ($bookmarkedIds === null) { + $bookmarkedIds = Auth::check() + ? Auth::user()->savedJobs()->pluck('job_id')->flip() + : collect(); + } + + $job = $view->getData()['job']; + $view->with('bookmarked', $bookmarkedIds->has($job->id)); + }); } } diff --git a/resources/views/components/job-card.blade.php b/resources/views/components/job-card.blade.php index 164934d..cea4d49 100644 --- a/resources/views/components/job-card.blade.php +++ b/resources/views/components/job-card.blade.php @@ -1,4 +1,4 @@ -@props(['job']) +@props(['job', 'bookmarked' => false])
@@ -10,11 +10,24 @@

{{ $job->company }}

- @if($job->remote_allowed) - - Remote - - @endif +
+ @if($job->remote_allowed) + + Remote + + @endif + @auth +
+ @csrf + +
+ @endauth +
diff --git a/resources/views/jobs/bookmarks.blade.php b/resources/views/jobs/bookmarks.blade.php new file mode 100644 index 0000000..d2f0949 --- /dev/null +++ b/resources/views/jobs/bookmarks.blade.php @@ -0,0 +1,36 @@ +@extends('layouts.app') + +@section('title', 'My Bookmarks - JobifyGarden') +@section('description', 'Your saved job listings on JobifyGarden.') +@section('canonical', route('bookmarks')) + +@section('content') +
+
+

My Bookmarks

+

{{ $jobs->total() }} saved {{ Str::plural('job', $jobs->total()) }}

+
+ + @if($jobs->isEmpty()) +
+ + + +

No bookmarks yet.

+ + Browse Jobs + +
+ @else +
+ @foreach($jobs as $job) + + @endforeach +
+ +
+ {{ $jobs->links() }} +
+ @endif +
+@endsection \ No newline at end of file diff --git a/resources/views/jobs/show.blade.php b/resources/views/jobs/show.blade.php index 8e7454f..b91fb04 100644 --- a/resources/views/jobs/show.blade.php +++ b/resources/views/jobs/show.blade.php @@ -181,6 +181,27 @@

You will be redirected to the company's application page

+ @auth +
+ @csrf + +
+ @else + + + + + Log in to bookmark + + @endauth
diff --git a/resources/views/layouts/app.blade.php b/resources/views/layouts/app.blade.php index 77a4eca..dd2c9a6 100644 --- a/resources/views/layouts/app.blade.php +++ b/resources/views/layouts/app.blade.php @@ -86,6 +86,12 @@
@auth + + Bookmarks + Dashboard diff --git a/routes/web.php b/routes/web.php index c1ad5d9..85c5e39 100644 --- a/routes/web.php +++ b/routes/web.php @@ -2,6 +2,7 @@ use App\Http\Controllers\Admin\DashboardController; use App\Http\Controllers\ProfileController; +use App\Http\Controllers\Web\BookmarkController; use App\Http\Controllers\Web\HomeController; use App\Http\Controllers\Web\JobController; use App\Http\Controllers\Web\PageController; @@ -31,11 +32,14 @@ Route::get('/sitemap-index.xml', [SitemapController::class, 'sitemapIndex'])->na Route::get('/sitemap-main.xml', [SitemapController::class, 'mainSitemap'])->name('sitemap.main'); Route::get('/sitemap-jobs.xml', [SitemapController::class, 'jobsSitemap'])->name('sitemap.jobs'); -// Profile (Breeze) +// Authenticated user routes Route::middleware('auth')->group(function () { Route::get('/profile', [ProfileController::class, 'edit'])->name('profile.edit'); Route::patch('/profile', [ProfileController::class, 'update'])->name('profile.update'); Route::delete('/profile', [ProfileController::class, 'destroy'])->name('profile.destroy'); + + Route::get('/bookmarks', [BookmarkController::class, 'index'])->name('bookmarks'); + Route::post('/jobs/{job}/bookmark', [BookmarkController::class, 'toggle'])->name('jobs.bookmark'); }); // Admin routes