Kotchasan Framework Documentation
ApiController Class - API Endpoint Management
ApiController Class - API Endpoint Management
คลาส ApiController เป็นคลาสพื้นฐานสำหรับการสร้าง API endpoints ในกรอบงาน Kotchasan รองรับการจัดการ routing, authentication, validation และ response แบบ RESTful API
Namespace
namespace Kotchasan;
use Kotchasan\Http\Request;
use Kotchasan\Http\Response;ภาพรวม
ApiController จัดการทุกแง่มุมของ API development รวมถึง:
- Routing - จัดเส้นทาง API ตาม pattern
module/method/action - Authentication - ตรวจสอบ Token, Bearer Token, JWT
- Authorization - ตรวจสอบ IP whitelist, CORS
- Validation - ตรวจสอบข้อมูล input ด้วยกฎที่กำหนด
- Response - สร้าง JSON response แบบมาตรฐาน
- Security - CSRF protection, signature validation
ใช้เมื่อไหร่:
- สร้าง RESTful API สำหรับ mobile apps
- สร้าง public API สำหรับ third-party integration
- สร้าง internal microservices
- สร้าง AJAX endpoints สำหรับ web applications
ข้อกำหนดของระบบ
- PHP 7.4 ขึ้นไป
- Kotchasan Framework
- Database connection (สำหรับ authentication)
Class Hierarchy
Kotchasan\KBase
└── Kotchasan\ApiController (extends KBase)การตั้งค่า (Configuration)
ต้องกำหนดค่าใน settings/config.php:
return array(
// API Token list สำหรับ validateToken()
'api_tokens' => [
'your-secret-token-1',
'your-secret-token-2'
],
// IP Whitelist สำหรับ API access
'api_ips' => [
'0.0.0.0', // อนุญาตทุก IP (development)
// '192.168.1.10', // production - specific IPs only
],
// CORS configuration
'api_cors' => '*', // หรือ 'https://your-domain.com'
// API Secret สำหรับ signature validation
'api_secret' => 'your-api-secret-key',
// JWT Secret สำหรับ JWT authentication
'jwt_secret' => 'your-jwt-secret-key'
);Public Methods
index()
Router หลักสำหรับ API endpoints จัดการ CORS, authentication, และ routing
public function index(Request $request): voidParameters:
$request(Request, required) - HTTP request object
Returns: void (ส่ง response แล้ว exit)
Routing Pattern:
/api/module/method/action
↓ ↓ ↓
Module Method Action
Example:
/api/v1/auth/login → V1\Auth\Controller::login($request)
/api/v1/user/profile → V1\User\Controller::profile($request)Example:
namespace Kotchasan;
use Kotchasan\Http\Request;
class ApiController extends \Kotchasan\KBase
{
public function index(Request $request)
{
// Framework handles routing automatically
// This method is called by index.php for /api/* routes
}
}Static Validation Methods
validateToken()
ตรวจสอบ API token กับรายการ tokens ใน config
public static function validateToken($token): boolParameters:
$token(string, required) - Token ที่ต้องการตรวจสอบ
Returns: bool - true ถ้าถูกต้อง
Throws: ApiException - ไม่พบ token หรือไม่ถูกต้อง (401)
Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class MyApiController extends ApiController
{
public function index(Request $request)
{
try {
$token = $request->post('token')->toString();
self::validateToken($token);
// Token valid - proceed
return $this->successResponse(['message' => 'Authenticated']);
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse($e->getMessage(), $e->getCode());
}
}
}validateTokenBearer()
ตรวจสอบ Bearer token จาก Authorization header
public static function validateTokenBearer(Request $request): boolParameters:
$request(Request, required) - HTTP request object
Returns: bool - true ถ้าถูกต้อง
Throws: ApiException - ไม่พบ header หรือ token ไม่ถูกต้อง (401)
Expected Header:
Authorization: Bearer your-token-hereExample:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class SecureApi extends ApiController
{
public function index(Request $request)
{
try {
// ตรวจสอบ Bearer token
self::validateTokenBearer($request);
// Authenticated - proceed with API logic
return $this->successResponse([
'user' => 'authenticated',
'data' => []
]);
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse($e->getMessage(), 401);
}
}
}validateSign()
ตรวจสอบ signature ของ request parameters
public static function validateSign($params): boolParameters:
$params(array, required) - Parameters รวมทั้ง 'sign' key
Returns: bool - true ถ้า signature ถูกต้อง
Throws: ApiException - signature ไม่ถูกต้อง (401)
Example:
use Kotchasan\ApiController;
use Kotchasan\Password;
// Client-side: สร้าง signature
$params = [
'user_id' => 123,
'action' => 'delete',
'timestamp' => time()
];
// เรียงลำดับ keys และสร้าง signature
$params['sign'] = Password::generateSign($params, 'api-secret-key');
// Server-side: ตรวจสอบ signature
class SignedApi extends ApiController
{
public function index(Request $request)
{
$params = $request->getQueryParams();
try {
self::validateSign($params);
// Signature valid - safe to proceed
return $this->successResponse(['verified' => true]);
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse('Invalid signature', 401);
}
}
}validateMethod()
ตรวจสอบ HTTP method ของ request
public static function validateMethod(Request $request, $method): boolParameters:
$request(Request, required) - HTTP request object$method(string, required) - Expected HTTP method: 'GET', 'POST', 'PUT', 'DELETE', 'OPTIONS'
Returns: bool - true ถ้า method ตรงกัน
Throws: ApiException - method ไม่ตรงกัน (405)
Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class UserApi extends ApiController
{
public function create(Request $request)
{
try {
// ต้องเป็น POST เท่านั้น
self::validateMethod($request, 'POST');
// Process creation
return $this->successResponse(null, 'Created', 201);
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse('Method not allowed', 405);
}
}
public function update(Request $request)
{
try {
// ต้องเป็น PUT เท่านั้น
self::validateMethod($request, 'PUT');
// Process update
return $this->successResponse(null, 'Updated');
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse('Method not allowed', 405);
}
}
}validateIpAddress()
ตรวจสอบ IP address ของ client กับ whitelist
public static function validateIpAddress(Request $request): boolParameters:
$request(Request, required) - HTTP request object
Returns: bool - true ถ้า IP ได้รับอนุญาต
Throws: ApiException - IP ไม่ได้รับอนุญาต (403)
Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class RestrictedApi extends ApiController
{
public function index(Request $request)
{
try {
// ตรวจสอบ IP whitelist
self::validateIpAddress($request);
// IP allowed - proceed
return $this->successResponse(['access' => 'granted']);
} catch (\Kotchasan\ApiException $e) {
// Log security event
Logger::security('BLOCKED_IP', [
'ip' => $request->getClientIp(),
'endpoint' => $request->getUri()
]);
return $this->errorResponse('Access denied', 403);
}
}
}Protected Helper Methods
Authentication Methods
authenticateRequest()
ตรวจสอบ authentication และคืนค่า user object
protected function authenticateRequest(Request $request): object|nullParameters:
$request(Request, required) - HTTP request object
Returns: object|null - User object ถ้า authenticated, null ถ้าไม่
Authentication Methods (ตามลำดับ):
- Opaque token จาก database (
user.tokencolumn) - JWT token (ถ้ามี
jwt_secretconfig) - Cookie token (
auth_token)
Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class ProfileApi extends ApiController
{
public function index(Request $request)
{
// ตรวจสอบ user authentication
$user = $this->authenticateRequest($request);
if (!$user) {
return $this->errorResponse('Unauthorized', 401);
}
// Return user profile
return $this->successResponse([
'id' => $user->id,
'name' => $user->name,
'email' => $user->email
]);
}
}getAccessToken()
ดึง access token จาก request (header, cookie, หรือ parameter)
protected function getAccessToken(Request $request): mixedParameters:
$request(Request, required) - HTTP request object
Returns: string|null - Access token หรือ null
Token Sources (ตามลำดับ):
Authorization: Bearer <token>headerX-Access-Token: <token>headeraccess_tokenPOST parameterauth_tokencookie
Example:
use Kotchasan\ApiController;
class TokenApi extends ApiController
{
public function verify(Request $request)
{
$token = $this->getAccessToken($request);
if (!$token) {
return $this->errorResponse('No token provided', 401);
}
// Verify token...
return $this->successResponse([
'token' => substr($token, 0, 10) . '...',
'valid' => true
]);
}
}Validation Methods
validate()
ตรวจสอบข้อมูล request ตามกฎที่กำหนด
protected function validate(Request $request, array $rules): arrayParameters:
$request(Request, required) - HTTP request object$rules(array, required) - Validation rules
Returns: array - [isValid (bool), errors (array)]
Validation Rules:
required- ค่าห้ามว่างemail- รูปแบบอีเมลnumeric- ตัวเลขinteger- จำนวนเต็มmin:x- ค่าต่ำสุด (number) หรือความยาวต่ำสุด (string)max:x- ค่าสูงสุด (number) หรือความยาวสูงสุด (string)in:a,b,c- ค่าต้องอยู่ในลิสต์date- วันที่ที่ถูกต้องjson- JSON string ที่ถูกต้องsame:field- ต้องเหมือนกับฟิลด์อื่นregex:pattern- ตรงกับ regex patternurl- URL ที่ถูกต้องip- IP address ที่ถูกต้องarray- ต้องเป็น arrayboolean- ต้องเป็น boolean
Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class RegisterApi extends ApiController
{
public function index(Request $request)
{
$rules = [
'email' => 'required|email',
'password' => 'required|min:8',
'age' => 'integer|min:18|max:100',
'role' => 'in:user,admin,moderator',
'website' => 'url',
'terms' => 'required|boolean'
];
list($isValid, $errors) = $this->validate($request, $rules);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
// Validation passed - create user
return $this->successResponse(null, 'Registration successful', 201);
}
}validateCsrfToken()
ตรวจสอบ CSRF token จาก header
protected function validateCsrfToken(Request $request): boolParameters:
$request(Request, required) - HTTP request object
Returns: bool - true ถ้า token ถูกต้อง
Throws: ApiException - token ไม่ถูกต้องหรือไม่มี (403)
Expected Header:
X-CSRF-TOKEN: <64-char-hex-token>Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class FormApi extends ApiController
{
public function submit(Request $request)
{
try {
// ตรวจสอบ CSRF token
$this->validateCsrfToken($request);
// Process form submission
return $this->successResponse(null, 'Form submitted');
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse('CSRF validation failed', 403);
}
}
}Filtering Methods
filter()
กรองและ sanitize ข้อมูล input
protected function filter(array $data, array $filters): arrayParameters:
$data(array, required) - ข้อมูลที่ต้องการกรอง$filters(array, required) - Filters ที่ต้องการใช้
Returns: array - ข้อมูลที่ผ่านการกรองแล้ว
Available Filters:
int- แปลงเป็น integerfloat- แปลงเป็น floatbool- แปลงเป็น booleanstring- แปลงเป็น stringemail- sanitize emailurl- sanitize URLstrip_tags- ลบ HTML tagstrim- ตัด whitespace- Custom callable function
Example:
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class ProductApi extends ApiController
{
public function create(Request $request)
{
$data = $request->getParsedBody();
// กรองข้อมูล
$filtered = $this->filter($data, [
'name' => 'trim',
'price' => 'float',
'quantity' => 'int',
'description' => 'strip_tags',
'url' => 'url',
'email' => 'email',
'active' => 'bool'
]);
// บันทึกข้อมูลที่กรองแล้ว
return $this->successResponse($filtered);
}
}getRequestData()
ดึงข้อมูลจาก request ตาม HTTP method
protected function getRequestData(Request $request): arrayParameters:
$request(Request, required) - HTTP request object
Returns: array - Request data
Behavior:
- GET → Query parameters
- POST/PUT/PATCH/DELETE → Parsed body
Example:
use Kotchasan\ApiController;
class DataApi extends ApiController
{
public function process(Request $request)
{
// อัตโนมัติดึงข้อมูลตาม method
$data = $this->getRequestData($request);
// $data จะเป็น query params (GET) หรือ body (POST/PUT/DELETE)
return $this->successResponse($data);
}
}Response Methods
successResponse()
สร้าง success response
protected function successResponse(
$data = null,
$message = 'Success',
$code = 200
): ResponseParameters:
$data(mixed, optional) - ข้อมูลที่ต้องการส่งกลับ$message(string, optional, default: 'Success') - ข้อความ$code(int, optional, default: 200) - HTTP status code
Returns: Response - JSON response object
Response Format:
{
"success": true,
"message": "Success",
"code": 200,
"data": { ... }
}Example:
return $this->successResponse(['id' => 123], 'Created', 201);
// Output:
// {
// "success": true,
// "message": "Created",
// "code": 201,
// "data": {"id": 123}
// }errorResponse()
สร้าง error response
protected function errorResponse(
$message = 'Error',
$code = 400,
$error = null
): ResponseParameters:
$message(string, optional, default: 'Error') - Error message$code(int, optional, default: 400) - HTTP status code$error(Exception, optional) - Exception object (แสดงเฉพาะ DEBUG mode)
Returns: Response - JSON error response
Response Format:
{
"success": false,
"message": "Error message",
"code": 400
}Example:
return $this->errorResponse('Invalid email', 400);
return $this->errorResponse('Unauthorized', 401);
return $this->errorResponse('Not found', 404);
return $this->errorResponse('Server error', 500);formErrorResponse()
สร้าง form validation error response
protected function formErrorResponse(
$errors,
$code = 400,
$error = null
): ResponseParameters:
$errors(array, required) - Validation errors$code(int, optional, default: 400) - HTTP status code$error(Exception, optional) - Exception object
Returns: Response - JSON response with errors
Response Format:
{
"success": false,
"code": 400,
"errors": {
"email": ["Invalid email format"],
"password": ["Password must be at least 8 characters"]
}
}Example:
$errors = [
'email' => ['The email field is required.'],
'password' => ['The password must be at least 8 characters.']
];
return $this->formErrorResponse($errors);notificationResponse()
สร้าง notification response (สำหรับแจ้งเตือนเท่านั้น)
protected function notificationResponse(string $message): ResponseParameters:
$message(string, required) - Notification message
Returns: Response - JSON response with notification action
Response Format:
{
"success": true,
"message": "Operation completed",
"code": 200,
"data": {
"actions": [
{
"type": "notification",
"message": "Operation completed"
}
]
}
}Example:
return $this->notificationResponse('Email sent successfully');redirectResponse()
สร้าง redirect response
protected function redirectResponse(
$url,
$message = '',
$code = 200,
$delay = 0,
$target = ''
): ResponseParameters:
$url(string, required) - Redirect URL$message(string, optional) - Message to display$code(int, optional, default: 200) - HTTP status code$delay(int, optional, default: 0) - Delay in milliseconds$target(string, optional) - Target window
Returns: Response - JSON response with redirect action
Response Format:
{
"success": true,
"message": "Success",
"code": 200,
"data": {
"actions": [
{
"type": "redirect",
"url": "/dashboard",
"delay": 1000
},
{
"type": "notification",
"message": "Login successful",
"level": "success"
}
]
}
}Example:
// Redirect ทันที
return $this->redirectResponse('/dashboard', 'Login successful');
// Redirect หลัง 2 วินาที
return $this->redirectResponse('/dashboard', 'Redirecting...', 200, 2000);
// Redirect ไปหน้าต่างใหม่
return $this->redirectResponse('/external', 'Opening...', 200, 0, '_blank');Utility Methods
initLanguage()
กำหนดภาษาจาก Accept-Language header
protected function initLanguage(Request $request): stringParameters:
$request(Request, required) - HTTP request object
Returns: string - Language code ('th', 'en', etc.)
Example:
public function index(Request $request)
{
$lang = $this->initLanguage($request);
// $lang = 'th' หรือ 'en' ตาม Accept-Language header
Language::setName($lang);
return $this->successResponse(['language' => $lang]);
}normalizeResult()
ปรับ result array ให้มี 'success' flag
protected function normalizeResult(?array $result): arrayParameters:
$result(array|null, required) - Result array
Returns: array - Normalized result with 'success' field
Example:
$result = ['code' => 200, 'data' => []];
$normalized = $this->normalizeResult($result);
// $normalized = ['code' => 200, 'data' => [], 'success' => true]getResponseHeaders()
สร้าง standard response headers พร้อม CSRF token
protected function getResponseHeaders(): arrayParameters: ไม่มี
Returns: array - Response headers
Headers:
Content-Type: application/json; charset=utf-8Access-Control-Allow-Origin: *Access-Control-Allow-Methods: GET, POST, PUT, DELETE, OPTIONSAccess-Control-Allow-Headers: ...X-CSRF-Token: <new-token>
Example:
$headers = $this->getResponseHeaders();
// Headers includ new CSRF token for next requestตัวอย่างการใช้งาน
Example 1: Basic API Controller
namespace V1\Products;
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class Controller extends ApiController
{
/**
* GET /api/v1/products/index
*/
public function index(Request $request)
{
// ดึงรายการสินค้าทั้งหมด
$products = \Kotchasan\DB::create()
->select()
->from('products')
->where(['active', 1])
->fetchAll();
return $this->successResponse($products);
}
/**
* POST /api/v1/products/create
*/
public function create(Request $request)
{
try {
// Validate HTTP method
self::validateMethod($request, 'POST');
// Validate input
list($isValid, $errors) = $this->validate($request, [
'name' => 'required|min:3',
'price' => 'required|numeric|min:0',
'quantity' => 'integer|min:0'
]);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
// Filter data
$data = $this->filter($this->getRequestData($request), [
'name' => 'trim',
'price' => 'float',
'quantity' => 'int',
'description' => 'strip_tags'
]);
// Insert into database
$db = \Kotchasan\DB::create();
$db->insert('products', $data)->execute();
$id = $db->lastInsertId();
return $this->successResponse(['id' => $id], 'Product created', 201);
} catch (\Exception $e) {
return $this->errorResponse('Failed to create product', 500, $e);
}
}
}Example 2: Authentication with JWT
namespace V1\Auth;
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
use Kotchasan\Jwt;
use Kotchasan\Password;
class Controller extends ApiController
{
/**
* POST /api/v1/auth/login
*/
public function login(Request $request)
{
// Validate input
list($isValid, $errors) = $this->validate($request, [
'email' => 'required|email',
'password' => 'required'
]);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
$email = $request->post('email')->toString();
$password = $request->post('password')->toString();
// Find user
$user = \Kotchasan\DB::create()
->first('user', [['email', $email]]);
if (!$user || !Password::verify($password, $user->password)) {
return $this->errorResponse('Invalid credentials', 401);
}
// Generate JWT token
$payload = [
'sub' => $user->id,
'email' => $user->email,
'exp' => time() + 3600 // 1 hour
];
$token = Jwt::encode($payload, self::$cfg->jwt_secret);
return $this->successResponse([
'token' => $token,
'expires_in' => 3600,
'user' => [
'id' => $user->id,
'email' => $user->email,
'name' => $user->name
]
]);
}
/**
* GET /api/v1/auth/profile
*/
public function profile(Request $request)
{
// Authenticate user
$user = $this->authenticateRequest($request);
if (!$user) {
return $this->errorResponse('Unauthorized', 401);
}
return $this->successResponse([
'id' => $user->id,
'email' => $user->email,
'name' => $user->name
]);
}
}Example 3: CSRF Protected API
namespace V1\Form;
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class Controller extends ApiController
{
/**
* POST /api/v1/form/submit
*/
public function submit(Request $request)
{
try {
// Validate CSRF token
$this->validateCsrfToken($request);
// Validate input
list($isValid, $errors) = $this->validate($request, [
'name' => 'required',
'email' => 'required|email',
'message' => 'required|min:10'
]);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
// Process form...
return $this->successResponse(null, 'Form submitted successfully');
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse($e->getMessage(), $e->getCode());
}
}
}Example 4: Complete CRUD API
namespace V1\Users;
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
use Kotchasan\DB;
class Controller extends ApiController
{
/**
* GET /api/v1/users/index - List all users
*/
public function index(Request $request)
{
$users = DB::create()
->select('id', 'name', 'email', 'created_at')
->from('user')
->fetchAll();
return $this->successResponse($users);
}
/**
* GET /api/v1/users/view - View single user
*/
public function view(Request $request)
{
$id = $request->get('id')->toInt();
if ($id <= 0) {
return $this->errorResponse('Invalid ID', 400);
}
$user = DB::create()->first('user', [['id', $id]]);
if (!$user) {
return $this->errorResponse('User not found', 404);
}
return $this->successResponse([
'id' => $user->id,
'name' => $user->name,
'email' => $user->email,
'created_at' => $user->created_at
]);
}
/**
* POST /api/v1/users/create - Create user
*/
public function create(Request $request)
{
self::validateMethod($request, 'POST');
list($isValid, $errors) = $this->validate($request, [
'name' => 'required|min:3',
'email' => 'required|email',
'password' => 'required|min:8'
]);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
$data = $this->filter($this->getRequestData($request), [
'name' => 'trim',
'email' => 'email'
]);
$data['password'] = \Kotchasan\Password::hash($request->post('password')->toString());
$data['created_at'] = date('Y-m-d H:i:s');
$db = DB::create();
$db->insert('user', $data)->execute();
$id = $db->lastInsertId();
return $this->successResponse(['id' => $id], 'User created', 201);
}
/**
* PUT /api/v1/users/update - Update user
*/
public function update(Request $request)
{
self::validateMethod($request, 'PUT');
$id = $request->get('id')->toInt();
if ($id <= 0) {
return $this->errorResponse('Invalid ID', 400);
}
list($isValid, $errors) = $this->validate($request, [
'name' => 'min:3',
'email' => 'email'
]);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
$data = $this->filter($this->getRequestData($request), [
'name' => 'trim',
'email' => 'email'
]);
DB::create()
->update('user')
->set($data)
->where([['id', $id]])
->execute();
return $this->successResponse(null, 'User updated');
}
/**
* DELETE /api/v1/users/delete - Delete user
*/
public function delete(Request $request)
{
self::validateMethod($request, 'DELETE');
$id = $request->get('id')->toInt();
if ($id <= 0) {
return $this->errorResponse('Invalid ID', 400);
}
DB::create()
->delete('user', [['id', $id]])
->execute();
return $this->successResponse(null, 'User deleted');
}
}Example 5: IP Whitelist & Bearer Token
namespace V1\Secure;
use Kotchasan\ApiController;
use Kotchasan\Http\Request;
class Controller extends ApiController
{
/**
* GET /api/v1/secure/data
*
* Requires:
* - IP whitelist
* - Bearer token
*/
public function data(Request $request)
{
try {
// Check IP whitelist
self::validateIpAddress($request);
// Check Bearer token
self::validateTokenBearer($request);
// Both validations passed - return sensitive data
return $this->successResponse([
'sensitive' => 'data',
'access_granted' => true
]);
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse($e->getMessage(), $e->getCode());
}
}
}Best Practices
✅ ควรทำ:
// 1. ใช้ try-catch สำหรับ validation
try {
self::validateTokenBearer($request);
self::validateMethod($request, 'POST');
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse($e->getMessage(), $e->getCode());
}
// 2. Validate และ filter ข้อมูลก่อนใช้งาน
list($isValid, $errors) = $this->validate($request, $rules);
if (!$isValid) {
return $this->formErrorResponse($errors);
}
$data = $this->filter($this->getRequestData($request), $filters);
// 3. ใช้ HTTP status codes ที่ถูกต้อง
return $this->successResponse($data, 'Created', 201); // Created
return $this->errorResponse('Not found', 404); // Not found
return $this->errorResponse('Unauthorized', 401); // Unauthorized
// 4. Log ข้อผิดพลาดสำคัญ
catch (\Exception $e) {
Logger::exception($e, 'API Error');
return $this->errorResponse('Server error', 500);
}❌ ไม่ควรทำ:
// 1. อย่าเปิดเผยข้อผิดพลาดโดยตรง (production)
return $this->errorResponse($e->getMessage()); // ไม่ดี - เปิดเผย internal error
// 2. อย่าใช้ GET สำหรับ operations ที่เปลี่ยนแปลงข้อมูล
public function delete(Request $request) {
// ไม่ดี - ควรใช้ DELETE method
}
// 3. อย่าลืม validate input
$data = $request->getParsedBody();
DB::create()->insert('table', $data); // อันตราย!
// 4. อย่า hardcode tokens
$token = '123456'; // ไม่ดี - ใช้ configCommon Mistakes
❌ ข้อผิดพลาด: ลืม validate HTTP method
// ❌ ผิด - รับทุก method
public function create(Request $request) {
// Anyone can call with GET, POST, PUT, etc.
}
// ✅ ถูก
public function create(Request $request) {
self::validateMethod($request, 'POST');
// Now only POST is allowed
}❌ ข้อผิดพลาด: ไม่ handle ApiException
// ❌ ผิด - exception จะ propagate
self::validateTokenBearer($request);
// ✅ ถูก
try {
self::validateTokenBearer($request);
} catch (\Kotchasan\ApiException $e) {
return $this->errorResponse($e->getMessage(), $e->getCode());
}❌ ข้อผิดพลาด: validate() return format ผิด
// ❌ ผิด - validate() คืนค่า array 2 ตัว
$validation = $this->validate($request, $rules);
if (!$validation) { // ผิด!
return $this->errorResponse('Invalid');
}
// ✅ ถูก - ใช้ list() destructure
list($isValid, $errors) = $this->validate($request, $rules);
if (!$isValid) {
return $this->formErrorResponse($errors);
}FAQ (คำถามที่พบบ่อย)
Q: ต่างระหว่าง validateToken() และ validateTokenBearer() อย่างไร?
A:
validateToken($token)- ตรวจสอบ token ที่ส่งมาเป็น parametervalidateTokenBearer($request)- ตรวจสอบ Bearer token จาก Authorization header
Q: จะทำ API versioning ได้อย่างไร?
A: ใช้ module pattern:
/api/v1/users/index → V1\Users\Controller::index()
/api/v2/users/index → V2\Users\Controller::index()Q: CSRF token ทำงานอย่างไร?
A:
- Client ได้ token จาก
X-CSRF-Tokenresponse header - Client ส่ง token กลับมาใน
X-CSRF-TOKENrequest header - Server validate token กับ session
Q: JWT authentication ต้องตั้งค่าอย่างไร?
A: เพิ่ม jwt_secret ใน config.php:
'jwt_secret' => 'your-secret-key-min-32-chars'Q: Validation rules มีอะไรบ้าง?
A: ดูรายการครบใน validate() method documentation
Related Classes
- Request - HTTP Request handling
- Response - HTTP Response handling
- Database - Database operations
- Jwt - JWT token handling
- Password - Password hashing and verification
💡 Tip: ใช้ ApiController เป็น base class และ extend เพื่อเพิ่ม custom functionality
⚠️ Security: อย่าลืม validate input ทุกครั้งก่อนใช้งาน และ sanitiz ข้อมูลก่อนบันทึกลง database
📝 Note: Response methods ทั้งหมดคืนค่า Response object พร้อม CORS headers และ CSRF token อัตโนมัติ