**update: horray! so it is a journey of practice and understanding. ;) now i no longer feel so dumb.*
I have read up many articles on REST, and coded up several rails apps that makes use of RESTful resources. However, I never really felt like I fully understood what it is, and what is the difference between RESTful and not-restful. I also have a hard time explaining to people why/when they should use it.
If there is someone who have found a very clear explanation for REST and circumstances on when/why/where to use it, (and when not to) it would benefit the world if you could put it up, thanks! =)
REST is usually learned like this:
You hear about REST being using HTTP the way it was meant to be used, and from that you shun SOAP Web Services' envelopes, since most of what's needed by many SOAP standards are handled by HTTP in a simple, no-nonsense way. You also quickly learn that you need to use the right method for the right operation.
Later, perhaps years later, you hear that REST is more than that. REST is in fact also the concept of linking between resources. This often takes a while to grasp the full meaning of, but when you learn this, you start introducing hyperlinks into your responses so that clients can navigate your system without being coupled to how the server wants to name its resources (i.e. the URIs).
Even later, you learn that you still haven't understood REST! And this is because you find out that media types are important. You start making media types called application/vnd.example.foo+json and put hyperlinks in them, since that's already your understanding of REST.
Years pass, and you re-read Fielding's thesis for the umpteenth time, to see if there's anything you missed, and it suddenly dawns upon you what really the HATEOAS constraint is: It's about the client not having any notion of how the server's resources are structured, but that it discoveres these relationships at runtime. It also means that the screen in front of the user is driven completely by what is passed over the wire, so in fact, if a server passes an image/jpeg then that's what you're supposed to show to the user, not an error message saying "AtomProcessor can't handle image/jpeg".
I'm just coming to terms with #4 and I'm hoping the ladder isn't much longer! It's taken me seven years.
This article does a good job classifying the differences in several http application styles from WS-* to RESTian purity. What I like about this post is it reminds you that most of what we call REST really is something only partly in line with Roy Fielding's original definition.
InfoQ has a whole section addressing more of the "what is REST" angle as well.
In terms of REST vs. SOAP, this question seems to have a number of good responses, particularly the selected answer.
I would imagine YMMV, but I found it very easy to start understanding the details of REST after I realised how REST essentially was a continuation of the static WWW concepts into the web application design space. I had written (a rather longish) post on the same : Why REST?
Scalability is an obvious benefit of REST (stateless, caching).
But also - and this is probably the main benefit of hypertext - REST is ideal for when you have lots of clients to your service. Following REST and the hypertext constraint drastically reduces the coupling between all those clients and your server, which means you have more freedom when evolving/developing your service over time - you are not tied down by the risk of breaking would-be-coupled clients.
On a practical note, if you're working with rails - then restfulie is a great little framework for tackling hypertext on the client and server. Server side is a rails extension, and client is a DSL for handling state changes. Interesting stuff, check it out here: http://restfulie.caelum.com.br/ - I highly recommend the tutorial/demo vids they have up on vimeo :)
Content-Type: text/x-flamebait
I've been asking the same question lately, and my supposition is that
half the problem with explaining why full-on REST is a good thing when
defining an interface for machine-consumed data is that much of the
time it isn't. OK, you'd need a really good reason to ignore the
commonsense bits (URLs define resources, HTTP verbs define actions,
etc etc) - I'm in no way suggesting we go back to the abomination that
was SOAP. But doing HATEOAS in a way that is both Fielding-approved
(no non-standard media types) and machine-friendly seems to offer
diminishing returns: it's all very well using a standard media type to
describe the valid transitions (if such a media type exists) but where
the application is at all complicated your consumer's agent still
needs to know which are the right transitions to make to achieve the
desired goal (a ticket purchase, or whatever), and it can't do that
unless your consumer (a human) tells it. And if he's required to
build into his program the out-of-band knowledge that the path with
linkrels create_order => add_line => add_payment_info => confirm is
the correct one, and reset_order is not the right path, then I don't
see that it's so much more grievous a sin to make him teach his XML
parser what to do with application/x-vnd.yourname.order.
I mean, obviously yes it's less work all round if there's a suitable
standard format with libraries and whatnot that can be reused, but in
the (probably more common) case that there isn't, your options
according to Fielding-REST are (a) create a standard, or (b) to
augment the client by downloading code to it. If you're merely
looking to get the job done and not to change the world, option (c)
"just make something up" probably looks quite tempting and I for one wouldn't
blame you for taking it.
Related
I watched some videos, read some blogs about it. SO has many questions and answers on that subject but I can not find anywhere exact answer for my question.
Almost every question and answer has a lack of usage context.
I have one middle sized, asp.net-mvc, monolith application which is running in one process on IIS. I want to (refactor and) go all the way with DDD (and CQRS without separated storage for reads and writes for now) but for me it looks like impossible mission without breaking some rules/guides/etc.
Bounded Context
For example I have more than one BCs. Each should not cross their boundaries which means should not share their storage. Right?
It is not possible if you use the whole known (everywhere scattered over the web) solution to work with NHibernate session and UoW.
Aggregate Root
Only one AR should be modified in one transaction. When others ARs are involved should introduce eventual consistency (if I remember those are Eric Evans words).
I try to do it but it is not easy in app like that. Pub/Sub not working as desired because if event is published then all subscribers are take their action within one transaction (NSB/MT does that way).
If event handlers wants to modify others ARs they should be executed in separated transactions, right?
Is it possible to deal with it in monolith application (application where whole code works in one process)?
It is not possible if you use the whole known (everywhere scattered
over the web) solution
[...]
if event is published then all subscribers are take their action
within one transaction
I think you're setting yourself useless and harmful constraints by trying to stick to some "state of the art".
Migrating an entire application to DDD + CQRS is a massive undertaking. Some areas of it don't have well-documented beaten paths yet and you'll probably have a fair bit of exploration to do. My best advice would be to stay at a reasonable distance from "the way people do things". Both in traditional ASP.Net web apps because mainstream practices often don't match the way DDD+CQRS works, and in CQRS itself because the case studies out there are few and far between and most probably very domain specific, with a tendency to advocate the use of heavy tools which may not make sense in your context.
You may need to think out of the box, adopt things incrementally and refrain from goldplating everything. You'll be better off starting with very simple implementations that suit your needs exactly than throwing a ton of tools and frameworks at your codebase.
For instance, do you really need a service bus or could a simple Observer pattern suffice ?
Regarding NHibernate, most implementations out there use a (single) Session Per Request approach, but just because it's the most popular doesn't mean it's the only one. Have you tried using multiple ISessions (one for each BC) available at a more programmable level, such as per-action, or managed entirely manually ? Conversely, have you considered sharing a database between Bounded Contexts at first and see for yourself if that's bad or not ?
Not sure whether it is here to ask these basic questions about REST...
The more I try to understand REST and want to implement it, the more I get confused. I think probably because of those abstract words I see when people come to teach you what a REST is. For instance,
REST from wikipedia,
Representational state transfer (REST) is an abstraction of the
architecture of the World Wide Web; more precisely, REST is an
architectural style consisting of a coordinated set of architectural
constraints applied to components, connectors, and data elements,
within a distributed hypermedia system.
And from this link
Representations of resources should be uniform
Use hypermedia—not URL schemes or resource name mapping—to represent
relationships
Use a single entry to an API, hyperlink from there (hyperlink? why not hypermedia??)
Include a “self” link in your representations
REST doesn’t just mean spitting out ActiveRecord models as JSON (so what should you spit out??)
So, what does it mean by these abstract jargons below?
Representations,
resources,
URL schemes,
hypermedia (what the difference of it from hypertext or hyperlink???),
resource name mapping—to,
ActiveRecord models
Can you explain them in a concrete examples?
Representation is the name given for the complete set of bytes that are sent over the wire when you make a request to a resource using a link.
Resource is a any concept that is important to your application and you wish to expose it to a client application. A resource is identified by a URL.
Technically an URL Scheme is the first few bytes of a URL that appear before the colon. e.g. http, urn, ftp, file, etc.
However, I suspect in the context you are seeing it, it means a convention for organizing the paths segments and query string parameters of and URL and assigning a significance to those pieces of the URL.
From the perspective of REST, a server can create URL conventions, but clients should know nothing about those conventions.
Hypermedia is a classification of media types that support hyperlinks. Hypertext is an older term that is almost synonymous with hypermedia. In theory hypermedia does not need to be a text based format. So far I'm not aware of any hypermedia formats that are not hypertext.
Hyperlink, link and web link are synonymous.
Unfortunately these terms are abstract by definition. There are many different ways to implement these concepts.
ActiveRecord is an implementation concept that is often used to contain the data that will be used to build a representation of a resource. However, if you limit yourself to only being able to create resources from ActiveRecord instances, you will likely struggle to implement an effective REST API.
Representations of resources should be uniform - This makes no sense to me. There is a REST constraint called "Uniform Interface". However, this constraint refers to using a consistent interface to enable building layered applications. i.e. When a client wants to talk to server, you can slip a proxy, load balancer, cache in between and the client and server don't know the difference because the interface is consistent.
Use hypermedia - Hypermedia helps you to decouple your client and server to allow either to evolve independently. If this is not important to you (i.e. you can always deploy your client javascript at the same time as the website) then you are not going to get a whole lot of value out of it.
Use a single entry to an API - See previous point. If you need independent evolvability then explore some more.
Include a “self link in your representations And again...
REST doesn’t just mean spitting out ActiveRecord models as JSON REST is an architectural style of the boundary of your application. Exposing ActiveRecords as Resources ties your client to implementation details of your server. Also, HTTP is limited to just a few methods (GET, PUT, POST, DELETE, OPTIONS, HEAD). In order to compensate for this limited vocabulary you will need to create Resources that are nothing to do with records in a database.
Many are quick to point out that "REST," as typically used, isn't really REST, as originally defined.
There's endless (and pointless) discussion and debate around this topic, but from a practical standpoint I prefer to think about "resources," and how best to expose them.
The concept of REST may be instructional in this regard, even if common implementations diverge from the source.
In the end, we're programmers and have to build things that meet today's objectives, knowing they won't be tomorrow's.
We are developing the following setup:
A rails webapp allows users to make requests for tasks that are passed on to a Scala backend to complete, which can take up to 10 seconds or more. While this is happening, the page the user used to make the request periodically polls rails using AJAX to see if the task is complete, and if so returns the result.
From the user's point of view the request is synchronous, except their browser doesn't freeze and they get a nice spinny thing.
The input data needed by the backend is large and has a complex structure, as does the output. My initial plan was to simply have the two apps share the same DB (which will be MongoDB), so the rails app could simply write an id to a 'jobs' table which would be picked up by the scala backend running as a daemon, but the more I think about it the more I worry that there may be lots of potential gotchas in this approach.
The two things that worry me the most is the duplication of model code, in two different languages, which would need to be kept in sync, and the added complexity of dealing with this at deployment. What other possible problems should I take into account when assessing this approach?
Some other possibilities I'm looking at are 1) making the Scala backend a RESTful service or 2) implementing a message queue. However, I'm not fully convinced about either option as they will both require more development work and it seems to me that in both cases the model code is effectively duplicated anyway, either as part of the RESTful API or as a message for the message queue - am I wrong about this? If one of these options is better, what is a good way to approach it?
I have used several times resque for similar problems and Ive been always very happy with it, it gives you all you need to implement a job queue and is backed on redis. I would strongly suggest you to take a look at it
Don't take me wrong, but, for this project what does Rails provide that Scala does not?
Put another way, can you do without Scala entirely and do it all in Rails? Obviously yes, but you're developing the back end in Scala for a reason, right? Now, what does Scala provide that Rails does not?
I'm not saying you should do one or the other, but maintaining duplicate code is asking for trouble/complication.
If you have a mountain of Ruby code already invested in the project, then you're committed to Rails, barring a complete Twitter-esque overhaul (doesn't sound like that's an option nor desired).
Regardless, not sure how you are going to get around the model duplication. Hitting a Mongo backend does buy you BSON result sets, which you could incorporate with Spray, their excellent implementation of Akka, out-of-the-box REST, and JSON utilities.
Tough problem, sounds like you're caught between 2 paradigms!
I have a decent understanding of RESTful urls and all the theory behind not nesting urls, but I'm still not quite sure how this looks in an enterprise application, like something like Amazon, StackOverflow, or Google...
Google has urls like this:
http://code.google.com/apis/ajax/
http://code.google.com/apis/maps/documentation/staticmaps/
https://www.google.com/calendar/render?tab=mc
Amazon like this:
http://www.amazon.com/books-used-books-textbooks/b/ref=sa_menu_bo0?ie=UTF8&node=283155&pf_rd_p=328655101&pf_rd_s=left-nav-1&pf_rd_t=101&pf_rd_i=507846&pf_rd_m=ATVPDKIKX0DER&pf_rd_r=1PK4ZKN4YWJJ9B86ANC9
http://www.amazon.com/Ruby-Programming-Language-David-Flanagan/dp/0596516177/ref=sr_1_1?ie=UTF8&s=books&qid=1258755625&sr=1-1
And StackOverflow like this:
https://stackoverflow.com/users/169992/viatropos
https://stackoverflow.com/questions/tagged/html
https://stackoverflow.com/questions/tagged?tagnames=html&sort=newest&pagesize=15
So my question is, what is best practice in terms of creating urls for systems like these? When do you start storing parameters in the url, when don't you? These big companies don't seem to be following the rules so hotly debated in the ruby community (that you should almost never nest URLs for example), so I'm wondering how you go about implementing your own urls in larger scale projects because it seems like the idea of not nesting urls breaks down at anything larger than a blog.
Any tips?
Don't get too bogged down by the "rules" in the Ruby community. The idea is that you shouldn't go overboard when nesting URLs, but when they're appropriate they're built into the Rails framework for a reason: use them.
If a resource always falls within another resource, nest it. Nothing wrong with that. Going deeper than one can sometimes be a bit of a pain because your route paths will be very long and can get a bit confusing.
Also, don't confuse nesting with namespacing. Just because you see example.com/admin/products/1234/edit does not mean that there's any nesting happening. Routing can make things look nested when they're actually not at the code level.
I'm personally a big fan of nesting and use it often (just one level -- occasionally two) in my applications. Also, adding permalink style URLs that use words rather than just IDs are more visually appealing and they can help with SEO, whether or not they're nested.
I believe the argument for or against REST and/or nesting in your routes has much to do with how you want to expose your API. If you do not care to ever expose an API for your app publicly, there is an argument to be made that strict adherence to RESTful design is a waste of time, particularly if you disagree with the reasoning behind REST. Your choice.
I find that thinking about how a client (other than a browser) might access information from you app helps in the design process. One of the greatest advantages of thinking about your app's design from an API perspective is that you tend to eliminate unnecessary complexity. To me this is the root of the cautions you hear in the Rails community surrounding nested routes. I would take it as an indication that things are getting a bit complicated and it might be time to step back and rethink the approach. Systems "larger than a blog" do not have to be inherently complex. Some parts might be but you also may be surprised when you approach the design from a different perspective.
In short, consider some of the dogma you might hear from certain parts of the community as guides and signals that you may want to think more deeply about your design. Strict REST is simply another way to think about how you are structuring your application.
If you're writing something by yourself, whether to practice, solve a personal problem, or just for entertainment, is it ok, once in a while, to have a public field? Maybe?
Let me give you an analogy.
I come from a part of the world where English is not the primary language. But it’s necessary for all things in life.
During one of those usual days during my pre-teen years I said something very funny in English. Then my Dad said, “Son, think in English. Then you’ll get fluent”
I think it applies perfectly to this situation.
Think,try and question best practices in your playground. You will soon realize what’s best for what.Why are properties needed in the first place. Why should this be public? Why should I not call a virtual member from the constructor? Let me try using "new" modifier for a method call. What happens when I write 10 nested levels of if-then-else and try reading it again after 10 days. Why the heck should I use a factory pattern for a simple project. Et cetera.
And then you’ll realize without shooting at your foot, why design patterns are patterns...
I think it's reasonable if you're consciously throwing the code away afterwards. In particular, if you're experimenting with something completely different, taking shortcuts makes sense. Just don't let it lead to habits which cross over into "real" code.
Violating general principles is always "ok"! It is not an error to violate a principle but it is a trade off. The cost of not writing clean code will be higher the longer your software will survive. My take on this is: If in doubt make it clean!
Of course it's OK. It's your code, you can do whatever you want with it. Personally, I try to stick to good practice also in my private code, just to make it a natural habit so I don't have to think about it.
The short answer is yes, if you believe that you're gaining a lot by making things public instead of private with accessors you are welcome to do so. Consistency, I think, is the biggest thing to keep in mind. For instance, don't make some variables straight public, and some not. Do the same across the board if you break with best practices. It comes back to a trade-off. Almost no-one follows many of the IEEE specs for how Software Engineering should be executed and documented because the overhead is far too great, and it can get unmanageable. The same is true for personal, light-weight programming. It's okay to do something quick and dirty, just do not get used to it.
Public members are acceptable in the Data Transfer Object design patter:
Typically, the members in the Transfer Object are defined as public, thus eliminating the need for get and set methods.
One of the key advantages of OOP is for scaling and maintainability. By encapsulating code, one can hide the implementation. This means other programmers don't have to know the implementation, and can't change your object's internal state. If you language doesn't support properties, you end up with a lot of code which obfuscates and bloats your project. If the code doesn't need to be worked on by multiple programmers, you aren't producing a reusable component, and YOU are the maintenance programmer, then code in whatever manner allows you to get things done.
Does a maid need to make his/her own bed in the morning in order to practice properly making a bed?
Side note: it also depends on the language:
In Scala, according to the Uniform Access Principle, clients read and write field values as if they are publicly accessible, even though in some case they are actually calling methods. The maintainer of the class has the freedom to change the implementation without forcing users to make code changes.
Scala keeps field and method names in the same namespace.
Many languages, like Java, keep field and method names in separate namespaces.
However, these languages can’t support the uniform access principle as a result, unless they build in ad hoc support in their grammars or compilers.
So the real question is:
What service are you exposing (here by having a public field)?.
If the service (get/set a given type value) makes sense for your API, then the "shortcut" is legitimate.
As long as you encapsulate that field eventually, is it ok because you made the shortcut for the "right" reason (API and service exposure), versus the "wrong" reason (quick ad-hoc access).
A good unit test (thinking like the user of your API) can help you check if that field should be accessed directly or if it is only useful for internal development of other classes within your program.
Here's my take on it:
I'd advise avoiding public fields. They have a nasty habit of biting you later on because you can't control them. (The word you're looking for here is volatility.) Further, if you decide to change their internal implementation, you have to touch a lot more code.
Then again, that's what refactoring tools are for. If you have a decent refactoring tool, that's not nearly so difficult.
There is no silver bullet. I can't repeat this enough. If you have work to do, and you need to get it done in a hurry, writing one line of code instead of eight (as is the case in Visual Basic) is certainly faster.
Rules were meant to be broken. If a rule doesn't necessarily apply in your case, don't use it. Design patterns, coding guidelines, laws and best practices should not be treated as a straightjacket that requires you to needlessly complicate your code to the point where it is enormously complex and difficult to understand and maintain. Don't let someone force you into a practice just because it's popular or "standard" when it doesn't fit your requirements.
Again, this is a subjective opinion, and your mileage may vary.