4 ms·
If your domain is built with all nouns as a core part of what it inherently already is (like a Database being built on "records" or "documents"), then a RESTful
by WClayFerguson 6y ago
If your domain is built with all nouns as a core part of what it inherently already is (like a Database being built on "records" or "documents"), then a RESTful interface for it "might" be workable, with the limited CRUD verbs.
However, a vast number of web developers (dare I say "most") became convinced the proper way to "think" about their architecture was "as if it were all nouns" (even when it obviously wasn't), because they thought they were having an "epiphany" about how to use REST
...when what they were really doing was conforming to software development "meme" (or trend)
- nordsieck 6y ago> However, a vast number of web developers (dare I say "most") became convinced the proper way to "think" about their architecture was "as if it were all nouns" (even when it obviously wasn't), because they thought they were having an "epiphany" about how to use REST I don't think "developers thinking their architecture was 'as if it were all nouns'" is somehow limited to REST or even web APIs. It's a fundamental part of objected oriented design philosophy. http://steve-yegge.blogspot.com/2006/03/execution-in-kingdom-of-nouns.html http://steve-yegge.blogspot.com/2006/03/execution-in-kingdom...
- WClayFerguson 6y agoI think a conversation between a web browser (SPA RPC) and a back-end server is best thought of as an RPC. Procedure calls are verbs if you ask me. Here's my own code that is such an API: https://github.com/Clay-Ferguson/quantizr/blob/master/src/main/java/org/subnode/AppController.java https://github.com/Clay-Ferguson/quantizr/blob/master/src/ma... You can point out that 80% of those API methods are resulting in some kind of CRUD method, and I'd agree, but nonetheless trying to make it a true REST API would be super awkward and verbose, imo, because lots of those functions result in multiple CRUD ops on multiple different types of data. When I design an API, I think: "What is this operation called? What data is best to send upstream, and what do I want to get back." Then I design the API. The API is a wrapper around an abstraction layer of functionality. REST is all about removing that abstraction layer which is moronic.
- tsimionescu 6y agoThis is all a matter of definitions. For example, from a syntactic point of view, Java has three verbs for all objects: "instantiate (new)", "call method" and "access field". An object has members, and you can use those 3 verbs to interact with the members of the object. In my experience, the nice part about designing APIs in a REST-like manner is that they encourage you to think in terms of observable operations. For example, instead of "calling" a long running blocking method, you create a resource that represents the long running operation, and now you can check its status while it is running, report progress, cancel it. Basically, when designing a REST API you think about the exact same things you are saying - what is the operation called? what data does it need, and what does it return? - and then you represent this as a resource that can be created with the right input, and that will point to a result resource for the final output. For example, my usual pattern for things outside of CRUD is something like this: --> POST .../operations/renderNode {ExecuteNodeRequest goes here} <-- 202 Accepted Location: .../operations/renderNode/891 --> GET .../operations/renderNode/891 <-- 200 OK {status: IN_PROGRESS, percentage: 78, ... (includes initial ExecuteNodeRequest params)} --> GET .../operations/renderNode/891 <-- 200 OK {status: SUCCESSFUL, percentage: 100, resultURL: .../operations/renderNode/891/result, ...} And then on GET .../operations/renderNode/891/result, you have the final result. Of course, if the operation finishes quickly enough, any of the polling steps can be omitted - e.g. it can directly return 200 OK and the result URL for the initial request. If you have WebSockets support, you can also be notified via WebSockets when execution finishes, instead of polling. It may look like more ceremony, but in general, for long running operations that will be called from a browser, this kind of approach is a requirement anyway, since the number of connections with a particular origin is extremely limited. Note that I also think your API would be much more concise as a REST API, since all of the miriad "setX", "getX", "createY" methods would be reduced to a few resources with multiple fields, that you can simply GET to see all fields, or PATCH to change a single field (or even change multiple fields in a single request).
- lmilcin 6y agoThe goal of REST isn't to be the RPC protocol. It is to be lower level protocol which uses simple verbs to transfer state. For example, SQL has simple verbs because it doesn't want to know what are the actual operations executed by the application (for example, verifying status of an existing process, checking optimisting lock, etc.) Another example are some remote memory interfaces which basically transfer blocks of memory back and forth without knowing what is the operation for. You build your higher level, business logic-aware protocol on top of it. The same way, REST is about intentionally not getting involved with the imperative style and instead provide transport protocol that will make it possible to refer to the things as resources, discover resource graph through hyperlinks, etc. The business logic is supposed to introduce changes to the object but use REST to only transfer representation of the changed state (Representational State Transfer) without burdening it with RPC details. That is why so many APIs fail to use REST effectively, because designers do not understand the goal and limitations of REST. It is conscious decision not only what the API does but also what it is not supposed to do. To update the user the REST-ful way would be to allow the client to fetch the user document, introduce changes client side with whatever logic the client wants and then transfer the representation of modified state back to the server with a simple verb (same way we interact with filesystem through reads and writes without kernel ever knowing what this is). The server decides what to do with these changes. Trying to burden the kernel with information about what the operation is is futile but that's what usually happens when people design "REST"-ful APIs.