Làm cách nào để tạo URL REST không có động từ?


283

Tôi đang vật lộn để xác định cách thiết kế các URL yên tĩnh. Tôi hoàn toàn dành cho cách tiếp cận đầy đủ của việc sử dụng URL với danh từ chứ không phải động từ không hiểu cách thực hiện việc này.

Chúng tôi đang tạo ra một dịch vụ để thực hiện một máy tính tài chính. Máy tính có một loạt các tham số mà chúng tôi sẽ tải lên thông qua tệp CSV. Các trường hợp sử dụng sẽ liên quan đến:

  1. Tải lên các tham số mới
  2. Lấy thông số mới nhất
  3. Nhận thông số cho một ngày làm việc nhất định
  4. Tạo một bộ thông số hoạt động
  5. Xác thực một bộ tham số

Tôi tập hợp cách tiếp cận đầy đủ sẽ có các loại URL sau:

/parameters
/parameters/12-23-2009

Bạn có thể đạt được ba trường hợp sử dụng đầu tiên với:

  1. POST nơi bạn bao gồm tệp tham số trong yêu cầu bài viết
  2. NHẬN URL đầu tiên
  3. NHẬN URL thứ hai

Nhưng làm thế nào để bạn làm trường hợp sử dụng thứ 4 và thứ 5 mà không có động từ? Bạn sẽ không cần các URL như:

/parameters/ID/activate
/parameters/ID/validate

??


3
Tôi thích PATCH hơn là POST để cập nhật một phần.
dùng2016971

Câu trả lời:


71

Có lẽ một cái gì đó như:

PUT /parameters/activation HTTP/1.1
Content-Type: application/json; encoding=UTF-8
Content-Length: 18

{ "active": true }

1
POSTSẽ ổn nếu bạn cần thực hiện một "thủ tục" như xác minh các tham số mỗi khi bạn gửi yêu cầu. Nhưng khi bạn sửa đổi trạng thái (ứng dụng) của tài nguyên, bạn thực sự cập nhật tài nguyên hiện có, không tạo một số tài nguyên mới hoặc gửi yêu cầu xử lý.
Andrey Vlasovskikh

19
PUT là để tạo một tài nguyên mới hoặc đặt (toàn bộ, không phải một phần) một tài nguyên mới tại một URL cụ thể. Tôi không thấy PUT phù hợp với trường hợp này như thế nào.
Breton

30
Trên thực tế, POSTvs PUTkhông hoàn toàn giống insertvs update. PUTcập nhật tài nguyên tương ứng với đường dẫn đã cho hoặc tạo tài nguyên mới tương ứng với đường dẫn đã cho. POSTtạo ra một nguồn tài nguyên mới ở đâu đó Ví dụ: PUT /blog/posts/3/comments/5sẽ cập nhật nhận xét thích hợp, trong khi POST /blog/posts/3/commentssẽ tạo một commenttài nguyên mới (và sẽ trả lại đường dẫn đến tài nguyên mới trong phản hồi).
yfeldblum

23
@Justice @Breton Sự khác biệt quan trọng hơn PUTlà không có gì trong khi POSTkhông. Thông thường bạn nên đặt càng nhiều ràng buộc vào những gì bạn cung cấp càng nhiều càng tốt. Gắn bó với việc PUTcung cấp thêm thông tin cho khách hàng của dịch vụ.
Andrey Vlasovskikh

3
Tài nguyên cũng có thể là / tham số / trạng thái và phần thân của yêu cầu có thể chỉ là "hoạt động". Bằng cách đó, bằng cách nào đó bạn đang đặt một tài nguyên hoàn toàn mới vào một URL cụ thể.
Carlos Aguayo

991

Nguyên tắc chung để thiết kế URI tốt:

  • Không sử dụng tham số truy vấn để thay đổi trạng thái
  • Đừng sử dụng các đường dẫn hỗn hợp nếu bạn có thể giúp nó; chữ thường là tốt nhất
  • Không sử dụng các tiện ích mở rộng dành riêng cho triển khai trong URI của bạn (.php, .py, .pl, v.v.)
  • Đừng rơi vào RPC với các URI của bạn
  • Đừng giới hạn không gian URI của bạn càng nhiều càng tốt
  • Đừng giữ các đoạn đường dẫn ngắn
  • Đỗ thích một trong hai /resourcehoặc /resource/; tạo 301 chuyển hướng từ cái bạn không sử dụng
  • Do các thông số sử dụng truy vấn cho phụ lựa chọn của một tài nguyên; tức là phân trang, truy vấn tìm kiếm
  • Không di chuyển công cụ ra khỏi URI phải có trong tiêu đề HTTP hoặc phần thân

(Lưu ý: Tôi không nói "Thiết kế URI RESTful"; URI về cơ bản là mờ đục trong REST.)

Nguyên tắc chung cho lựa chọn phương thức HTTP:

  • Đừng bao giờ sử dụng GET để thay đổi trạng thái; đây là một cách tuyệt vời để Googlebot hủy hoại ngày của bạn
  • Không sử dụng PUT trừ khi bạn đang cập nhật toàn bộ tài nguyên
  • Không sử dụng PUT trừ khi bạn cũng có thể thực hiện GET trên cùng một URI
  • Không sử dụng POST để truy xuất thông tin tồn tại lâu hoặc có thể hợp lý để lưu vào bộ đệm
  • Đừng thực hiện một hoạt động mà không được idempotent với PUT
  • Do sử dụng GET cho càng nhiều càng tốt
  • Do sử dụng POST trong ưu tiên cho PUT khi nghi ngờ
  • Do sử dụng POST bất cứ khi nào bạn cần phải làm điều gì đó mà cảm thấy RPC-like
  • Do sử dụng PUT cho các lớp tài nguyên có dung lượng lớn hoặc thứ bậc
  • Đừng sử dụng DELETE trong ưu tiên cho POST để nguồn remove
  • Đỗ sử dụng GET cho những thứ như tính toán, trừ khi đầu vào của bạn là lớn, trong đó trường hợp sử dụng POST

Nguyên tắc chung của thiết kế dịch vụ web với HTTP:

  • Không đặt siêu dữ liệu trong phần nội dung của phản hồi phải có trong tiêu đề
  • Đừng đặt siêu dữ liệu vào một tài nguyên riêng trừ khi bao gồm nó sẽ tạo ra chi phí đáng kể
  • Đừng sử dụng các mã trạng thái thích hợp
    • 201 Createdsau khi tạo tài nguyên; tài nguyên phải tồn tại tại thời điểm phản hồi được gửi
    • 202 Accepted sau khi thực hiện thao tác thành công hoặc tạo tài nguyên không đồng bộ
    • 400 Bad Requestkhi ai đó thực hiện một thao tác trên dữ liệu rõ ràng là không có thật; cho ứng dụng của bạn đây có thể là một lỗi xác nhận; thường dự trữ 500 cho các trường hợp ngoại lệ
    • 401 Unauthorizedkhi ai đó truy cập API của bạn mà không cung cấp Authorizationtiêu đề cần thiết hoặc khi thông tin đăng nhập trong Authorizationđó không hợp lệ; không sử dụng mã phản hồi này nếu bạn không mong đợi thông tin đăng nhập qua Authorizationtiêu đề.
    • 403 Forbidden khi ai đó truy cập API của bạn theo cách có thể độc hại hoặc nếu họ không được ủy quyền
    • 405 Method Not Allowed khi ai đó sử dụng POST khi họ nên sử dụng PUT, v.v.
    • 413 Request Entity Too Large khi ai đó cố gắng gửi cho bạn một tệp lớn không được chấp nhận
    • 418 I'm a teapot khi cố gắng pha cà phê bằng ấm trà
  • Do sử dụng tiêu đề bộ nhớ đệm bất cứ khi nào bạn có thể
    • ETag tiêu đề là tốt khi bạn có thể dễ dàng giảm tài nguyên thành giá trị băm
    • Last-Modified nên cho bạn biết rằng giữ khoảng thời gian khi tài nguyên được cập nhật là một ý tưởng hay
    • Cache-ControlExpiresnên được đưa ra các giá trị hợp lý
  • Làm mọi thứ bạn có thể để tôn vinh các tiêu đề bộ đệm trong một yêu cầu ( If-None-Modified, If-Modified-Since)
  • Đỗ ← liên kết sử dụng khi họ có ý nghĩa, nhưng những nên hiếm hoi cho một dịch vụ web

Đối với câu hỏi cụ thể của bạn, POST nên được sử dụng cho # 4 và # 5. Các hoạt động này nằm trong hướng dẫn "giống như RPC" ở trên. Đối với # 5, hãy nhớ rằng POST không nhất thiết phải sử dụng Content-Type: application/x-www-form-urlencoded. Đây có thể dễ dàng là một tải trọng JSON hoặc CSV.


11
413 được dành cho kích thước của yêu cầu bạn đang gửi để bạn có thể từ chối một cách lịch sự một ai đó gửi cho bạn hợp đồng dữ liệu, thường kết hợp với 411 để bạn buộc mọi người cho bạn biết số tiền được gửi. Đối với ví dụ được đưa ra so với 413, tôi nghĩ 400 sẽ là một phản ứng phù hợp hơn.
Garry Shutler

5
+1 vì đây là một tài nguyên tuyệt vời. Tuy nhiên, đó là một tài nguyên chung và không trực tiếp trả lời câu hỏi. Điều này lý tưởng nên bao gồm một đoạn bổ sung với một câu trả lời cụ thể.
Samuel Neff

@GarryShutler Bắt tốt, bạn hoàn toàn đúng. Cảm ơn đã chỉnh sửa.
Bob Aman

1
Có, bạn sẽ chỉ sử dụng PUT trong trường hợp bạn ghi đè lên toàn bộ đối tượng. Tuy nhiên, tôi muốn khẳng định rằng một trong hai PATCH hoặc POST là hợp lý trong trường hợp của một bản cập nhật phần của một tài nguyên. PATCH rõ ràng hơn về những gì hoạt động sẽ làm, nhưng bởi vì không phải tất cả các khách hàng thậm chí có khả năng đưa ra yêu cầu PATCH , nên hoàn toàn thích hợp để cho phép POST thay thế, và tôi thậm chí có thể đi xa hơn để ủng hộ rằng POST phải luôn luôn được cho phép như một dự phòng nếu sử dụng PATCH .
Bob Aman

1
+1 cho 409 lỗi. Một lỗi 400 là một cái gì đó có thể được giải quyết bằng cách xác nhận đủ phía khách hàng. 409 làm rõ rằng bản thân yêu cầu có thể chấp nhận và nhất quán, nhưng mâu thuẫn với một số khía cạnh của trạng thái máy chủ (thường là các điều khiển đồng thời, nhưng về mặt lý thuyết là bất kỳ ràng buộc không đầu vào nào).
claytond

18

Bất cứ khi nào có vẻ như bạn cần một động từ mới, thay vào đó hãy nghĩ về việc biến động từ đó thành một danh từ. Ví dụ: biến 'kích hoạt' thành 'kích hoạt' và 'xác thực' thành 'xác thực'.

Nhưng chỉ từ những gì bạn đã viết, tôi nói ứng dụng của bạn có vấn đề lớn hơn nhiều.

Bất cứ khi nào một tài nguyên được gọi là 'tham số' được đề xuất, nó sẽ gửi cờ đỏ trong tâm trí của mỗi thành viên nhóm dự án. 'tham số' theo nghĩa đen có thể áp dụng cho bất kỳ tài nguyên nào; nó không đủ cụ thể

Chính xác thì 'tham số' thể hiện điều gì? Có lẽ một số thứ khác nhau, mỗi thứ nên có một tài nguyên riêng dành riêng cho nó.

Một cách khác để có được điều này - khi bạn thảo luận về ứng dụng của mình với người dùng cuối (những người có lẽ ít biết về lập trình), những từ mà họ sử dụng nhiều lần là gì?

Đó là những từ bạn nên thiết kế ứng dụng của bạn xung quanh.

Nếu bạn chưa có chuyển đổi này với người dùng tiềm năng - hãy dừng mọi thứ ngay bây giờ và đừng viết một dòng mã khác cho đến khi bạn làm điều đó! Chỉ sau đó, nhóm của bạn mới có ý tưởng về những gì cần được xây dựng.

Tôi không biết gì về phần mềm tài chính, nhưng nếu tôi phải đoán, tôi sẽ nói một số tài nguyên có thể đi theo các tên như "Báo cáo", "Thanh toán", "Chuyển khoản" và "Tiền tệ".

Có một số cuốn sách hay về phần này của quy trình thiết kế phần mềm. Hai tôi có thể đề xuất là các mẫu phân tíchthiết kế hướng tên miền .


1
Đây là một điểm thực sự tốt. Thật dễ dàng để bỏ lỡ nếu bạn ở trong trạng thái tinh thần để xử lý logic và lý luận chính thức. Không quan trọng X là gì miễn là nó khớp với các phần khác một cách hợp lệ. Yếu tố con người chỉ trôi đi.
Breton

1
Đôi khi tôi thấy hữu ích khi chuyển đổi các từ thành "tài nguyên xử lý" như "trình kích hoạt" hoặc "trình xác nhận". Theo RFC 2616 POST có thể được sử dụng để "Cung cấp khối dữ liệu ... cho quy trình xử lý dữ liệu"
Darrel Miller

Hiểu. Trong trường hợp này, người dùng thường gọi dữ liệu là "tham số" (hoặc "tham số rủi ro" hoặc một cái gì đó tương tự). Danh sách các tham số chứa nhiều loại cài đặt khác nhau nhưng các tham số luôn được tải lên dưới dạng toàn bộ (trong tệp CSV).
Marcus Leon

@Marcus - nghe có vẻ là một trường hợp rất bất thường. Có thể nếu bạn giải thích những gì ứng dụng của bạn làm chi tiết hơn, chúng tôi sẽ có thể cung cấp các đề xuất tốt hơn để xác định tài nguyên.
Giàu Apodaca

1
"khi bạn thảo luận về ứng dụng của mình với người dùng cuối, những từ mà họ sử dụng nhiều lần là gì?" ... Và nếu tất cả chúng là động từ thì sao? XD
Amalgovinus

11

Thiết kế URL của bạn không liên quan gì đến việc ứng dụng của bạn có RESTful hay không. Do đó, cụm từ "URL RESTful" là vô nghĩa.

Tôi nghĩ bạn nên đọc thêm về REST thực sự là gì. REST coi URLS là mờ đục và vì thế không biết những gì trong đó, cho dù có động từ hay danh từ hay bất cứ điều gì. Bạn vẫn có thể muốn thiết kế URL của mình, nhưng đó là về UI, không phải REST.

Điều đó nói rằng, hãy để câu hỏi của bạn: Hai trường hợp cuối cùng không phải là RESTful và không phù hợp với bất kỳ loại sơ đồ yên tĩnh nào. Đó là những gì bạn có thể gọi RPC. Nếu bạn nghiêm túc về REST, bạn sẽ phải suy nghĩ lại về cách ứng dụng của bạn hoạt động từ đầu. Hoặc là hoặc từ bỏ REST và chỉ làm ứng dụng của bạn như một ứng dụng RPC.

Hrmmm có thể không.

Ý tưởng ở đây là bạn phải coi mọi thứ là tài nguyên, vì vậy một khi tập hợp các tham số có URL bạn có thể tham chiếu từ đó, bạn chỉ cần thêm:

GET [parametersurl]/validationresults

POST [paramatersurl]
body: {command:"activate"}

Nhưng một lần nữa, thứ kích hoạt đó là RPC, không phải REST.


Bạn nêu một điểm thú vị ở đây. Bạn có thể nói rõ hơn một chút về cách tiếp cận RESTful cho một cái gì đó như thế này không?
poezn

Tôi đã dành một chút thời gian để đọc các câu trả lời ở đây và tôi nghĩ rằng công lý có thể sẽ xảy ra với một cái gì đó. anh ta mô hình các thuộc tính riêng lẻ của đối tượng tham số của bạn dưới dạng tài nguyên riêng lẻ và sử dụng động từ PUT để thay thế nội dung của thuộc tính đó tại tài nguyên đó. Đây là mô hình hóa trạng thái của từng đối tượng dưới dạng tập hợp các tài nguyên và sửa đổi trạng thái là đặt hoặc xóa hoặc sửa đổi tài nguyên. Đối với xác nhận - Bạn chỉ cần một tài nguyên nói một cách kỳ diệu xem các tham số có hợp lệ hay không, như trên trong câu trả lời của tôi. Điều đó sẽ ổn thôi, miễn là không có tác dụng phụ.
Breton

Tất nhiên, với điều kiện là những gì "Kích hoạt" thực hiện chỉ là đặt một thuộc tính duy nhất thành đúng. Nếu nó phải làm bất cứ điều gì khác, thì nó vẫn không RESTful và tôi không chắc bạn sẽ mô hình hóa nó như thế nào.
Breton

Tôi không nghĩ bạn có thể nói hai trường hợp cuối không phải là RESTful. Trong thực tế Kích hoạt và Xác thực chỉ là những cách gián tiếp để nói tài nguyên đang thay đổi sang trạng thái mới trong một máy trạng thái. REST hoàn toàn có khả năng mô hình hóa điều này.
Darrel Miller

@Darrel, tôi nghĩ bạn chỉ ra một phần của REST có thể là thách thức đối với nhiều người mới biết về REST. Làm thế nào bạn có thể thực hiện một hoạt động "Xác thực tài nguyên x"? Tôi nghĩ rằng điều thách thức là nó là một hoạt động có thể dẫn đến thay đổi trạng thái, nhưng trạng thái mới là kết quả của yêu cầu được thực hiện.
Sean

6

Các yêu cầu kích hoạt và xác nhận là các tình huống trong đó bạn đang cố gắng thay đổi trạng thái của tài nguyên. Không có gì khác nhau khi thực hiện một đơn đặt hàng "đã hoàn thành" hoặc một số yêu cầu khác "được gửi". Có nhiều cách để mô hình hóa các loại thay đổi trạng thái này, nhưng một cách mà tôi thấy thường làm việc là tạo tài nguyên thu thập cho các tài nguyên ở cùng trạng thái và sau đó di chuyển tài nguyên giữa các bộ sưu tập để ảnh hưởng đến trạng thái.

ví dụ: Tạo một số tài nguyên như,

/ActiveParameters
/ValidatedParameters

Nếu bạn muốn làm cho một tập hợp các tham số hoạt động, sau đó thêm bộ đó vào bộ sưu tập ActiveParameter. Bạn có thể truyền tập hợp các tham số dưới dạng một thực thể hoặc bạn có thể truyền url dưới dạng tham số truy vấn, như sau:

POST /ActiveParameters?parameter=/Parameters/{Id}

Điều tương tự có thể được thực hiện với / ValidatedParameter. Nếu các Tham số không hợp lệ thì máy chủ có thể trả về "Yêu cầu xấu" cho yêu cầu thêm các tham số vào bộ sưu tập các tham số được xác thực.


1

Tôi muốn đề xuất các tài nguyên và phương pháp Meta sau đây.

Làm cho các tham số hoạt động và / hoặc xác nhận chúng:

> PUT /parameters/<id>/meta HTTP/1.1
> Host: example.com
> Content-Type: application/json
> Connection: close
>
> {'active': true, 'require-valid': true}
>
< HTTP/1.1 200 OK
< Connection: close
<

Kiểm tra xem các tham số có hoạt động và hợp lệ không:

> GET /parameters/<id>/meta HTTP/1.1
> Host: example.com
> Connection: close
>
< HTTP/1.1 200 OK
< Content-Type: application/json
< Connection: close
<
< {
<     'active': true,
<     'require-valid': true,
<     'valid': {'status': false, 'reason': '...'}
< }
<

Theo như tôi hiểu, câu hỏi là về cách đặt tên của các URL yên tĩnh, không phải về chức năng, phải không?
poezn

2
Một câu hỏi giới hạn trong "URL RESTful" là một câu hỏi tồi và không nên trả lời. Thay vào đó, câu hỏi nên được mở rộng để xem xét "Tài nguyên RESTful, với các phương thức và URL được liên kết" - và được trả lời như vậy.
yfeldblum

Theo tôi hiểu, câu hỏi là về các quy ước đặt tên URL các phương thức HTTP mà tài nguyên được đặt tên sẽ đáp ứng.
Andrey Vlasovskikh

1

Tôi cảm thấy hơi buồn khi thấy rằng sau hơn 10 năm, không có câu trả lời nào thực sự nêu rõ làm thế nào một thứ như yêu cầu trong OP có thể được thiết kế theo kiến ​​trúc REST, do đó tôi cảm thấy cần phải làm điều này ngay bây giờ.

Đầu tiên, REST là gì?! Từ viết tắt REST hoặc ReST là viết tắt của "Chuyển giao trạng thái đại diện" và định nghĩa việc trao đổi trạng thái của tài nguyên theo một định dạng biểu diễn nhất định. Các định dạng đại diện là thủy triều cho loại phương tiện đàm phán. Trong trường hợp application/htmlđịnh dạng biểu diễn có thể là một luồng nội dung văn bản được định dạng HTML được hiển thị trong trình duyệt, có thể sau khi áp dụng một số định dạng biểu định kiểu để định vị các thành phần nhất định tại các vị trí nhất định.

Về nguyên tắc, REST là một sự khái quát hóa của Web có thể duyệt mà chúng ta đều biết, mặc dù nhắm mục tiêu tất cả các loại ứng dụng và không chỉ các trình duyệt. Do đó, theo thiết kế, các khái niệm tương tự áp dụng cho Web cũng áp dụng cho kiến ​​trúc REST. Một câu hỏi như làm thế nào để đạt được điều gì đó theo cách "RESTful" giải quyết xung quanh việc trả lời câu hỏi làm thế nào để đạt được điều gì đó trên trang Web và sau đó áp dụng các khái niệm tương tự lên lớp ứng dụng.

Một máy tính dựa trên Web thường có thể bắt đầu với một số "trang" cho phép bạn nhập một số giá trị để tính toán trước khi gửi dữ liệu đã nhập đến máy chủ. Trong HTML, điều này thường đạt được thông qua <form>các phần tử HTML dạy cho khách hàng về các tham số có sẵn để đặt, vị trí đích để gửi yêu cầu cũng như định dạng biểu diễn để áp dụng khi gửi dữ liệu đầu vào. Điều này có thể có nghĩa là như thế này:

<html>
  <head>
    ...
  </head>
  <body>
    <form action="/../someResource" method="post" enctype="application/x-www-form-urlencoded">
      <label for="firstNumber">First number:</label>
      <input type="number" id="firstNumber" name="firstNumber"/>

      <label for="secondNumber">Second number:</label>
      <input type="number" id="secondNumber" name="secondNumber"/>

      <input type="submit" value="Add numbers"/>
    </form>
  </body>
</html>

Mẫu ở trên tức là có hai trường đầu vào có thể được điền bởi người dùng hoặc bởi một số automata khác và khi gọi phần tử đầu vào gửi, trình duyệt sẽ xử lý định dạng dữ liệu đầu vào thành application/x-www-form-urlencodedđịnh dạng đại diện được gửi đến vị trí đích được đề cập thông qua phương thức yêu cầu HTTP được chỉ định, POSTtrong trường hợp này. Nếu chúng ta nhập 1vào trường firstNumberđầu vào và 2vào trường secondNumberđầu vào, trình duyệt sẽ tạo ra một đại diện firstNumber=1&secondNumber=2và gửi nó dưới dạng trọng tải cơ thể của yêu cầu thực tế đến tài nguyên đích.

Do đó, yêu cầu HTTP thô được cấp cho máy chủ có thể trông như thế này:

POST /../someResource
Host: www.acme.com
Content-Type: application/x-www-form-urlencoded
Content-Length: 28
Accept: application/html

firstNumber=1&secondNumber=2

Máy chủ có thể thực hiện tính toán và trả lời với một trang HTML khác có chứa kết quả của phép tính, vì yêu cầu chỉ ra rằng máy khách hiểu định dạng này.

Như Breton đã chỉ ra, không có URL hay URI "RESTful" nào. URI / URL là loại điều riêng của nó và không nên truyền đạt bất kỳ ý nghĩa nào cho khách hàng / người dùng. Trong mẫu máy tính ở trên, người dùng chỉ đơn giản là không quan tâm đến việc gửi dữ liệu tới đâu, chỉ quan tâm đến việc khi kích hoạt trường nhập dữ liệu, yêu cầu được gửi. Tất cả các thông tin cần thiết để thực hiện nhiệm vụ đã được cung cấp bởi máy chủ.

Một trình duyệt cũng có thể không nhận thức được rằng yêu cầu thực sự cung cấp cho máy tính một số tham số đầu vào, nó cũng có thể là một dạng đơn đặt hàng trả về đại diện biểu mẫu tiếp theo để tiếp tục quá trình đặt hàng hoặc một loại hoàn toàn khác nguồn. Nó chỉ đơn giản thực hiện những gì đặc tả HTML yêu cầu trong trường hợp như vậy và nó không quan tâm đến những gì máy chủ thực sự đang làm. Khái niệm này cho phép trình duyệt sử dụng cùng một định dạng đại diện để thực hiện tất cả các loại việc như đặt hàng một số thứ từ cửa hàng trực tuyến ưa thích của bạn, trò chuyện với những người bạn thân nhất của bạn, đăng nhập vào tài khoản trực tuyến, v.v.

Các affordance của một số yếu tố, chẳng hạn trong trường hợp nộp lĩnh vực đầu vào mà thường được trả lại như nút, định nghĩa những gì bạn nên đến với nó. Trong trường hợp của một nút hoặc một liên kết, về cơ bản nó sẽ cho bạn nhấp vào nó. Các yếu tố khác có thể truyền đạt chi phí khác nhau. Khả năng chi trả như vậy cũng có thể được thể hiện thông qua các mối quan hệ liên kết, tức là với preloadcác liên kết được chú thích về cơ bản cho khách hàng biết rằng nó có thể tải nội dung của tài nguyên được liên kết trong nền vì người dùng rất có thể sẽ lấy nội dung này tiếp theo. Các mối quan hệ liên kết như vậy tất nhiên phải được chuẩn hóa hoặc tuân theo cơ chế mở rộng cho các loại quan hệ như được xác định bởi liên kết Web .

Đây là những khái niệm cơ bản được sử dụng trên Web và cũng nên được sử dụng trong kiến ​​trúc REST. Theo "Chú Bob" Robert C. Martin, một kiến ​​trúc là về ý định và ý định đằng sau kiến ​​trúc REST là tách rời các máy khách khỏi các máy chủ để cho phép các máy chủ phát triển tự do trong tương lai mà không phải sợ chúng phá vỡ máy khách. Thật không may, điều này đòi hỏi rất nhiều kỷ luật vì nó rất dễ dàng để giới thiệu khớp nối hoặc thêm các giải pháp khắc phục nhanh để hoàn thành công việc và tiếp tục. Như Jim Webber đã chỉ ra trong kiến ​​trúc REST, với tư cách là nhà cung cấp dịch vụ, bạn nên cố gắng thiết kế một giao thức ứng dụng miền tương tự như trò chơi máy tính dựa trên văn bản của thập niên 70 mà khách hàng sẽ thực hiện cho đến khi họ kết thúc quá trình.

Rất nhiều cái gọi là API "REST" không may làm trong thực tế là tất cả mọi thứ trừ cái đó. Bạn thấy việc trao đổi dữ liệu chủ yếu dựa trên JSON được chỉ định trong tài liệu bên ngoài cụ thể API thường khó tích hợp một cách linh hoạt khi đang di chuyển. Định dạng của một yêu cầu cần trông như thế nào cũng được mã hóa vào tài liệu bên ngoài dẫn đến nhiều URI diễn giải để trả về các ty được xác định trướcthay vì sử dụng một số định dạng đại diện phổ biến được đàm phán trả trước. Điều này ngăn máy chủ thay đổi vì hiện tại khách hàng sẽ nhận được một định dạng dữ liệu nhất định (lưu ý không phải định dạng đại diện!) Cho các URI được xác định trước. Ngoài ra, việc trao đổi định dạng dữ liệu tùy chỉnh này còn ngăn khách hàng tương tác với các API khác vì "định dạng dữ liệu" thường được chuyển sang một API cụ thể. Chúng ta biết khái niệm này từ quá khứ từ các công nghệ RPC như Corba, RMI hoặc SOAP mà chúng ta lên án là xấu xa, mặc dù Peppol đã chuyển sang sử dụng lại bằng cách thay thế AS2 bằng AS4 làm giao thức chuyển mặc định như gần đây.

Liên quan đến câu hỏi thực tế, việc gửi dữ liệu dưới dạng tệp csv không có gì khác so với sử dụng application/x-www-form-urlencodedbiểu diễn hoặc nội dung tương tự. Jim Webber đã nói rõ rằng sau tất cả HTTP chỉ là một giao thức truyền tải mà miền ứng dụng của nó là chuyển tài liệu qua Web . Máy khách và máy chủ ít nhất phải hỗ trợ cả hai text/csvnhư được định nghĩa trong RFC 7111 . Tệp CSV này có thể được tạo do hậu quả của việc xử lý loại phương tiện xác định các thành phần biểu mẫu, thành phần đích hoặc thuộc tính để gửi yêu cầu cũng như phương thức HTTP để thực hiện tải lên cấu hình.

Có một số loại phương tiện hỗ trợ các biểu mẫu như HTML , HAL Forms , halform , ion hoặc Hydra . Tuy nhiên, hiện tại tôi không biết loại phương tiện tự động có thể mã hóa dữ liệu đầu vào thành text/csvtrực tiếp do đó có thể cần phải được xác định và đăng ký với sổ đăng ký loại phương tiện của IANA .

Tôi đoán việc tải lên và tải xuống bộ tham số hoàn chỉnh không phải là vấn đề. Như đã đề cập trước đó, URI mục tiêu không liên quan vì khách hàng sẽ chỉ sử dụng URI để truy xuất nội dung mới để xử lý. Lọc theo ngày làm việc cũng không nên khó khăn. Tuy nhiên, ở đây máy chủ nên ứng dụng khách với tất cả các khả năng khách hàng có thể chọn. Trong những năm gần đây, GraphQL và RestQL đã phát triển để giới thiệu một ngôn ngữ giống như SQL có thể được nhắm mục tiêu tại một điểm cuối nhất định để có được phản hồi được lọc. Tuy nhiên, theo nghĩa REST thực sự, điều này vi phạm ý tưởng đằng sau REST là a) GraphQL tức là chỉ sử dụng một điểm cuối duy nhất ngăn chặn việc sử dụng bộ nhớ đệm tối ưu và b) đòi hỏi kiến ​​thức về các trường có sẵn, điều này có thể dẫn đến việc kết nối các máy khách đến mô hình dữ liệu cơ sở của tài nguyên.

Kích hoạt hoặc hủy kích hoạt một số tham số cấu hình nhất định chỉ đơn giản là vấn đề kích hoạt các điều khiển hypermedia cung cấp khả năng chi trả này. Trong các biểu mẫu HTML, đây có thể là hộp kiểm đơn giản hoặc lựa chọn nhiều dòng trong danh sách hoặc loại đó. Tùy thuộc vào hình thức và phương thức mà nó xác định, sau đó nó có thể gửi toàn bộ cấu hình thông qua PUThoặc thông minh về các thay đổi được thực hiện và chỉ thực hiện cập nhật một phần thông qua PATCH. Cái thứ hai về cơ bản đòi hỏi một tính toán của biểu diễn thay đổi cho một bản cập nhật và cung cấp cho máy chủ các bước cần thiết để chuyển đổi biểu diễn hiện tại thành biểu diễn mong muốn. Theo đặc tả PATH, điều này phải được thực hiện trong một giao dịch để tất cả hoặc không có bước nào được áp dụng.

HTTP cho phép và khuyến khích một máy chủ xác nhận trả trước yêu cầu đã nhận trước khi áp dụng các thay đổi. Đối với PUT, các thông số kỹ thuật:

Máy chủ gốc NÊN xác minh rằng đại diện PUT phù hợp với bất kỳ ràng buộc nào mà máy chủ có đối với tài nguyên đích không thể hoặc sẽ không bị thay đổi bởi PUT. Điều này đặc biệt quan trọng khi máy chủ gốc sử dụng thông tin cấu hình bên trong liên quan đến URI để đặt các giá trị cho siêu dữ liệu đại diện trên các phản hồi GET. Khi biểu diễn PUT không phù hợp với tài nguyên đích, máy chủ gốc NÊN làm cho chúng nhất quán, bằng cách chuyển đổi biểu diễn hoặc thay đổi cấu hình tài nguyên hoặc phản hồi với thông báo lỗi thích hợp chứa đủ thông tin để giải thích tại sao biểu diễn không phù hợp. Mã trạng thái 409 (Xung đột) hoặc 415 (Loại phương tiện không được hỗ trợ) được đề xuất,

Ví dụ: nếu tài nguyên đích được định cấu hình để luôn có Loại nội dung "văn bản / html" và đại diện là PUT có Loại nội dung là "hình ảnh / jpeg", thì máy chủ gốc phải thực hiện một trong:

a. cấu hình lại tài nguyên đích để phản ánh loại phương tiện mới;

b. chuyển đổi biểu diễn PUT thành định dạng phù hợp với định dạng của tài nguyên trước khi lưu nó dưới dạng trạng thái tài nguyên mới; hoặc là,

c. từ chối yêu cầu với phản hồi 415 (Loại phương tiện không được hỗ trợ) cho biết rằng tài nguyên đích bị giới hạn ở "text / html", có lẽ bao gồm một liên kết đến một tài nguyên khác sẽ là mục tiêu phù hợp cho đại diện mới.

HTTP không xác định chính xác làm thế nào một phương thức PUT ảnh hưởng đến trạng thái của máy chủ gốc ngoài những gì có thể được thể hiện bằng ý định của yêu cầu tác nhân người dùng và ngữ nghĩa của phản hồi của máy chủ gốc. ...

Để tổng hợp bài đăng này, bạn nên sử dụng loại phương tiện hiện có cho phép bạn dạy khách hàng về các tham số đầu vào được yêu cầu hoặc được hỗ trợ, vị trí mục tiêu để gửi yêu cầu đến, thao tác sử dụng cũng như loại phương tiện yêu cầu phải được định dạng hoặc xác định yêu cầu của riêng bạn mà bạn đăng ký với IANA. Cái sau có thể là cần thiết nếu bạn muốn chuyển đổi đầu vào thànhtext/csvvà sau đó tải lên đại diện CSV lên máy chủ. Việc xác nhận phải xảy ra trước khi những thay đổi được áp dụng cho tài nguyên. URI thực tế không nên liên quan đến các khách hàng ngoài việc xác định nơi gửi yêu cầu đến và do đó, người triển khai dịch vụ có thể tự do lựa chọn. Bằng cách làm theo các bước này, bạn có thể tự do thay đổi phía máy chủ của mình bất cứ lúc nào và khách hàng sẽ không bị hỏng do hậu quả nếu họ hỗ trợ các loại phương tiện đã sử dụng.


0

Chỉnh sửa: Thật vậy, URI sẽ ngăn GETcác yêu cầu từ idempotent còn lại.


Tuy nhiên, để xác thực, việc sử dụng mã trạng thái HTTP để thông báo tính hợp lệ của yêu cầu (để tạo mới hoặc sửa đổi 'tham số' hiện tại) sẽ phù hợp với mô hình Restful.

Báo cáo lại bằng 400 Bad Requestmã trạng thái nếu dữ liệu được gửi là / không hợp lệ và yêu cầu phải được thay đổi trước khi được gửi lại ( Mã trạng thái HTTP / 1.1 ).

Điều này phụ thuộc vào việc xác nhận tại thời điểm gửi, thay vì trì hoãn nó như trong trường hợp sử dụng của bạn. Các câu trả lời khác có giải pháp phù hợp cho kịch bản đó.


URI có nghĩa là một định danh. Sử dụng một URL cụ thể sẽ không có tác dụng phụ. Hãy tưởng tượng một proxy sẽ làm gì với điều đó.
Breton

2
hoặc google, cho vấn đề đó. Tôi đã từng đọc một câu chuyện về một cửa hàng web có tất cả các sản phẩm của họ bị xóa bởi google vì loại ngu ngốc này.
Breton

0

Trong môi trường REST, mỗi URL là một tài nguyên duy nhất. Tài nguyên của bạn là gì? Một máy tính tài chính thực sự không có bất kỳ nguồn lực rõ ràng. Bạn cần đào sâu vào những gì bạn đang gọi tham số và rút tài nguyên. Ví dụ, lịch khấu hao cho khoản vay có thể là một nguồn. URL cho lịch có thể bao gồm ngày bắt đầu, thời hạn (tính theo tháng hoặc năm), khoảng thời gian (khi lãi gộp), lãi suất và nguyên tắc ban đầu. Với tất cả các giá trị đó, bạn có một lịch thanh toán cụ thể:

http://example.com/amort_cal/2009-10-20/30yrsfixed/monthly/5.00/200000

Bây giờ, tôi không biết bạn đang tính toán gì, nhưng khái niệm về danh sách tham số của bạn không có vẻ RESTful. Như một người khác đã nói, các yêu cầu của bạn ở trên nghe có vẻ nhiều XMLRPC hơn. Nếu bạn đang cố gắng cho REST, bạn cần danh từ. Tính toán không phải là danh từ, chúng là những động từ hoạt động trên danh từ. Bạn cần phải xoay nó để kéo các danh từ ra khỏi calcs của bạn.


5
Tôi nghĩ rằng hơi ngớ ngẩn khi sử dụng dấu gạch chéo ở đây, điều gì sẽ sai với amort_cal? Date = 2009-10-20 & type = 30yrsfixed & period = hàng tháng & Rate = 5.0 & initamount = 200000? REST không quan tâm miễn là nó là một tài nguyên. Thông số URI không quan tâm mặc dù. Làm thế nào để bạn tưởng tượng các liên kết tương đối để làm việc với một sơ đồ như thế này?
Breton

Bạn vẫn đưa ra một điểm tốt dù sao. Những "tham số" này thậm chí có cần được lưu trữ bên máy chủ không? Nếu đó chỉ là một phép tính tắt, tại sao không tạo một không gian ảo, nơi các tham số nằm trong URL. Miễn là bạn không thay đổi trạng thái nội bộ, nó sẽ ổn thôi.
Breton

1
Và "tham số" không áp dụng cho "tài nguyên". Tài nguyên là một thực thể duy nhất với một định danh duy nhất. Url của tôi xác định một tài nguyên duy nhất. URL được tham số hóa biểu thị một tập hợp các tài nguyên bạn chọn trong khi sử dụng các tham số.
jmucchiello

2
REST không dựa trên "Tài nguyên CRUDing". Việc dán tất cả các tham số truy vấn của bạn vào các phân đoạn đường dẫn không tự động tạo giao diện RESTful vì bây giờ bạn nghĩ rằng bạn có thể gọi mỗi hoán vị là tài nguyên. Thật không may, không có quy trình kỳ diệu nào mà bạn có thể áp dụng để xác định tài nguyên trong hệ thống của bạn là gì. Nó đòi hỏi thiết kế cẩn thận, không phải là một công thức cơ học.
Darrel Miller

2
Một lần nữa, kiến ​​trúc REST không CHĂM SÓC những gì trong URL. URL có nghĩa là mờ đục . Không quan trọng để nghỉ ngơi cho dù bạn sử dụng dấu gạch chéo về phía trước, dấu chấm phẩy hoặc trái tim unicode làm ngăn cách. Đọc cái này và trả lời cái này - không phải những gì bạn tưởng tượng tôi đang nói.
Breton
Khi sử dụng trang web của chúng tôi, bạn xác nhận rằng bạn đã đọc và hiểu Chính sách cookieChính sách bảo mật của chúng tôi.
Licensed under cc by-sa 3.0 with attribution required.