공개 블로그 화면
공개 블로그 화면은 로그인하지 않은 방문자도 볼 수 있는 영역입니다.
담당 컨트롤러는 다음 파일입니다.
app/Http/Controllers/PostController.php
글 목록 흐름
방문자가 / 또는 /posts에 접속하면 index()가 실행됩니다.
public function index()
{
$posts = Post::where('is_published', true)
->with('category')
->latest('published_at')
->paginate(10);
$categories = Category::withCount(['posts' => function ($query) {
$query->where('is_published', true);
}])->orderBy('name')->get();
$activeCategory = null;
return view('posts.index', compact('posts', 'categories', 'activeCategory'));
}
글 목록 쿼리 해석
Post::where('is_published', true)
공개 글만 가져옵니다.
비공개 글은 관리자 화면에서는 보이지만 방문자 화면에는 보이지 않습니다.
->with('category')
글에 연결된 카테고리 정보를 함께 가져옵니다.
이렇게 하면 목록에서 $post->category->name을 사용할 수 있습니다.
->latest('published_at')
발행일 기준 최신순으로 정렬합니다.
->paginate(10)
한 페이지에 10개씩 보여줍니다.
카테고리 필터 흐름
방문자가 카테고리 버튼을 누르면 /categories/{slug}로 이동합니다.
public function category(string $slug)
{
$activeCategory = Category::where('slug', $slug)->firstOrFail();
$posts = Post::where('is_published', true)
->where('category_id', $activeCategory->id)
->with('category')
->latest('published_at')
->paginate(10);
$categories = Category::withCount(['posts' => function ($query) {
$query->where('is_published', true);
}])->orderBy('name')->get();
return view('posts.index', compact('posts', 'categories', 'activeCategory'));
}
여기서 중요한 코드는 이것입니다.
Category::where('slug', $slug)->firstOrFail();
slug에 맞는 카테고리를 찾습니다.
없으면 Laravel이 자동으로 404 페이지를 보여줍니다.
->where('category_id', $activeCategory->id)
해당 카테고리에 속한 글만 가져옵니다.
카테고리 글 수
목록 위에는 카테고리 버튼과 글 개수가 표시됩니다.
Category::withCount(['posts' => function ($query) {
$query->where('is_published', true);
}])
이 코드는 각 카테고리마다 공개 글 수를 posts_count로 붙여줍니다.
Blade에서는 이렇게 출력합니다.
{{ $category->posts_count }}
글 목록 Blade
글 목록 화면 파일은 다음입니다.
resources/views/posts/index.blade.php
이 화면은 두 가지 상황에서 재사용됩니다.
| 상황 | $activeCategory |
|---|---|
| 전체 글 목록 | null |
| 카테고리별 글 목록 | 선택된 Category 객체 |
카테고리가 선택되었을 때만 제목과 설명을 보여줍니다.
@if($activeCategory)
<h1>{{ $activeCategory->name }}</h1>
<p>{{ $activeCategory->description }}</p>
@endif
글 상세 흐름
방문자가 글 제목을 누르면 /posts/{slug}로 이동합니다.
public function show(string $slug)
{
$post = Post::where('slug', $slug)
->where('is_published', true)
->with(['category', 'tags'])
->firstOrFail();
return view('posts.show', compact('post'));
}
중요한 점은 where('is_published', true)입니다.
비공개 글은 URL을 직접 알아도 볼 수 없습니다.
글 상세 Blade
상세 화면 파일은 다음입니다.
resources/views/posts/show.blade.php
글 제목은 안전하게 출력합니다.
{{ $post->title }}
본문은 HTML로 저장되어 있으므로 그대로 출력합니다.
{!! $post->content !!}
{!! !!}는 HTML을 이스케이프하지 않고 그대로 출력합니다.
관리자만 글을 작성하는 현재 구조에서는 편리하지만, 일반 사용자 입력을 받게 되면 XSS 보안 처리가 필요합니다.