parsaaghayi-backend/app/Http/Controllers/Api/Blog/PostController.php

131 lines
4.2 KiB
PHP

<?php
namespace App\Http\Controllers\Api\Blog;
use App\Http\Controllers\Controller;
use App\Http\Requests\Blog\StorePostRequest;
use App\Http\Requests\Blog\UpdatePostRequest;
use App\Http\Resources\PostResource;
use App\Models\Blog\Post;
use Illuminate\Http\Request;
/**
* @OA\Tag(name="Posts", description="Blog post management")
*/
class PostController extends Controller
{
/**
* @OA\Get(
* path="/blog/posts",
* tags={"Posts"},
* summary="Paginated list of posts",
* @OA\Parameter(name="per_page", in="query", @OA\Schema(type="integer")),
* @OA\Parameter(name="category", in="query", @OA\Schema(type="string")),
* @OA\Parameter(name="tag", in="query", @OA\Schema(type="string")),
* @OA\Parameter(name="search", in="query", @OA\Schema(type="string")),
* @OA\Parameter(name="sort_field", in="query", @OA\Schema(type="string")),
* @OA\Parameter(name="sort_direction", in="query", @OA\Schema(type="string", enum={"asc","desc"})),
* @OA\Response(response=200, description="OK")
* )
*/
public function index(Request $request)
{
$filters = $request->only(['category', 'tag', 'search', 'author', 'published']);
$sortField = $request->get('sort_field', 'published_at');
$sortDirection = $request->get('sort_direction', 'desc');
$perPage = $request->get('per_page', 10);
$query = Post::with(['category', 'tags', 'author'])
->filter($filters)
->sort($sortField, $sortDirection);
$posts = $query->paginate($perPage);
return PostResource::collection($posts);
}
/**
* @OA\Get(
* path="/blog/posts/{slug}",
* tags={"Posts"},
* summary="Get a single post by slug with related posts",
* @OA\Parameter(name="slug", in="path", required=true, @OA\Schema(type="string")),
* @OA\Response(response=200, description="OK")
* )
*/
public function show($slug)
{
$post = Post::with(['category', 'tags', 'author', 'relatedPosts.category', 'relatedPosts.tags', 'relatedPosts.author'])
->where('slug', $slug)
->firstOrFail();
return response()->json([
'post' => new PostResource($post),
'related_posts' => PostResource::collection($post->relatedPosts->sortByDesc('published_at')->take(5)),
], 200);
}
/**
* @OA\Post(
* path="/blog/posts",
* tags={"Posts"},
* summary="Create a post",
* @OA\RequestBody(@OA\MediaType(mediaType="application/json")),
* @OA\Response(response=201, description="Created")
* )
*/
public function store(StorePostRequest $request)
{
$post = Post::create($request->validated());
if ($request->has('tags')) {
$post->tags()->attach($request->tags);
}
return new PostResource($post->load(['category', 'tags', 'author']));
}
/**
* @OA\Put(
* path="/blog/posts/{id}",
* tags={"Posts"},
* summary="Update a post",
* @OA\Parameter(name="id", in="path", required=true, @OA\Schema(type="integer")),
* @OA\RequestBody(@OA\MediaType(mediaType="application/json")),
* @OA\Response(response=200, description="OK")
* )
*/
public function update(UpdatePostRequest $request, $id)
{
$post = Post::findOrFail($id);
$post->update($request->validated());
if ($request->has('tags')) {
$post->tags()->sync($request->tags);
}
return new PostResource($post->load(['category', 'tags', 'author']));
}
/**
* @OA\Delete(
* path="/blog/posts/{id}",
* tags={"Posts"},
* summary="Delete a post",
* @OA\Parameter(name="id", in="path", required=true, @OA\Schema(type="integer")),
* @OA\Response(response=200, description="OK")
* )
*/
public function destroy($id)
{
$post = Post::findOrFail($id);
$post->tags()->detach();
$post->relatedPosts()->detach();
$post->delete();
return response()->json(['message' => 'Post deleted successfully'], 200);
}
}