Authentication – Các phương thức xác thực phổ biến hiện nay

Authentication – Các phương thức xác thực phổ biến hiện nay

December 9, 2021 2 By Nam Vu

Bài viết trước mình có đề cập sơ lược về “Authentication vs Authorization – Trái tim của một ứng dụng“, bạn có thể đọc lại. 

Bài viết này mình xin phép đi tiếp chủ đề này nhé!

Các phương thức xác thực phổ biến hiện nay

HTTP Basic authentication

HTTP Basic authentication yêu cầu client cung cấp username và password mỗi lần gọi request. Đây là cách xác thực đơn giản nhất, không yêu cầu cookies, sessions… 

Để tạo được chuỗi bảo mật theo phương thức này sẽ thực hiện qua những bước sau:

+ Bước 1: Tạo chuối bảo mật từ Username và Password. Nó không được encrypt mà được cấu trúc như sau: Nối username và password theo dạng username:password; Encode chuỗi trên với Base64; Thêm từ khoá Basic

Ví dụ

curl --header "Authorization: Basic am9objpzZWNyZXQ=" my-website.com

+ Bước 2: Phía client cần thêm header Authorization đã tạo trên vào tất cả các request.

Nhìn khá là đơn giản phải không nhưng nó có khá nhiều nhược điểm khi sử dụng HTTP Basic Authentication.

– username và password được gửi trong mọi request, nên có nguy cơ bị lộ tài khoản, kể cả khi sử dụng kết nối bảo mật.
– Liên kết với SSL/TLS, nếu mà website sử dụng mã hoá yếu thì sẽ bị lộ tài khoản ngay lập tức.
– Không có cách nào để đăng xuất tài khoản cả.
– Phiên đăng nhập sẽ không bao giờ bị hết hạn, trừ khi người dùng đổi password.

HTTP cookies

Xác thực bằng Cookies sử dụng HTTP cookies để xác thực request của client và duy trì phiên đăng nhập. 

Luồng hoạt động:

– Client gửi request đăng nhập lên server.
– Khi server nhận được HTTP request, gửi thêm Set-Cookie header vào response.
– Trình duyệt thêm cookie đó vào tất cá các request có cùng origin với origin trong Cookie HTTP header.
– Khi đăng xuất, server sẽ gửi lại Set-Cookie để khiến cho cookie cũ hết hạn.

Nếu muốn sử dụng Cookies để xác thực thì phải tuân thủ một số nguyên tắc sau:

– Luôn luôn sử dụng HttpOnly cookies: Để giảm thiểu khả năng bị tấn công XSS thì luôn sử dụng HttpOnly flack khi thiết lập cookie. Bằng cách đó cookie sẽ không hiện lên ở document.cookies.
– Luôn luôn sử dụng signed cookies: Với signed cookies, server có thể biết được là cookie có bị client sửa đổi hay không.

Nhược điểm của xác thực sử dụng Cookies:

– Dễ bị tấn công CSRF (CSRF là một kiểu tấn công gây sự nhầm lẫn tăng tính xác thực và cấp quyền của nạn nhân khi gửi một request giả mạo đến máy chủ. Vì thế một lỗ hổng CSRF ảnh hưởng đến các quyền của người dùng ví dụ như quản trị viên, kết quả là chúng truy cập được đầy đủ quyền), cần phải làm thêm một số việc để giảm thiểu rủi ro.
– Không tương thích với REST (vì REST là stateless)

Tokens

Khái niệm chung nằm sau các phương pháp xác thực dựa trên Tokens khá đơn giản. Khi mà người dùng nhập username và password, họ sẽ nhận được một token. Token đó sẽ cho phép người dùng có thể gọi request lên server để thực hiện thao tác mong muốn, mà không cần phải nhập username và password.

Hiện tại thì JWT (JSON Web Token) có mặt hầu hết khắp mọi nơi nhưng nó vẫn có chứa những nguy cơ an ninh tiềm ẩn.

Đầu tiên hãy cùng tìm hiểu xem JWT là gì nhé. JWT bao gồm 3 phần:

– Header: Chứa kiểu dữ liệu và tên thuật toán hashing – tạm gọi là thuật toán X, được mã hoá bằng X
– Payload: Chứa các thông tin cần gửi như username, title… được mã hoá bằng X
– Signature: Là mã hoá của header, payload và 1 khoá bí mật, được tính theo công thức sau:

X(base64UrlEncode(header) + "." + base64UrlEncode(payload), secret)

Kết hợp 3 thành phần trên ta được một token hoàn chỉnh có dạng: header.payload.signature

curl --header "Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiYWRtaW4iOnRydWV9.TJVA95OrM7E2cBab30RMHrHDcEfxjoYZgeFONFh7HgQ" my-website.com

Bạn có thể kiểm tra tính đúng đắn của token tại https://jwt.io/
JWT  phù hợp với API cho native mobile app hoặc single page application. Có một điều cần lưu ý khi sử dụng JWT là browser sẽ lưu JWT trong LocalStorage hoặc SessionStorage, do đó có nguy cơ bị XSS attack.

Signatures

Dù sử dụng cookies hay là tokens, nếu mà transport layer vì 1 lý do nào đó mà để lộ thông tin, thì attacker hoàn toàn có thể dùng token và cookie để truy cập như người dùng thật.

Một cách để giải quyết vấn đề trên là chúng ta sẽ ký (sign) vào tất cả các request (ở đây chỉ đề cập đến các request qua APIs, không bao gồm các request từ browser).

Sign vào request có nghĩa là phải hash toàn bộ request sử dụng private key. Việc hashing cần sử dụng:

– HTTP method
– Đường dẫn của request
– HTTP headers
– Checksum của HTTP payload
– private key để tạo hash

Người gọi và người cung cấp API phải có chung 1 private key. Một khi mà đã có signature, người dùng cần thêm signature vào query string hoặc HTTP header của request. Người dùng cũng nên thêm date vào để có thể chỉ rõ được thời gian hết hạn của signature.

Bằng cách trên, nếu mà transport layer có bị hack thì attacker cũng chỉ có thể đọc được nội dung của request, chứ không thể nào mà giả vờ là user để gửi request được vì không có private key. Phương thức này có nhược điểm là không thể sử dụng với browser/client, chỉ sử dụng với APIs.

One-Time passwords

Thuật toán One-Time passwords tạo ra 1 password dùng 1 lần (one-time password) dựa vào khoá bí mật được dùng chung và thời gian hiện tại hoặc 1 bộ đếm:

– Time-based One-time Password Algorithm, dựa vào thời gian hiện tại
– HMAC-based One-time Password Algorithm, dựa vào bộ đếm

One-Time passwords thường được áp dụng trong các ứng dụng cần bảo mật hai lớp: người dùng nhập username, password sau đó cả server và client sẽ cùng tạo ra một one-time password.

One-Time passwords có nhược điểm sau:
– Nếu khoá bí mật bị lộ thì attacker sẽ nắm được one-time password.
– Client (thường là điện thoại) có thể bị trộm nên hệ thống cần có cách để skip one-time password, ví dụ như là rest qua email.

Ngoài những phương thức trên, còn rất nhiều phương thức khác mà mình chưa đề cập đến ở đây nhưng mình nghĩ những phương thức bên trên là khá phổ biến cho. Bạn có thể tìm hiểu thêm tại đây

Tóm lại tùy theo nhu cầu xây dựng và cơ sở bảo mật của hệ thống ứng dụng của bạn mà bạn có thể lựa chọn phương thức sao cho phù hợp

– Nếu mà bạn chỉ xây dựng web thì cookies và tokens là lựa chọn phù hợp. Với Cookies bạn cần chú ý về tấn công XSRF, còn với JWT thì cần chú ý đến tấn công XSS.
– Nếu mà bạn cần xây dựng cả web và app mobile thì nên dựng API xác thực qua token.
– Nếu bạn đang xây dựng APIs để người dùng gọi đến API của bạn thì nên dùng signatures. Hiện tại theo mình biết thì cả AWS và Vn-Pay cũng đang dùng phương thức này

#ntechdevelopers

Tham khảo:
https://auth0.com/docs/get-started/authentication-and-authorization
https://en.wikipedia.org/wiki/Authentication_protocol