Một số quy tắc thiết kế API

Một số quy tắc thiết kế API

Tin ngắn hàng ngày dành cho bạn
  • Mấy hôm trước OpenAI giới thiệu Deep Research - một công cụ duyệt web để nghiên cứu và cho ra một bản tổng hợp chỉ trong vài chục phút - so với nhiều giờ làm việc đối với con người, theo như họ công bố.

    Tính năng này hiện chỉ có sẵn cho người dùng Pro. Mặc dù chưa được dùng thử, nhưng qua nhiều bài viết đều nhấn mạnh vào sự ấn tượng trước khả năng của công cụ mới này. Nếu vẫn chưa biết Deep Research làm được gì thì bạn cứ hình dung như thế này: Nói với nó "Tôi cần thông tin nghiên cứu về lượng tiêu thụ cà phê của thế giới trong năm ngoái". Thế thôi! Ngồi chờ một lúc để nó tìm kiếm và tổng hợp lại kết quả và gửi lại cho bạn một bài báo cáo chi tiết. Chà, ghê thật chứ!

    Ngay lập tức huggingface đã lên một bài viết cố gắng tái tạo lại công cụ này theo cách của họ. Chi tiết tại Open-source DeepResearch – Freeing our search agents. Và không có gì ngạc nhiên khi cả 2 đều mang hơi hướng của AI Agents.

    » Xem thêm
  • Sống đủ lâu trong thế giới Internet, bạn có thể thấy rằng mọi người ở đây khá háo hức chạy theo xu hướng và chúng lan truyền với tốc độ chóng mặt.

    Chỉ vài tháng trước, chúng ta vẫn còn kinh ngạc về trí thông minh của các mô hình ngôn ngữ lớn (LLM) có thể trả lời giống như con người, và ngay sau đó, chúng đã được cập nhật với khả năng suy nghĩ và lý luận đáng kinh ngạc. Chúng được ứng dụng rộng rãi không chỉ trong lĩnh vực lập trình. Gần đây, thuật ngữ AI Agents đã tạo nên một sự khuấy động.

    Vậy, AI Agents là gì? Trong bài viết ngắn này, tất nhiên là không thể đưa ra một định nghĩa ngắn gọn nhưng toàn diện. Bạn đọc có thể tham khảo bài viết rất chi tiết này tại đây Agents | Chip Huyền. Để dễ hình dung hơn, AI Agents có thể được coi là một người hoặc một thực thể nào đó. Bản thân các Agents được trang bị tất cả các công cụ cần thiết. Từ đó, các Agents có thể kết hợp chúng để hoàn thành một nhiệm vụ mà chúng ta giao.

    Vẫn còn hơi mơ hồ phải không? Một ví dụ thực tế là khi bạn ra lệnh cho các Agents truy cập Facebook vào lúc 8 giờ tối mỗi ngày, kiểm tra bất kỳ tin tức nổi bật nào từ bạn bè, sau đó gửi tóm tắt đến Telegram. Vậy là xong!

    » Xem thêm
  • Hôm qua đến nay, lượt truy cập tới từ Facebook tăng đột biến. Thường như thế là do ai đó chia sẻ bài viết của blog vào một nhóm nào đó.

    Cơ mà lần này là liên kết trực tiếp đến trang chủ luôn. Tò mò ghê, không biết ai chia sẻ, chia sẻ ở đâu nữa. Muốn biết để tìm hiểu "insight" ghê 🥹

    » Xem thêm

Vấn đề

Khi viết chương trình, chúng ta có các Design Pattern nên hoặc thậm chí cần được tuân theo để giúp cho mọi người trong nhóm có thể hiểu và phối hợp với nhau một cách nhịp nhàng. Các "mẫu thiết kế" là minh chứng rõ nhất cho việc đọc hiểu dễ hơn khi con người chúng ta cùng chung một lối suy nghĩ.

Design API cũng vậy, việc tạo ra hàng tá endpoint trong một khoảng thời gian là khá dễ nhưng làm sao để duy trì được sự thống nhất trong suốt quá trình phát triển mới là điều khó. Dự án phát triển theo năm tháng, con người cũng thay đổi, càng có nhiều bộ óc tham gia vào quá trình, càng có nhiều tính cách được bộc phát qua những dòng code.

Thực tê, Design API phụ thuộc vào tính sáng tạo của từng cá nhân, tổ chức. Nếu một nhóm không quá khắt khe với vấn đề đặt tên cho một endpoint thì thế giới này là của bạn, hãy tự do sáng tạo dựa trên những gì có thể nghĩ ra được. Ngược lại, có những tổ chức lại đưa ra những quy định ngặt nghèo trong quá trình này, buộc chúng ta phải tuân theo. Nhưng dù là thế nào đi nữa, mục đích cuối cùng của việc đó vẫn là làm sao để đại đa số lập trình viên nhìn vào đều có thể hiểu hoặc biết cách để tìm kiếm thứ mà họ cần.

Tôi là một người thích sự sáng tạo, nhưng không nên phá cách. Có những thứ mình vẫn cần tuân theo để đảm bảo được sự minh bạch của API. Bài viết này hôm nay, tôi sẽ trình bày một số quy tắc trong quá trình Design API mà rất nhiều lập trình viên trên thế giới đang áp dụng. Nếu không tin, sau khi đọc xong bài viết này, hãy thử "vọc vạch" một bộ API của bất kỳ bên thứ 3 nào đó đang cung cấp để xem họ đang làm như thế nào.

Một lần nữa, các quy tắc nêu ra dưới đây chỉ để tham khảo và không bắt buộc ai phải làm theo. Nếu bạn nhận ra được lợi ích từ việc tuân theo nguyên tắc, tôi tin rằng đây là một điều không nên bỏ qua. Không dài dòng nữa, vào việc thôi!

Một số quy tắc

Đầu tiên, hãy làm rõ một số khái niệm liên quan đến việc thiết kế API.

Chúng ta có resource, đại diện cho "tài nguyên" muốn truy cập hoặc thực hiện một thao tác. Khi gọi đến một endpoint, dữ liệu được trả về, nó là danh sách bài viết, chi tiết bài viết… gọi chung là resource. Bên cạnh đó, trong resource thường có các thuộc tính (attributes), chúng là một thành phần của resource hoặc được tính toán dựa trên resource.

Một "bộ sưu tập" hay Collections là tập hợp của các resource, thông thường các resource giống nhau được xếp chung vào một Collections. Ví dụ đối với một tài nguyên là "Users", chúng ta có tập hợp các thao tác với người dùng như là thêm, sửa, xóa… gọi là Collections.

URLs thì rõ rồi, đường dẫn đến resource của bạn. Ví dụ /articles để trỏ vào danh sách bài viết.

Quy tắc về đường dẫn (path)

Xác định bộ sưu tập cho tài nguyên, ví dụ /articles cho các bài viết, /comments cho các bình luận và luôn sử dụng danh từ số nhiều.

Sử dụng "kebab-case" cho mọi thứ trong đường dẫn URLs, "camelCase" cho tham số trong truy vấn. Ví dụ /special-articles?isHighlight=true.

Sử dụng "mã định danh" như ID của resource để thao tác với một tài nguyên chỉ định. Ví dụ: /articles/nodejs-la-gi để tương tác với bài viết có URL "nodejs-la-gi".

Tránh sử dụng đường dẫn có chứa thuộc tính của resource hoặc là các hành động đối với resource, nó sẽ gây ra nhiều rắc rối cũng như phức tạp hóa đường dẫn sau này. Ví dụ: không nên /articles/nodejs-la-gi/summary hoặc /articles/nodejs-la-gi/reset-view, hãy thử chuyển thuộc tính vào parameters hoặc trong request body, ví dụ /articles/nodejs-la-gi?summary=true.

Nên xác định tiền tố cho phiên bản API, ví dụ /v1/articles để trỏ đến phiên bản 1 của API. Nếu sau này nâng cấp API, chúng ta có thể mở rộng thêm /v2, /v3… mà hạn chế ảnh hưởng đến các phiên bản trước đó.

Quy tắc về phương thức

Có 5 phương thức HTTP phổ biến mà chắc hẳn ai cũng nghe qua.

GET: Để lấy một tài nguyên.
POST: Để tạo tài nguyên mới.
PUT: Để cập nhật các tài nguyên hiện có.
PATCH: Để cập nhật các tài nguyên hiện có, nhưng chỉ cập nhật các trường được cung cấp, để yên những trường khác.
DELETE: Để xóa các tài nguyên hiện có.

Kết hợp với quy tắc về đường dẫn, các phương thức HTTP góp phần làm rõ thêm hành động bạn đang muốn tương tác với tài nguyên là gì. Ví dụ:

GET /articles - lấy danh sách tất cả bài biết.
GET /articles/nodejs-la-gi - lấy chi tiết bài viết có URL nodejs-la-gi.
POST /articles - tạo mới một bài viết.
DELETE /articles - xóa bài viết.

Quy tắc về response status code

HTTP response status code là những con số cho biết liệu một yêu cầu HTTP có được hoàn thành hay là không.

Có rất nhiều status code nhưng dưới đây là một vài con số chúng ta thường hay gặp:

200 OK: thành công.
201 Created: thường được trả về khi API vừa tạo một tài nguyên mới thành công.
204 No Content: thao tác thành công nhưng không có gì được trả về, ví dụ như thao tác DELETE một tài nguyên đã có.
400 Bad Request: báo lỗi khi một yêu cầu không hợp lệ, có thể là hành vi gửi lên dữ liệu không hợp lệ cho nên cần phải từ chối xử lý.
401 Unauthorized: lỗi khi yêu cầu này cần xác thực thông tin hợp lệ trước khi hành động, ví dụ như chưa đăng nhập vào hệ thống.
403 Forbidden: lỗi khi không có quyền thực hiện chức năng này.
404 Not Found: lỗi không tìm thấy tài nguyên hoặc hành động.
500 Internal Server Error: một lỗi "không xác định" từ máy chủ, có thể do sự cố ngoài ý muốn như lỗi phần cứng, phần mềm, mạng…

Ngoài ra, bạn đọc có thể tham khảo thêm mã lỗi khác tại HTTP response status codes - Mozilla. Việc tuân thủ status code giúp đạt được sự thống nhất trong quá trình phát triển, cũng như cho các bên tích hợp API.

Quy tắc về response body

Giữ cho response body của bạn được xuyên suốt từ đầu đến cuối. Ví dụ một phản hồi thành công bao gồm mã phản hồi, thông điệp và dữ liệu trả về.

{
  "status": 200,  
  "message": "OK",  
  "data": {
    "id": 1,  
    "name": "John Doe",  
    "email": "[email protected]"
  }
}

Nếu là thông báo lỗi, hãy kèm theo mã lỗi và thông điệp lỗi.

{
  "code": 400,  
  "message": "Bad Request"
}

Giữ thông báo lỗi chung nhất có thể để hạn chế việc làm lộ dữ liệu hoặc thông tin quan trọng khác.

Ngoài ra, có một vài quy tắc khác trong việc thiết kế API như:

Luôn phân trang cho các yêu cầu đến tài nguyên dạng danh sách, ví dụ /articles?limit=10&offset=0 hoặc /articles?page=1&limit=10… Nếu có thể, trả về thêm tổng số resource có trong danh sách đó. Các tài nguyên dạng danh sách cũng có thể cần được sắp xếp theo một thứ tự nào đó, ví dụ /articles?sort=createdAt:desc

Tài nguyên chi tiết thông thường trả về hết thuộc tính có thể có, nhưng đó không phải lúc nào cũng cần, có thể hỗ trợ cần lấy những thuộc tính nào thông qua lọc, ví dụ /articles?field=url,title,content,createdAt

Tham khảo:

API design.

Cao cấp
Hello

Bí mật ngăn xếp của Blog

Là một lập trình viên, bạn có tò mò về bí mật công nghệ hay những khoản nợ kỹ thuật về trang blog này? Tất cả bí mật sẽ được bật mí ngay bài viết dưới đây. Còn chờ đợi gì nữa, hãy bấm vào ngay!

Là một lập trình viên, bạn có tò mò về bí mật công nghệ hay những khoản nợ kỹ thuật về trang blog này? Tất cả bí mật sẽ được bật mí ngay bài viết dưới đây. Còn chờ đợi gì nữa, hãy bấm vào ngay!

Xem tất cả

Đăng ký nhận thông báo bài viết mới

hoặc
* Bản tin tổng hợp được gửi mỗi 1-2 tuần, huỷ bất cứ lúc nào.

Bình luận (1)

Nội dung bình luận...
Avatar
Tiennx Business1 năm trước
bài viết hay quá anh Hoài. Mà e nghĩ những từ cần chú ý "keyword" vd như: 401,400,500,... thì nên đổi màu cho nổi để dễ nhìn :D
Trả lời
Avatar
Xuân Hoài Tống1 năm trước
Ok luôn, a cũng thấy hơi lấn cấn 😅
Bấm hoặc cuộn mạnh để sang bài mới