JSON Response
Miko's JsonResponse class provides standardized JSON API responses with proper HTTP status codes.
Response Methods
| Method | Status | Description |
|---|---|---|
success($data) | 200 | Successful response |
created($data) | 201 | Resource created |
noContent() | 204 | No content (delete) |
error($message, $code) | 4xx/5xx | Error response |
notFound($message) | 404 | Resource not found |
unauthorized($message) | 401 | Authentication required |
forbidden($message) | 403 | Access denied |
validationError($errors) | 422 | Validation failed |
paginated($items, ...) | 200 | Paginated response |
Success Responses
Basic Success
use Miko\Core\Http\JsonResponse;
// Simple success
JsonResponse::success(['message' => 'Operation completed']);
// Output:
// {
// "success": true,
// "data": {
// "message": "Operation completed"
// }
// }
Return Data
// Return user data
$user = User::find(1);
JsonResponse::success($user->toArray());
// Return collection
$users = User::where('IsActive', true)->get();
JsonResponse::success(array_map(fn($u) => $u->toArray(), $users));
Created (201)
$user = User::create([
'Name' => 'John Doe',
'Email' => 'john@example.com'
]);
JsonResponse::created($user->only('Id', 'Name', 'Email'));
// Output:
// HTTP 201 Created
// {
// "success": true,
// "data": {
// "Id": 1,
// "Name": "John Doe",
// "Email": "john@example.com"
// }
// }
No Content (204)
$user = User::find(1);
$user->delete();
JsonResponse::noContent();
// Output:
// HTTP 204 No Content
// (empty body)
Error Responses
Generic Error
JsonResponse::error('Something went wrong', 500);
// Output:
// HTTP 500 Internal Server Error
// {
// "success": false,
// "error": {
// "message": "Something went wrong",
// "code": 500
// }
// }
Not Found (404)
$user = User::find($id);
if (!$user) {
JsonResponse::notFound('User not found');
return;
}
// Output:
// HTTP 404 Not Found
// {
// "success": false,
// "error": {
// "message": "User not found",
// "code": 404
// }
// }
Unauthorized (401)
$token = $_SERVER['HTTP_AUTHORIZATION'] ?? '';
if (!$token) {
JsonResponse::unauthorized('Authentication required');
return;
}
// Output:
// HTTP 401 Unauthorized
// {
// "success": false,
// "error": {
// "message": "Authentication required",
// "code": 401
// }
// }
Forbidden (403)
if ($user->Role !== 'admin') {
JsonResponse::forbidden('Admin access required');
return;
}
Validation Error (422)
$validator = new Validator($data);
$validator->validate([
'email' => 'required|email',
'password' => 'required|min:8'
]);
if ($validator->fails()) {
JsonResponse::validationError($validator->errors());
return;
}
// Output:
// HTTP 422 Unprocessable Entity
// {
// "success": false,
// "error": {
// "message": "Validation failed",
// "code": 422,
// "errors": {
// "email": ["The email field is required"],
// "password": ["Password must be at least 8 characters"]
// }
// }
// }
Paginated Response
$page = (int)($_GET['page'] ?? 1);
$perPage = (int)($_GET['per_page'] ?? 20);
$result = User::where('IsActive', true)
->orderBy('Name')
->paginate($perPage, $page);
JsonResponse::paginated(
$result['data'],
[
'current_page' => $result['current_page'],
'last_page' => $result['last_page'],
'total' => $result['total'],
'per_page' => $result['per_page'],
]
);
// Output:
// {
// "success": true,
// "data": [...],
// "pagination": {
// "current_page": 1,
// "total_pages": 5,
// "total_count": 100,
// "per_page": 20,
// "has_next": true,
// "has_prev": false
// }
// }
Custom Response
JsonResponse::send([
'success' => true,
'data' => $data,
'meta' => [
'version' => '1.0',
'timestamp' => time()
]
], 200);
API Controller Example
class UserController
{
public function index(): void
{
$users = User::where('IsActive', true)->get();
JsonResponse::success(array_map(fn($u) => $u->only('Id', 'Name', 'Email'), $users));
}
public function show(int $id): void
{
$user = User::find($id);
if (!$user) {
JsonResponse::notFound('User not found');
return;
}
JsonResponse::success($user->only('Id', 'Name', 'Email', 'Role'));
}
public function store(): void
{
$data = json_decode(file_get_contents('php://input'), true);
$validator = new Validator($data);
$validator->validate([
'name' => 'required|string|max:100',
'email' => 'required|email'
]);
if ($validator->fails()) {
JsonResponse::validationError($validator->errors());
return;
}
$user = User::create($data);
JsonResponse::created($user->only('Id', 'Name', 'Email'));
}
public function update(int $id): void
{
$user = User::find($id);
if (!$user) {
JsonResponse::notFound('User not found');
return;
}
$data = json_decode(file_get_contents('php://input'), true);
$user->fill($data)->save();
JsonResponse::success($user->only('Id', 'Name', 'Email'));
}
public function destroy(int $id): void
{
$user = User::find($id);
if (!$user) {
JsonResponse::notFound('User not found');
return;
}
$user->delete();
JsonResponse::noContent();
}
}
Response Headers
JsonResponse automatically sets:
Content-Type: application/json; charset=utf-8
Additional headers can be set before calling response methods:
header('X-Request-Id: ' . uniqid());
header('X-Response-Time: ' . $duration . 'ms');
JsonResponse::success($data);