Thứ Hai, 31 tháng 8, 2026

Authorization là gì? (Đăng nhập rồi vẫn chưa chắc được phép làm mọi thứ!)

Bạn mua vé máy bay hạng phổ thông. Khi lên máy bay, bạn "vô tư" ngồi vào chỗ hạng thương gia, tiếp viên tới và nhẹ nhàng "Xin lỗi, vé của anh ngồi ở phía dưới kia".

Ở bài 68.

Chúng ta đã gặp hai anh em rất dễ nhầm:

Authentication

→ "Anh là ai?"

và:

Authorization

→ "Anh được phép làm gì?"

😄

Hôm nay chúng ta tập trung vào anh thứ hai:

Authorization

Và đây là một câu chuyện rất đời thường:

Bạn đã đăng nhập thành công.

Bạn có tài khoản.

Bạn có mật khẩu đúng.

Server biết chính xác:

"Đây là user Nguyễn Văn A."

Authentication:

Nhưng bạn bấm:

Xóa tài khoản của người khác.

Server:

"Khoan..."

😐

"Anh là Nguyễn Văn A thì đúng."

"Nhưng..."

"Anh có quyền xóa người khác đâu?"

🤣

Và thế là:

403 Forbidden

Đây chính là Authorization.


Authorization là gì?

Authorization là quá trình xác định người dùng hoặc hệ thống đã được xác thực có được phép thực hiện một hành động hoặc truy cập một tài nguyên cụ thể hay không.

Nói đơn giản:

Authentication = Anh là ai?

Authorization = Anh được phép làm gì?

Ví dụ:

User A → được xem sản phẩm
User A → được sửa sản phẩm của mình
User A → không được xóa user khác

Admin → được xem
Admin → được sửa
Admin → được xóa
Admin → quản lý user

Authorization thường được triển khai bằng Role, Permission, hoặc các cơ chế kiểm soát truy cập khác.



Ví dụ đời thường nhất 🏢

Hãy tưởng tượng bạn làm việc trong một công ty.

Bạn bước vào cửa.

Bảo vệ kiểm tra thẻ.

"Đúng là nhân viên công ty."

Bạn được vào.

Đó là:

Authentication.


Nhưng bạn đi lên tầng 20.

Thấy cửa:

PHÒNG SERVER

Bạn quẹt thẻ.

🚫

Cửa không mở.

Bạn hỏi:

"Tôi là nhân viên mà?"

Bảo vệ:

"Đúng."

"Nhưng anh không có quyền vào phòng Server."

🤣

Đó là:

Authorization.


Một câu nhớ cả đời 😎

Nếu bạn chỉ muốn nhớ một câu:

Authentication cho bạn vào tòa nhà. Authorization quyết định bạn được vào phòng nào.

Quá dễ.


Authentication vs Authorization


AuthenticationAuthorization
Câu hỏiAnh là ai?Anh được làm gì?
Kiểm traDanh tínhQuyền
Thường xảy raTrướcSau Authentication
Ví dụLoginXóa user
Thành côngBiết user là aiCho phép hành động
Thất bại thường gặp401403

Ví dụ:

Bạn đăng nhập:

email = an@email.com
password = đúng

Authentication:

Server biết:

user_id = 25

Nhưng bạn muốn:

DELETE /api/users/30

Server phải hỏi tiếp:

"User 25 có quyền xóa User 30 không?"

Nếu không:

403 Forbidden

😎


401 vs 403

Đây là một trong những thứ rất đáng nhớ khi làm API.

401 Unauthorized

Hiểu đơn giản:

"Tôi chưa xác thực được anh."

Ví dụ:

GET /api/profile

Không có token.

Hoặc token không hợp lệ.

Server:

401 Unauthorized

403 Forbidden

Hiểu đơn giản:

"Tôi biết anh là ai. Nhưng anh không được phép làm việc này."

Ví dụ:

DELETE /api/users/30

Bạn đã đăng nhập.

Token hợp lệ.

Server biết:

User ID = 25

Nhưng user 25 không có quyền Admin.

Server:

403 Forbidden

"Chua thêm" 😆

Authentication giống như:

Bảo vệ hỏi CMND/ID.

Bạn đưa ra.

Bảo vệ:

"OK, đúng là anh."

Authorization giống như:

Bạn nói:

"Cho tôi vào két sắt."

Bảo vệ:

"Anh là ai?"

"Nhân viên."

"OK."

"Nhưng anh có chìa khóa két sắt không?"

🤣

Biết anh là ai không đồng nghĩa với việc anh được phép làm mọi thứ.

Đây là nguyên tắc cực kỳ quan trọng của bảo mật.


Role là gì? 👨‍💼

Một cách rất phổ biến để phân quyền là:

Role

tức là:

Vai trò.

Ví dụ website có:

Admin
Editor
Author
User
Guest

Mỗi Role có quyền khác nhau.


Ví dụ đơn giản

Website blog.

Có:

Admin 👑

Có thể:

Tạo bài
Sửa bài
Xóa bài
Quản lý user

Editor ✏️

Có thể:

Tạo bài
Sửa bài
Duyệt bài

Nhưng:

Không quản lý user

Author 📝

Có thể:

Viết bài
Sửa bài của mình

User 👤

Có thể:

Đọc bài
Bình luận

Role không phải Permission

Đây cũng là chỗ dễ nhầm.

Role

→ Vai trò.

Permission

→ Quyền cụ thể.

Ví dụ:

Role:
Admin

có thể có:

Permission:
create_post
edit_post
delete_post
manage_users

Còn:

Role:
Author

có thể có:

create_post
edit_own_post

Nhìn vậy sẽ dễ hiểu hơn:

User
 ↓
Role
 ↓
Permissions
 ↓
Actions

Ví dụ ngoài đời 🏥

Hãy tưởng tượng một bệnh viện.

Có:

Bác sĩ
Y tá
Lễ tân
Quản trị viên

Lễ tân có thể:

Tạo hồ sơ bệnh nhân
Xem thông tin cơ bản

Nhưng không nhất thiết được:

Xem mọi dữ liệu chuyên môn
Sửa kết quả xét nghiệm

Bác sĩ có quyền khác.

Quản trị viên có quyền khác.

😄

Không phải cứ:

"Tôi làm trong bệnh viện."

thì:

"Tôi được xem tất cả."

Đó chính là Authorization.


Authorization trong API 🌐

Bây giờ quay lại REST API.

Giả sử:

GET /api/users

Server nhận request.

Token cho biết:

user_id = 25

Authentication:

Sau đó Authorization kiểm tra:

User 25
    ↓
Role = User
    ↓
Permission = view_users?

Nếu:

No

Server trả:

403 Forbidden

Nếu:

Yes

Server trả dữ liệu.


Một ví dụ nguy hiểm 😱

API có:

DELETE /api/users/50

Developer mới có thể viết:

Nếu có token
    → cho xóa

😨

Sai.

Vì:

Có token

chỉ chứng minh:

"Anh đã xác thực."

Nó không chứng minh:

"Anh có quyền xóa."

Đúng hơn phải là:

Có token?
   ↓
Authentication
   ↓
User là ai?
   ↓
Có quyền DELETE user không?
   ↓
YES → cho phép
NO  → 403

Đây là lỗi bảo mật rất nguy hiểm 🚨

Giả sử:

User A
id = 10

có đơn hàng:

order_id = 100

User B:

id = 20

có đơn hàng:

order_id = 200

User A gọi:

GET /api/orders/200

Nếu Server chỉ kiểm tra:

Token hợp lệ?

Có.

Trả đơn hàng 200.

💀

User A có thể xem đơn hàng của User B.


Server phải kiểm tra thêm

Không chỉ:

"Anh đã đăng nhập chưa?"

mà phải hỏi:

"Đơn hàng này có thuộc về anh không?"

Ví dụ ý tưởng:

User ID = 10
Order ID = 200

Order 200 thuộc User 20

→ DENY

Đây chính là Authorization ở cấp độ resource.


Resource Authorization là gì?

Resource có thể hiểu đơn giản là:

Tài nguyên/dữ liệu mà user muốn truy cập.

Ví dụ:

Post
Order
Invoice
Profile
Photo
Document
Product

Authorization phải kiểm tra:

User này có quyền thao tác với resource này không?

Ví dụ:

GET /api/orders/200

Không chỉ hỏi:

"User có đăng nhập không?"

Mà hỏi:

"Order 200 có thuộc user này không?"


Một ví dụ cực thực tế với Blog 📝

Bạn có bài:

Post ID = 100
Author ID = 25

User 25 gọi:

PUT /api/posts/100

Server:

"Đây là bài của User 25."

→ Cho sửa.


User 30 gọi:

PUT /api/posts/100

Server:

"User 30 không phải tác giả."

→ Có thể từ chối.

403 Forbidden

😎


Admin thì sao?

Admin có thể có quyền đặc biệt.

Ví dụ:

Admin

được phép:

edit_any_post
delete_any_post
manage_users

Trong khi:

Author

chỉ có:

create_post
edit_own_post

Đây là lý do Role + Permission rất hữu ích.


RBAC là gì? 👮

Bạn sẽ gặp thuật ngữ:

RBAC

= Role-Based Access Control

Nói đơn giản:

Phân quyền dựa trên Role.

Ví dụ:

Admin
 ↓
delete_user

Editor
 ↓
edit_post

Author
 ↓
create_post

User được gán Role.

Role quyết định quyền.

Đây là mô hình rất phổ biến.


ABAC là gì? 🤔

Sau này bạn có thể gặp:

ABAC

= Attribute-Based Access Control.

Thay vì chỉ hỏi:

"Anh là Admin không?"

hệ thống có thể kiểm tra nhiều thuộc tính:

User
Resource
Action
Environment

Ví dụ:

User này có phải người phụ trách phòng ban đó không?

Tài liệu có thuộc cùng công ty không?

Đang truy cập trong giờ cho phép không?

Resource có mức bảo mật phù hợp không?

Đây là mô hình linh hoạt hơn nhưng cũng phức tạp hơn.

Với người mới:

RBAC trước.

ABAC để sau.

😄


Authorization không chỉ có Admin/User

Đây là một hiểu lầm rất phổ biến.

Nhiều người mới nghĩ:

Admin
User

là xong.

Không hẳn.

Website thực tế có thể có:

Super Admin
Admin
Manager
Editor
Author
Moderator
Customer
Support
Guest
...

Hoặc thậm chí không dùng Role cố định mà dùng Permission.


Ví dụ hệ thống bán hàng 🛒

Admin
→ quản lý tất cả

Manager
→ quản lý sản phẩm + đơn hàng

Staff
→ xử lý đơn hàng

Customer
→ xem sản phẩm + quản lý đơn của mình

Nếu Customer gọi:

DELETE /api/products/15

Server:

"Không."

🤣


Frontend có thể kiểm tra quyền không?

Có thể.

Ví dụ:

Nếu user không phải Admin.

Frontend không hiển thị:

[Xóa User]

Điều này tốt cho trải nghiệm người dùng.

Nhưng...

⚠️ Không được coi đó là biện pháp bảo mật chính.

Tại sao?

Vì người dùng có thể tự gọi API.

Ví dụ:

DELETE /api/users/15

Họ không cần bấm nút trên giao diện.

Họ có thể dùng:

  • DevTools
  • Postman
  • curl
  • Một chương trình tự viết

😅

Vì vậy:

Authorization phải được kiểm tra ở Backend.


Đây là nguyên tắc cực kỳ quan trọng 🔥

Frontend nói:

"Tôi không cho user thấy nút Delete."

Backend vẫn phải nói:

"Tôi sẽ kiểm tra xem user có quyền Delete không."

Hai lớp:

Frontend
→ UX

Backend
→ Security

Đừng nhầm hai thứ này.


"Chua thêm" lần 2 🤣

Bạn vào ngân hàng.

App không hiện nút:

"Rút 10 tỷ."

Bạn nghĩ:

"Vậy là an toàn rồi."

Không.

🤣

Bạn có thể tự gửi request:

POST /api/withdraw

Nếu Backend chỉ nghĩ:

"Frontend không có nút."

thì...

💀

Backend phải tự kiểm tra:

"User này có được phép rút số tiền này không?"

Backend mới là người gác cổng thật sự.


Authorization và HTTP Method

Authorization có thể phụ thuộc vào hành động.

Ví dụ:

GET /api/products

→ User được phép xem.

Nhưng:

DELETE /api/products/15

→ Chỉ Admin được phép.

Cùng một resource.

Nhưng:

Action khác nhau → Permission khác nhau.


Ví dụ Permission

Bạn có thể thiết kế:

products.view
products.create
products.update
products.delete

Một user:

products.view

→ được xem.

Nhưng:

products.delete

→ không có.


Authorization Matrix 📊

Một cách rất dễ hình dung:

RoleView   Create   Update   Delete
Guest   ❌   ❌   ❌
User   ❌   ❌   ❌
Author   ✅   Own   ❌
Editor   ✅   ✅   ❌
Admin   ✅   ✅   ✅

Đây chính là một:

Authorization Matrix.

Nó giúp developer nhìn rõ:

Ai được làm gì?


Debug Authorization kiểu dev thật 🔍

API trả:

403 Forbidden

Bạn nghĩ:

"API chết."

Không.

😄

Kiểm tra:

1. User đã đăng nhập chưa?

Nếu chưa:

→ Có thể là 401.


2. User là ai?

Kiểm tra:

user_id

3. Role là gì?

Admin?
Editor?
User?

4. Permission có tồn tại không?

Ví dụ:

products.delete

5. Resource có thuộc user không?

Ví dụ:

order_id = 200

thuộc ai?


6. Backend có thực sự kiểm tra quyền không?

Đừng chỉ nhìn Frontend.


Một lỗi rất hay gặp: IDOR 😱

Bạn có thể gặp thuật ngữ:

IDOR

= Insecure Direct Object Reference

Tên nghe rất hàn lâm.

Nhưng ý tưởng khá dễ hiểu.

Ví dụ:

Bạn đang xem:

/api/orders/100

Bạn đổi thành:

/api/orders/101

Nếu Server cho bạn xem dữ liệu của người khác chỉ vì bạn đổi ID...

💀

Đó là một vấn đề Authorization.

Đây là lý do:

"Có đăng nhập" chưa đủ.

Server phải kiểm tra:

User này có quyền truy cập resource này không?


Authorization và Database

Database có thể lưu:

users

Ví dụ:

id | name | role
---|------|------
1  | An   | admin
2  | Bình | user
3  | Cường| user

Backend đọc:

user_id = 2
role = user

Khi Bình gọi:

DELETE /api/users/3

Backend kiểm tra:

role = user

Có quyền:

delete_user?

→ Không.

Trả:

403 Forbidden

Nhưng đừng chỉ dựa vào Role trong Database

Ví dụ:

role = admin

không có nghĩa Admin được phép làm mọi thứ trong mọi hệ thống.

Authorization thực tế có thể phụ thuộc vào:

  • Role
  • Permission
  • Resource ownership
  • Organization
  • Subscription
  • Trạng thái tài khoản
  • Chính sách hệ thống

Vì vậy Authorization nên được thiết kế rõ ràng.


Authorization trong Laravel

Khi học Laravel.

Bạn sẽ gặp những công cụ như:

Middleware

Gate

Policy

Đây là những cơ chế giúp kiểm soát quyền truy cập.

Ví dụ tư duy:

Request
   ↓
Authentication
   ↓
User
   ↓
Authorization
   ↓
Policy / Permission
   ↓
Controller

Không cần học thuộc tất cả ngay.

Chỉ cần nhớ:

Middleware có thể chặn request. Policy có thể giúp kiểm tra quyền đối với resource.

Sau này học Laravel sâu hơn.

Bạn sẽ thấy những thứ này rất tự nhiên.


Một nguyên tắc cực hay 💡

Hãy viết Authorization theo kiểu:

"User có được phép thực hiện ACTION trên RESOURCE này không?"

Ví dụ:

User 25
    ↓
EDIT
    ↓
Post 100

Hỏi:

User 25 có được edit Post 100 không?

Nếu:

YES

→ Cho phép.

Nếu:

NO

→ 403.

Cách suy nghĩ này rất mạnh.


Đừng viết Authorization kiểu "cảm tính" 😅

Ví dụ:

if user_id == 1
    cho phép

😨

Có thể chạy.

Nhưng rất khó bảo trì.

Ngày mai:

Admin = 1

Ngày kia:

Admin = 15

Ngày nọ:

Có 5 Admin

Code bắt đầu:

💥

Tốt hơn là xây dựng quyền theo Role/Permission/Policy rõ ràng.


Checklist chuẩn không cần chỉnh 😎

  • Authentication = Anh là ai?

  • Authorization = Anh được phép làm gì?

  • 401 thường liên quan đến Authentication.

  • 403 thường liên quan đến Authorization.

  • Role = Vai trò.

  • Permission = Quyền cụ thể.

  • RBAC = phân quyền dựa trên Role.

  • Backend phải kiểm tra Authorization.

  • Không được chỉ ẩn nút trên Frontend rồi nghĩ là an toàn.

  • Phải kiểm tra quyền với resource cụ thể khi cần.

  • User đăng nhập thành công không có nghĩa được làm mọi thứ.

  • Cần đặc biệt chú ý các API thao tác dữ liệu như Update/Delete.

  • IDOR là một ví dụ điển hình của lỗi kiểm soát quyền truy cập.

  • Authorization nên được thiết kế rõ ràng và nhất quán.


FAQ nhanh

Authentication và Authorization khác nhau thế nào?

→ Authentication trả lời "Anh là ai?", còn Authorization trả lời "Anh được phép làm gì?"

Đã đăng nhập thì có được phép xem mọi dữ liệu không?

→ Không. Quyền truy cập còn phụ thuộc vào Role, Permission, ownership và các chính sách của hệ thống.

401 và 403 khác nhau thế nào?

→ 401 thường có nghĩa request chưa có thông tin xác thực hợp lệ. 403 nghĩa Server biết hoặc đã xác thực người dùng nhưng từ chối vì không đủ quyền.

Frontend có thể làm Authorization không?

→ Frontend có thể ẩn/hiện chức năng để cải thiện UX, nhưng Backend phải là nơi thực thi kiểm tra quyền thực sự.

Role và Permission khác nhau thế nào?

→ Role là một nhóm vai trò như Admin hoặc Author. Permission là quyền cụ thể như delete_user hoặc edit_post.

User thường có thể tự sửa Role của mình thành Admin không?

→ Không nên. Việc thay đổi Role phải được Backend kiểm soát chặt chẽ.

IDOR có phải là lỗi Authentication không?

→ Thường đây là vấn đề Authorization/Access Control: user đã đăng nhập nhưng được phép truy cập resource mà họ không nên được phép truy cập.


Bạn có thể cũng đang gặp 😭

👉 API Authentication là gì? 

👉 REST API là gì? 

👉 API Pagination là gì?

👉 JSON là gì? 

👉 API là gì? (Giải thích như gọi đồ ăn.)

👉 Session vs Cookie - Hai anh em dễ nhầm nhất của PHP

👉 Cookie là gì? (Vì sao website nhớ được bạn là ai?)

👉 CRUD là gì? 

👉 MVC là gì? 

👉 Framework là gì?

👉 SQL Injection là gì?

👉 Prepared Statement là gì?


Tổng kết

Authorization nghe có vẻ là một thuật ngữ rất "Backend".

Nhưng thực chất nó chỉ là một câu hỏi:

"Anh được phép làm việc này không?"

😎

Server nhận request:

DELETE /api/users/50

Không được chỉ hỏi:

"Anh đăng nhập chưa?"

Mà phải hỏi:

Anh là ai?
   ↓
User 25
   ↓
Anh có quyền DELETE không?
   ↓
Có
   ↓
Anh có được xóa User 50 không?
   ↓
Có
   ↓
Cho phép

Nếu không:

403 Forbidden

Đó chính là Authorization.

Và nếu bạn chỉ nhớ một câu:

Authentication đưa bạn qua cửa. Authorization quyết định bạn được phép mở những cánh cửa nào. 👮