To create an archive page in Laravel 10, you can follow these steps:
Step 1: Update Your Routes
First, define the necessary routes in your web.php file. You'll need routes for the archive page and individual posts.
use App\Http\Controllers\PostController;
Route::get('/blogs/{month}-{year}', [PostController::class, 'archive'])->name('posts.archive');
Route::get('/blogs/{slug}', [PostController::class, 'show'])->name('posts.show');
Step 2: Create the Controller Methods
In your PostController, add methods to handle the archive and individual post views.
namespace App\Http\Controllers;
use Illuminate\Http\Request;
use App\Models\Post;
use Carbon\Carbon;
class PostController extends Controller
{
public function archive($month, $year)
{
$posts = Post::whereYear('created_at', $year)
->whereMonth('created_at', $month)
->get();
return view('posts.archive', compact('posts', 'month', 'year'));
}
public function show($slug)
{
$post = Post::where('slug', $slug)->firstOrFail();
return view('posts.show', compact('post'));
}
}
Step 3: Update Your Post Model
Ensure your Post model has a slug attribute. You can generate slugs using Laravel's Str helper.
namespace App\Models;
use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Support\Str;
class Post extends Model
{
use HasFactory;
protected $fillable = ['title', 'content', 'slug'];
public static function boot()
{
parent::boot();
static::creating(function ($post) {
$post->slug = Str::slug($post->title);
});
}
}
Step 4: Create Blade Views
Create a posts/archive.blade.php file to display the archive.
@extends('layouts.app')
@section('content')
<h1>Archive for {{ $month }}-{{ $year }}</h1>
<ul>
@foreach($posts as $post)
<li>
<a href="{{ route('posts.show', $post->slug) }}">{{ $post->title }}</a>
</li>
@endforeach
</ul>
@endsection
Create a posts/show.blade.php file to display individual posts.
@extends('layouts.app')
@section('content')
<h1>{{ $post->title }}</h1>
<p>{{ $post->content }}</p>
@endsection
Step 5: Generate Archive Links
In your main blog page, generate links to the archive pages. You can use a query to group posts by month and year.
$archives = Post::selectRaw('year(created_at) year, month(created_at) month, count(*) published')
->groupBy('year', 'month')
->orderByDesc('year')
->orderByDesc('month')
->get();
In your Blade view, loop through the $archives to create links.
<ul>
@foreach($archives as $archive)
<li>
<a href="{{ route('posts.archive', ['month' => $archive->month, 'year' => $archive->year]) }}">
{{ $archive->month }}-{{ $archive->year }} ({{ $archive->published }} posts)
</a>
</li>
@endforeach
</ul>
Summary
- Define routes for archives and individual posts.
- Create controller methods to handle archive and post views.
- Ensure your
Postmodel generates slugs. - Create Blade views for displaying archives and posts.
- Generate archive links on your main blog page.
This setup will allow you to have an archive page that lists posts by month and year, and individual post pages accessible via slugs.