# 🌐 Example: API Integration A comprehensive real-world example showing how to use Laravel Arc DTOs in modern API controllers with behavioral traits and validation. ## Complete API Controller Example This example is based on the actual code from `examples/modern-api-controller-example.php`: ```php when($request->search, function ($query, $search) { $query->where('name', 'like', "%{$search}%") ->orWhere('email', 'like', "%{$search}%"); }) ->when($request->status, function ($query, $status) { $query->where('status', $status); }) ->paginate($request->per_page ?? 15); // Transform to DTOs with behavioral traits $userDtos = $users->getCollection()->map(function ($user) { return UserDTO::fromModel($user); }); return response()->json([ 'data' => $userDtos, 'pagination' => [ 'current_page' => $users->currentPage(), 'last_page' => $users->lastPage(), 'per_page' => $users->perPage(), 'total' => $users->total(), ], ]); } /** * Store a newly created user with comprehensive validation */ public function store(Request $request): JsonResponse { // Use ValidatesData trait for validation if (UserDTO::fails($request->all())) { return response()->json([ 'message' => 'Validation failed', 'errors' => UserDTO::validator($request->all())->errors(), ], 422); } // Create user with validated data $validated = UserDTO::validate($request->all()); $user = User::create($validated); // Convert to DTO and demonstrate behavioral traits $userDto = UserDTO::fromModel($user); // Use HasTagging trait if available if (method_exists($userDto, 'addTag')) { $userDto = $userDto->addTag('new_user'); } // Use HasAuditing trait if available if (method_exists($userDto, 'setCreator')) { $userDto = $userDto->setCreator(auth()->id()); } return response()->json([ 'message' => 'User created successfully', 'user' => $userDto->toArray(), ], 201); } /** * Display the specified user */ public function show(User $user): JsonResponse { $userDto = UserDTO::fromModel($user); return response()->json([ 'user' => $userDto->toArray(), ]); } /** * Update the specified user */ public function update(Request $request, User $user): JsonResponse { // Validate with DTO $validated = UserDTO::validate($request->all()); // Update model $user->update($validated); // Convert to DTO $userDto = UserDTO::fromModel($user->fresh()); // Use HasTimestamps trait if (method_exists($userDto, 'touch')) { $userDto->touch(); // Updates updated_at } return response()->json([ 'message' => 'User updated successfully', 'user' => $userDto->toArray(), ]); } /** * Remove the specified user (soft delete) */ public function destroy(User $user): JsonResponse { $userDto = UserDTO::fromModel($user); // Soft delete the user $user->delete(); return response()->json([ 'message' => 'User deleted successfully', 'user' => $userDto->toArray(), ]); } } ``` ## YAML Definition for API Example The corresponding YAML definition (`examples/user.yaml`): ```yaml # API User DTO with behavioral traits header: dto: UserDTO table: users model: App\Models\User namespace: App\DTO traits: - HasUuid - HasTimestamps - ValidatesData - ConvertsData use: - App\DTO\ProfileDTO fields: name: type: string required: true validation: [required, string, min:2, max:100] transformers: [trim, title_case] email: type: string required: true validation: [required, email, unique:users] transformers: [trim, lowercase] email_verified_at: type: datetime required: false validation: [nullable, date] status: type: string required: false validation: [nullable, in:active,inactive,pending] default: "active" # Profile as nested DTO profile: type: dto dto: ProfileDTO required: false relations: posts: type: hasMany target: App\Models\Post roles: type: belongsToMany target: App\Models\Role ``` ## Key Benefits in API Controllers ### 1. Automatic Validation ```php // Instead of manual validation rules $request->validate([ 'name' => 'required|string|min:2|max:100', 'email' => 'required|email|unique:users', ]); // Use DTO validation if (UserDTO::fails($request->all())) { return response()->json([ 'errors' => UserDTO::validator($request->all())->errors(), ], 422); } ``` ### 2. Consistent Data Transformation ```php // DTOs ensure consistent output format return response()->json([ 'user' => $userDto->toArray(), // Always consistent structure ]); ``` ### 3. Type Safety ```php // Type-safe property access $userName = $userDto->name; // string $userEmail = $userDto->email; // string $verified = $userDto->email_verified_at; // ?DateTime ``` ### 4. Behavioral Traits Usage ```php // Use behavioral traits methods if (method_exists($userDto, 'wasRecentlyCreated')) { $isNew = $userDto->wasRecentlyCreated(); // boolean } if (method_exists($userDto, 'touch')) { $userDto->touch(); // Updates timestamp } ``` ## Advanced API Patterns ### Bulk Operations ```php public function bulkStore(Request $request): JsonResponse { $users = collect($request->users)->map(function ($userData) { // Validate each user $validated = UserDTO::validate($userData); $user = User::create($validated); return UserDTO::fromModel($user); }); return response()->json([ 'message' => 'Users created successfully', 'users' => $users->toArray(), 'count' => $users->count(), ], 201); } ``` ### Search and Filtering ```php public function search(Request $request): JsonResponse { $users = User::query() ->when($request->name, fn($q, $name) => $q->where('name', 'like', "%{$name}%")) ->when($request->email, fn($q, $email) => $q->where('email', 'like', "%{$email}%")) ->when($request->status, fn($q, $status) => $q->where('status', $status)) ->get(); $userDtos = $users->map(fn($user) => UserDTO::fromModel($user)); return response()->json([ 'users' => $userDtos->toArray(), 'total' => $userDtos->count(), ]); } ``` ### Export Functionality ```php public function export(Request $request): JsonResponse { $users = User::all(); $userDtos = $users->map(fn($user) => UserDTO::fromModel($user)); // Use DTO export capabilities $format = $request->format ?? 'json'; switch ($format) { case 'csv': $content = $userDtos->toCsv(); break; case 'xml': $content = $userDtos->toXml(); break; default: $content = $userDtos->toJson(); } return response($content) ->header('Content-Type', "application/{$format}") ->header('Content-Disposition', "attachment; filename=users.{$format}"); } ``` ## Routes Configuration ```php // routes/api.php Route::apiResource('users', UserController::class); Route::post('users/bulk', [UserController::class, 'bulkStore']); Route::get('users/search', [UserController::class, 'search']); Route::get('users/export', [UserController::class, 'export']); ``` ## Testing the API ### Using the API ```bash # Create user curl -X POST /api/users \ -H "Content-Type: application/json" \ -d '{ "name": "John Doe", "email": "john@example.com", "status": "active" }' # Get user curl -X GET /api/users/1 # Search users curl -X GET "/api/users/search?name=John&status=active" # Export users as CSV curl -X GET "/api/users/export?format=csv" ``` ### Expected Response Format ```json { "user": { "id": "123e4567-e89b-12d3-a456-426614174000", "name": "John Doe", "email": "john@example.com", "email_verified_at": null, "status": "active", "created_at": "2024-01-15T10:30:00Z", "updated_at": "2024-01-15T10:30:00Z", "profile": null } } ``` ## Error Handling ```php public function store(Request $request): JsonResponse { try { // Validate with DTO $validated = UserDTO::validate($request->all()); // Create user $user = User::create($validated); $userDto = UserDTO::fromModel($user); return response()->json([ 'message' => 'User created successfully', 'user' => $userDto->toArray(), ], 201); } catch (ValidationException $e) { return response()->json([ 'message' => 'Validation failed', 'errors' => $e->errors(), ], 422); } catch (\Exception $e) { return response()->json([ 'message' => 'Server error', 'error' => $e->getMessage(), ], 500); } } ``` ## What's Next? This example shows Laravel Arc in a real API context. Explore more: - **[Behavioral Traits](Behavioral-Traits.md)** - Learn about HasTimestamps, HasUuid, etc. - **[Collections](Collections.md)** - Handle arrays of DTOs - **[Field Transformers](Field-Transformers.md)** - Automatic data cleaning - **[Generated DTO Structure](Generated-DTO-Structure.md)** - Understanding the generated code --- *This real-world example demonstrates how Laravel Arc DTOs provide type safety, validation, and consistency in modern API development.* 🌐