پرش به مطلب اصلی

لایه ترنسفورمرها با league/fractal

در این سند

مقدمه

در توسعه Laravel، لایه ترنسفورمرها نقش مهمی در شکل‌دهی داده برای پاسخ‌های API ایفا می‌کند. پکیج league/fractal به طور گسترده‌ای برای این منظور پذیرفته شده است و مجموعه ابزاری انعطاف‌پذیر و قدرتمند برای تبدیل داده‌های خام به یک قالب سازگار و ساختاریافته مناسب برای مصرف‌کنندگان API ارائه می‌دهد.

ترنسفورمرها چیستند؟

ترنسفورمرها کلاس‌هایی هستند که ساختارهای داده داخلی شما را به پاسخ‌های API استاندارد تبدیل می‌کنند و سازگاری و قالب‌بندی مناسب را در سراسر API شما تضمین می‌کنند.

چرا ترنسفورمرها؟

ترنسفورمرها به جداسازی فرآیند بازیابی داده از قالب‌بندی پاسخ API کمک می‌کنند. با استفاده از ترنسفورمرها، می‌توانید اطمینان حاصل کنید که داده‌های برگردانده شده توسط API شما به روشی استاندارد ارائه می‌شوند، که سازگاری را ترویج می‌کند و نگهداری کد شما را ساده‌تر می‌سازد.

نصب league/fractal

برای شروع کار با league/fractal، باید پکیج را با استفاده از Composer نصب کنید:

ترمینال
composer require league/fractal

پس از نصب، می‌توانید ترنسفورمرها را برای تعریف نحوه نمایش داده‌های خود در پاسخ‌های API ایجاد کنید.

راهنمای پیاده‌سازی

ایجاد ترنسفورمرها

ترنسفورمرها کلاس‌هایی هستند که مسئول تبدیل داده‌های خام به یک ساختار خاص برای پاسخ‌های API هستند. در Laravel، ترنسفورمرها اغلب از کلاس League\Fractal\TransformerAbstract ارث‌بری می‌کنند.

ترنسفورمر پایه

app/Transformers/UserTransformer.php
<?php

namespace App\Transformers;

use App\Models\User;
use League\Fractal\TransformerAbstract;

class UserTransformer extends TransformerAbstract
{
public function transform(User $user)
{
return [
'id' => (int) $user->id,
'name' => $user->name,
'email' => $user->email,
'created_at' => $user->created_at->toIso8601String(),
'updated_at' => $user->updated_at->toIso8601String(),
];
}
}

ترنسفورمر با روابط

app/Transformers/PostTransformer.php
<?php

namespace App\Transformers;

use App\Models\Post;
use League\Fractal\TransformerAbstract;

class PostTransformer extends TransformerAbstract
{
protected $availableIncludes = [
'author', 'comments'
];

public function transform(Post $post)
{
return [
'id' => (int) $post->id,
'title' => $post->title,
'content' => $post->content,
'slug' => $post->slug,
'published' => (bool) $post->published,
'created_at' => $post->created_at->toIso8601String(),
'updated_at' => $post->updated_at->toIso8601String(),
];
}

public function includeAuthor(Post $post)
{
return $this->item($post->author, new UserTransformer());
}

public function includeComments(Post $post)
{
return $this->collection($post->comments, new CommentTransformer());
}
}

ویژگی‌های پیشرفته

صفحه‌بندی

Fractal پشتیبانی از نتایج صفحه‌بندی شده را ارائه می‌دهد:

پاسخ صفحه‌بندی شده
<?php

namespace App\Http\Controllers;

use App\Models\Post;
use App\Transformers\PostTransformer;
use Illuminate\Http\Request;

class PostController extends Controller
{
public function index(Request $request)
{
$paginator = Post::paginate(10);

$posts = $paginator->getCollection();

$response = fractal()
->collection($posts)
->transformWith(new PostTransformer())
->paginateWith(new \League\Fractal\Pagination\IlluminatePaginatorAdapter($paginator))
->toArray();

return response()->json($response);
}
}

سریالایزرهای سفارشی

Fractal به شما امکان می‌دهد ساختار پاسخ‌های API خود را با استفاده از سریالایزرها سفارشی کنید:

سریالایزر سفارشی
<?php

namespace App\Serializers;

use League\Fractal\Serializer\ArraySerializer;

class CustomSerializer extends ArraySerializer
{
public function collection($resourceKey, array $data)
{
return $resourceKey ? [$resourceKey => $data] : $data;
}

public function item($resourceKey, array $data)
{
return $resourceKey ? [$resourceKey => $data] : $data;
}
}
استفاده از سریالایزر سفارشی
return fractal()
->item($user)
->transformWith(new UserTransformer())
->serializeWith(new CustomSerializer())
->toArray();

ویژگی‌های شرطی

می‌توانید ویژگی‌ها را به صورت شرطی در ترنسفورمرهای خود شامل کنید:

ویژگی‌های شرطی
<?php

namespace App\Transformers;

use App\Models\User;
use League\Fractal\TransformerAbstract;

class UserTransformer extends TransformerAbstract
{
public function transform(User $user)
{
$data = [
'id' => (int) $user->id,
'name' => $user->name,
'email' => $user->email,
'created_at' => $user->created_at->toIso8601String(),
];

// فقط برای کاربران مدیر وضعیت مدیر را شامل کنید
if ($user->isAdmin()) {
$data['is_admin'] = true;
}

// فقط اگر کاربر احراز هویت شده در حال مشاهده پروفایل خود است، داده‌های خصوصی را شامل کنید
if (auth()->id() === $user->id) {
$data['phone'] = $user->phone;
$data['address'] = $user->address;
}

return $data;
}
}

بهترین شیوه‌ها

حفظ سازگاری

  • از قالب یکسان برای تمام پاسخ‌های API استفاده کنید
  • قالب‌های تاریخ را سازگار نگه دارید (ISO 8601 توصیه می‌شود)
  • از قراردادهای نام‌گذاری سازگار استفاده کنید (camelCase یا snake_case)
  • همیشه IDها و مقادیر بولی را به انواع مناسب خود تبدیل کنید
قالب‌بندی سازگار
return [
'id' => (int) $model->id,
'is_active' => (bool) $model->is_active,
'created_at' => $model->created_at->toIso8601String(),
];

نتیجه‌گیری

پیاده‌سازی لایه ترنسفورمرها با استفاده از league/fractal در Laravel به یک کد تمیزتر و قابل نگهداری‌تر کمک می‌کند. با جداسازی دغدغه‌های تبدیل داده از بقیه منطق برنامه خود، اطمینان حاصل می‌کنید که پاسخ‌های API شما سازگار و به راحتی قابل انطباق با تغییرات آینده هستند.

به یاد داشته باشید که ویژگی‌های پیشرفته league/fractal را برای مدیریت سناریوهای پیچیده‌تر در توسعه API خود، مانند includeها، صفحه‌بندی و سریالایزرهای سفارشی بررسی کنید.