List

Designing Hypermedia APIs

Designing Hypermedia APIs

by Steve Klabnik

In the talk titled "Designing Hypermedia APIs" at RailsConf 2012, Steve Klabnik explores how to create effective APIs that truly leverage the power of the web and HTTP, moving beyond traditional RESTful designs. He begins by addressing the misconceptions around REST in Rails, illustrating that many developers feel dissatisfied with its implementation. Steve asserts that while Rails has popularized REST, it does not fully embody the original principles of REST advocated by Roy Fielding in his dissertation. Here are the key points discussed:

  • Rest vs. Hypermedia: Klabnik emphasizes a shift from typical REST APIs to Hypermedia APIs, which enhance client-server interactions through links and guiding processes rather than relying solely on URL endpoints.
  • Importance of Learning: Steve shares his personal journey of understanding REST and hypermedia, indicating the significance of continuous learning in software development.
  • Pros and Cons: Hypermedia APIs allow for better scalability and change management but may introduce latency issues, making them unsuitable for applications requiring immediate responses.
  • Design Steps: He outlines five critical steps for building a hypermedia API: evaluating business processes, creating a state machine based on those processes, determining media type needs, designing a suitable media type, and implementing the API.
  • Case Study: Klabnik discusses a practical example involving an API that wraps the W3C HTML validator, employing a structured format to improve usability and flexibility in processing requests.
  • Media Type Design: The importance of building or leveraging existing media types to drive hypermedia functionality in JSON is also discussed.

In conclusion, Steve Klabnik advocates for a future where APIs evolve to be more adaptable, guiding clients through interactions rather than simply serving data. This results in a more effective and user-friendly approach to building web applications, emphasizing the long-term benefits of thoughtful API design over short-term efficiency. Through hypermedia, developers can foster robust, scalable applications that are more responsive to user needs and business changes.

Rails did a lot to bring REST to developers, but its conception leaves the REST devotee feeling a bit empty. "Where's the hypermedia?" she says. "REST isn't RPC," he may cry. "WTF??!?!" you may think. "I have it right there! resources :posts ! What more is there? RPC? Huh?"

In this talk, Steve will explain how to design your APIs so that they truly embrace the web and HTTP. Just as there's an impedance mismatch between our databases, our ORMs, and our models, there's an equal mismatch between our applications, our APIs, and our clients. Pros and cons of this approach will be discussed, as well as why we aren't building things this way yet.

Rails Conf 2012

00:00:24.640 if you want to follow along on github I have this presentation you know it's a show-off presentation so the slides are
00:00:31.730 also up there so if you want to see the latest slide stuff and you know I can
00:00:37.580 pretend you're not tweeting and not paying attention to me and you're just following my slides so that's the link
00:00:43.400 to the to the show off if you want to like follow along at home yeah so
00:00:50.170 alright this is a talk called designing hypermedia api's first of all hello
00:00:56.540 everybody I'm Steve thank you for coming to this awesome railsconf first thing in
00:01:02.060 the morning it's bright and early and there was a pre-party last night so I appreciate waking up at 10:30 a.m. which
00:01:08.360 is always difficult if you don't know me and what I do primarily i hack on
00:01:13.730 Hackett II hack which is originally created by Y the lucky stiff to teach programming to kids and other people via
00:01:21.650 Ruby so I try very hard to not make it just for kids to make it anybody to be
00:01:27.500 able to learn how to program so that's fun I also teach classes with jump start lab so all teaching all the time so if
00:01:34.520 your team needs to get better at Ruby and or rails give us a call we run the best training classes on earth we're
00:01:41.360 doing the Hunger Academy program with LivingSocial right now so that's pretty awesome taking people who have never
00:01:47.330 been developers before and turning them into professional developers at LivingSocial so it's pretty cool
00:01:53.170 anyway this this talk is sort of about a journey that I went on in the in sort of
00:02:02.240 this the spirit of like a Native American spirit trip right or like whatever our you know conception of that
00:02:08.929 is be like not real one but the the idea of one so I sort of like went wandering into the desert to find myself and then
00:02:15.970 came back you know totally disgusting not having shower and I'm like guys guys I saw the answer out there in the desert
00:02:23.260 and I have to share it with all of you and you're like yeah sure Steve whatever but I sort of have this continuous idea
00:02:31.030 a personal ethic of always learning so I always like to be learning new things if
00:02:36.460 they're program related or not programming related and whenever I hear someone say something
00:02:41.950 whenever here's someone that I respect or that I know knows a lot about a topic and they say something and I don't
00:02:47.470 understand what they're saying or I think they're wrong I always make a mental note like you know Kota Hale is
00:02:53.860 not stupid but he thinks that rails is bad someday I should figure out why he thinks that because I respect Coda's
00:03:00.250 opinion and so this happened with rest one time I heard a lot of people who knew what they were talking about say
00:03:05.290 rails his idea of rest is not actually rest and so I was like huh that's kind
00:03:10.900 of weird I wonder why they think that and so eventually one you know when I'm bored sometimes I will be like what is
00:03:16.870 on the list of things that I don't know about yet let me go look into that see why they would have that opinion or see
00:03:22.390 what they meant when they said that this is the truth and so one day I decided to do that for rest and I said holy crap
00:03:28.630 rails rest is not actually real rest and so then you know I'm a really big fan of
00:03:35.500 lean as a methodology for startups and for projects and so I decided to essentially lean start up a book I said
00:03:42.100 okay everyone I have learned why rails is not actually rest so I'm gonna write a book about it and it's not written yet
00:03:48.670 here's an email forum where you can put in your name and I'll email you when it's ready and I did that to see if my
00:03:55.270 laptop would fall asleep I did that to see if anybody cared other than me right
00:04:00.730 because the last thing I want to do is spend a ton of time yeah come on the
00:04:05.800 last thing I want to do is spend a ton of time writing something and they have no one care right so I decided to see
00:04:10.900 cool does it does anyone else care about this topic and it turns out that a lot of you did so I spend the next eight months of my life researching to really
00:04:17.680 make sure I knew my stuff because you know the the last thing that you want to do is tell everyone you're an expert not be an expert right so I spent a
00:04:25.000 bunch of time reading everything there is relating to rest and this this presentation is sort of a small
00:04:30.190 synthesis of what I've learned and in this book that I'm writing books sort of thing is like the bigger synthesis of
00:04:36.490 what I've learned and we'll talk about that later so the first thing I want to say is that like rest is over if you've
00:04:42.490 seen this Portlandia sketch it actually has a much deeper meaning if you think about what happens in the sketch with
00:04:47.590 what I'm saying it's actually a pretty deep reference but basically if you're
00:04:52.720 trying to convince someone to change their opinion the last thing that you want to do is tell them they're stupid right so like if you are aggressive with
00:04:59.500 people they're not going to change their opinion they're gonna dig in and fight back so if I say like hey you guys don't
00:05:06.370 actually know what rest is because you're stupid your first reaction to say you know Steve you suck uh you don't
00:05:12.700 know what you're talking about and it's not a productive way to change people's opinions secondarily rest is kind of bad
00:05:18.430 branding does anyone know why it's representational state transfer exactly
00:05:24.340 right it totally is meaningless and this is not really Fielding's fault whose dissertation defined what it is to be
00:05:30.580 restful when you write academic papers you are not concerned about marketability right like ROI it just
00:05:36.160 wants to go do his stuff and he doesn't care and so it's sort of not his fault that this buzzword is essentially totally meaningless and so in that sort
00:05:44.200 of spirit since no one knows what it actually means and everyone uses it wrong rather than try to fight over the
00:05:50.260 term rest and be like this is the right rest it's much more productive to invent yet another buzzword so that's sort of
00:05:56.530 what be the people the rest afar Ian's who really care about what rest means a
00:06:01.780 certain group of us have decided that that it's not worth that battle it's not going to be productive and no one is
00:06:08.500 going to care so as far as I'm concerned rails does rest perfectly so in the rest
00:06:13.780 of this talk when I say rest I will be meaning rails an idea of rest not the real idea of rest and so that's sort of
00:06:20.890 yet to like to to move forward and have a productive discussion this also doesn't mean that this is bad so like
00:06:27.100 you know what DHH said earlier today right like people said that rails rest was useless wanker II and now we all
00:06:33.760 consider it the default and I would totally rather work with a rails ish rest API then soap or all the other like
00:06:41.080 really crappy api's we had before like it is fundamentally a good thing but I think that we can do better right so in
00:06:47.710 that sort of spirit of like not resting on our laurels if we really want to move forward with really large applications
00:06:53.710 and really awesome API is like I think that we can do better than we're doing currently and so this is a talk about how to move forward from the sort of
00:07:00.220 standard API so that we all know and use today to something that's better so instead of REST API s we're going to
00:07:07.360 talk about hypermedia api's and so this communicates much more effectively what
00:07:13.810 i'm actually talking about if you know what hypermedia is so basically
00:07:19.389 hypermedia is the idea you have media or the older school is text so hypertext
00:07:25.090 you have this text document or other form of media and you add links to it that's the hyper part so it's it's hyper
00:07:31.539 as the prefix meaning like above or beyond so this is beyond just regular text there are links that connect things
00:07:37.090 together so fundamentally hyper media api's are about transferring text documents or other kinds of media that
00:07:43.479 have links to connect them to the rest of the world hyper media api's and there's sort of a reason that we we talk
00:07:49.630 about why this matters and why it's important it's also a really good name because it points out the fundamentally
00:07:55.570 thing that's wrong with the way that with or shouldn't say I should stop saying wrong even like what's different
00:08:01.240 about it then the rails idea of things like how many of you returned links in your JSON representations to other stuff
00:08:08.349 in your API right you don't so this is like the fundamental difference maybe okay some of you do this like some
00:08:13.780 people yeah who have heard me talk before or like of course I do now that I listen to you but we don't do this so
00:08:19.690 this is this is the like fundamental difference in what I'm talking about versus what we do today is these links
00:08:25.330 and so why should you bother right let's like before even talking about the
00:08:31.270 details let's talk about why you should care about what I have to say so basically hypermedia designs scale
00:08:36.640 better they're more easily changed and they promote decoupling and encapsulation with all of the software
00:08:41.740 engineering benefits that those things bring I really really liked again to reference DJ's dhhs talked earlier too
00:08:48.380 which I don't 100% agree with but I really agree with parts of it so one of the things that he sort of alluded to is
00:08:54.590 that we as developers are really good at saying things like I love change I love decoupling I love encapsulation
00:09:02.060 and then we do a direct sesor adder accessor at our accessor and we you know make these huge classes that go on for
00:09:10.100 miles right like if you ask anyone like do you write code that is very tightly coupled you'll say course not
00:09:17.030 Wendy Winn Don Knuth made the idea of literate programming he said that one of the reasons he likes the name literate
00:09:23.210 programming is that it implicitly implied that everyone else's programs were illiterate so unfortunately like our Roy Roy
00:09:33.770 fielding actually said like api's today have an X rated level of coupling going on like we we have incredibly tight
00:09:40.790 coupling between the clients on the server and you feel that pain all the time you just don't know that it's painful and that you can do better so
00:09:46.790 this is like radically decoupling things now the negatives this is not like any
00:09:53.150 architectural choice there are pros and their cons and sometimes those cons matter and so this is not a universally
00:09:59.300 good way of building things the downside mostly comes down to latency so if you need something to
00:10:06.320 happen in microseconds then rest is not for you or hypermedia api's are not for
00:10:11.360 you caches are one way that these api's scale and as the joke goes there are two
00:10:17.180 hard problems in computer science naming things cache invalidation and off-by-one errors so like cache invalidation is
00:10:23.630 really freaking hard and it's difficult to get right and so that's that's an inherently difficult problem also since
00:10:31.010 it tends to be textual or these if these api's are sent via text they won't be as
00:10:36.470 efficient on an individual level as like a binary protocol so if you compare a jate json to be sawn for example like
00:10:42.080 beasts on is much smaller because this is custom binary representation of what was textual and their advantages to the
00:10:47.510 text but it means that it's much bigger to transfer stuff and usually that doesn't matter but sometimes it does so like if that matters to you then this
00:10:54.380 may not be the appropriate thing to do so keep these cons in mind so Roy
00:11:00.950 fielding has this really great quote that I enjoy quite a bit rest is software design on the scale of decades
00:11:06.950 every detail is intended to promote software Lin longevity and independent evolution many of the constraints are
00:11:12.350 directly opposed to short term efficiency unfortunately people are fairly good at short term design and really awful at long term design and
00:11:19.190 this is just I really don't like appeals to human nature I think the human nature is kind of like not true in a lot of
00:11:26.360 ways but it's very natural for people to be thinking in the short term right like
00:11:31.910 I am wearing these Vibrams right now for example I go to the gym like once or
00:11:37.160 twice a month right cuz like I'm like I need to go running right there's a 5k at railsconf but then I like need to play
00:11:43.430 Starcraft or like something comes up and I don't go to the gym right and I know that like for my long-term health if I
00:11:49.280 run I will be more healthy in the long term but that's like far away that's tomorrow right so you know my mother
00:11:55.850 would say that like getting tattoos and like earrings and and like you know hair and stuff like that's gonna hurt you in
00:12:01.130 the long term and I'm not thinking about that so people are just in general do this right so we we need to release this
00:12:08.030 weekend screw if the software is good or not that release is going out on Friday because we have a deadline and so we
00:12:15.200 tend to do this a lot we sort of make short-term decisions that come back to bite us later right like every time I
00:12:21.560 write code that doesn't have tests behind it I'm like yeah I know how to write code without tests and then six
00:12:26.660 months later I'm like why did I not write any tests so you know it happens
00:12:31.910 so these are the two big things that are like a big deal longevity and independent evolution that's the true
00:12:38.600 benefit and that's what I see that we fail at today with our api's currently right you release a new version of your
00:12:44.150 API and all the old stuff breaks or you force people to upgrade your we we have this like churn things don't go for a
00:12:50.720 long time like we could be building software on the scale of decades like HTML has has survived for like 30 years
00:12:58.040 now right like the world wide web is the largest information system that we've ever built as humanity which is kind of
00:13:03.590 crazy and yeah in general like coupling is the enemy this is sort of a personal theme I've been on lately with like
00:13:09.140 testing via mocks and like a bunch of other things but like software coupling is is the true
00:13:14.670 enemy of being able to change your software quickly and easily which is one of my favorite metrics on code quality
00:13:21.060 right like you can change your code easily it's good code coupling is the enemy of all that so I guess actually
00:13:29.310 before I start talking about this I'm gonna go back for a second to this longevity independent evolution bit and that thing like like the web is the
00:13:36.900 largest information system that we have ever built it is humanity's crowning achievement as far as I'm concerned like
00:13:43.050 the web is awesome right but it's also really really massive so in 2010 Google
00:13:50.040 was the largest single entity on the web and Google has like three blessed
00:13:55.170 languages right they allow you to use Java they allow you use C++ and they allow you use Python in the last couple
00:14:01.110 years they've actually started discouraging the use of Python because Python cannot handle a Google scale and that's not really a knock on Python I
00:14:07.620 mean ruby is not on that list at all right but like Google accounted for eight percent of web traffic in 2010 so
00:14:14.250 if only two languages are efficient enough to handle something that is one
00:14:19.860 to two orders of magnitude smaller than the web in general right like that scale like web scale it's really unfortunate
00:14:25.440 that web scale became a meme is because like web scale is truly a thing like the world wide web is incomprehensible large
00:14:32.130 and it works right the fact that I'm like on the internet right now and so are you and you're like beaming the
00:14:38.520 signal over there to that router and then it's going like somewhere else and then back instantly is it's totally
00:14:44.010 magic right and we all know as programmers that all of our software is crappy right so like all of the Ricky
00:14:50.070 deenis of these things built on top of each other like it's it's intense so anyway the point is that most of these
00:14:55.770 things need to happen to handle a decentralized web that's made up of a ton of different entities that all work
00:15:02.220 together right like all of us work for well I mean everybody here works for Groupon or LivingSocial right but if if
00:15:08.670 you don't like the other people that exist somewhere outside of that like have to cooperate to make the web work
00:15:14.580 and so these kinds of design choices are really important to handle this massively decoupled huge information
00:15:21.600 network anyway so there are two rules of what makes the hypermedia API
00:15:27.850 one of the problems with rest is that its proponents have been actively hostile to explaining what it really
00:15:34.060 means and why you should care so I made it simple two things you use HTTP properly with an asterisk and then you
00:15:40.750 use hypermedia to guide clients through your business process the asterisk is there because technically you don't have
00:15:46.569 to use HTTP you can use any protocol you want but in reality you should use HTTP and the reason is that my slides don't
00:15:55.540 advance there we go this is the constraints that define rest in Roy
00:16:02.560 Fielding's dissertation what is up here does not really matter the important part is that if you use HTTP properly
00:16:09.459 you get all of these checked off except for that sub constraint on the uniform interface constraint everything else
00:16:16.449 it works like those are all exist by just following web standards and using HTTP and URI and all those other things
00:16:22.750 the way they were meant to be used there are a couple small exceptions but we're gonna gloss over that because this is a 45-minute talk but rule number two the
00:16:30.490 hypermedia to guide your clients through the business process part that is the one constraint here that does not exists
00:16:36.579 so use HTTP properly and then guide people through your business process
00:16:41.620 we're gonna spend the rest of this talk discussing this last little tiny bullet point because it's the hard one it's the
00:16:47.170 one that can't be handled by standards bodies you have to actually do it yourself and that's the reason why HTTP
00:16:52.630 does not give it to you is because it's about the content of the messages you send over the wire and that really is is
00:16:58.089 not standard in the same way like it's not a protocol level concern it's an application level concern so that's all
00:17:04.539 it takes use links use HTTP correctly this is not
00:17:09.579 using HTTP correctly even though it is right so like this is a valid HTTP request that will work but it violates
00:17:16.750 certain semantics that can't be covered by the standard right like we we can say in the standard that something should
00:17:22.270 happen that way but just because the computer makes it works the right way does not mean it's following the intention of the standards this is what
00:17:28.539 I mean by properly right like this is a valid HTTP request it's just not a semantically valid HTTP request and
00:17:35.190 we're past that with rails but when I talk to people who are not Ruby developers sometimes they're not on this
00:17:40.440 yet so anyway so now we're gonna talk about five steps to actually build an
00:17:45.690 API in this manner and these are sort of rough guidelines this is also talking entirely about the server if we have
00:17:52.049 some time at the end usually this talk is half an hour and I have 45 minutes so we might spend a little bit of time talking about client stuff at the end
00:17:57.360 but we're gonna talk mostly about server-side things today because this is railsconf or building server's not clients that's for the JavaScript people
00:18:04.190 which is not us of course anyway so there's these are the five steps to doing a server you evaluate
00:18:11.549 your business processes you create a state machine that represents them you use that state machine to evaluate your
00:18:17.009 media type needs you create or use existing media types and then you implement it with the magical hand wavey
00:18:23.370 then build it right so you notice there's nothing about URLs there's nothing about objects there's nothing
00:18:29.669 about routes so these things are totally irrelevant and let's talk about all
00:18:36.360 these things a wild example appears I like to one of
00:18:41.730 the other things about this topic is that it's really abstract so I like to to always when I'm looking at something
00:18:48.600 that's about web standards I'm reading something and I have these this general rule I try to think of a concrete
00:18:54.779 example and then apply the abstract idea to that example to see how it works so
00:19:00.539 you'll often hear people talk about like web browsers is the perfect API client and rest people tend to do this all the
00:19:06.840 time and they're like you know HTML and the web browsers are like perfect and the exact way that things work so if you
00:19:12.720 want to read Roy Fielding's dissertation it's really abstract and it's really difficult in the like terminology if
00:19:18.809 you're not familiar with it but that's how you have to do is like think about the concrete example and how that abstract idea applies to the concrete
00:19:24.870 example so we're going to build an API for an example service to explain this
00:19:29.970 abstract idea in these steps so if you don't know about mendicant university it's a really cool project by Greg Brown
00:19:36.299 to help intermediate Ruby developers become awesome Ruby developers and one of their students built this service
00:19:41.490 called w3c love basically it wraps the w3c HTML validator so if you've ever
00:19:48.509 used that before which hopefully you do it only lets you put in one web page at a time like I have a website with tons of pages
00:19:54.230 right and that's super lame to type them in every single time so we wrote this gem called w3c love that lets you submit
00:20:00.050 a website it crawls your site validates all the pages and gives you a report back on if they've passed the validator
00:20:06.440 or not it's super cool I've been meaning to make like a integration test that does this some time which would be really neat right like before deploy
00:20:12.860 make sure your pages are valid anyway so this is what it looks like today and
00:20:18.170 when Jamie came to me and said Jaime I came to me and said hey what you know what should I do with this API this sort
00:20:24.830 of looks like what you would imagine a ret like if you were building an API to do this this is what I think that you would build as well so basically to
00:20:31.340 check a website you submit a get request to this URL and you pass in a get
00:20:37.730 parameter with the URI of the site but you want to check and then it returns
00:20:43.250 you a bunch of JSON and it gives you this like was it successful in scraping how many pages did it look at what how
00:20:49.550 many errors were there which is like a million because we don't ever think about these things and like individual
00:20:54.950 ones for every page and how many errors and what they were right big giant message a song there's also this web
00:21:00.770 pages service which basically gives you one page so if the first thing crawls this gives you the link to one of them
00:21:06.320 and it's their first of all for convenience because if you're gonna use the gem to validate multiple pages you probably want to do one page and because
00:21:12.170 it needs to be built to build the multi page crawler right so the multi page thing uses this to do it so he exposed
00:21:18.080 it as well so it's the second process and it gives you the same like big pile of JSON that this does so that is our we
00:21:26.030 need to now think about this service and I've sort of talked about it already but we need to evaluate our business process step one what other API actually do
00:21:32.720 right like what software are we building one of these I love about test-driven development is that it forces me to actually confront what I'm building
00:21:38.720 rather than just screwing around with software right like I cannot think about what I should be doing and just run
00:21:44.270 random code all day so there's these two fundamental processes we need a handle with this web pages API and the site
00:21:50.210 Maps API individual pages whole sites so those are the two processes we need to
00:21:55.340 handle then we make a state machine out of the steps in that business process
00:22:01.190 I love the dot language for making state machines you can write text files and it spits out these beautiful laughs this is a little teeny small
00:22:08.950 let's see if we can yeah there we go who's this scroll it does not scroll
00:22:15.130 I'll start good again so basically this is sort of like how I built a random
00:22:23.320 state machine to do this this process so we need to be able to make a request to actually get the data back right so
00:22:30.610 that's the second half but we need that we need that variable the actual URL that we're checking so we needed to
00:22:35.830 template that somehow so we need to intermediate step a form to say hey put in the URL and hit process and then it
00:22:42.010 would actually do the processing so there's sort of two steps so the the request form and the request form both
00:22:48.280 hit the middle ones they do the processing and give you this display which is the same in both instances and it returns you back to the root just to
00:22:55.240 demonstrate a little more that this is actually a like two-step process I made an alternate version of the state
00:23:01.300 machine which has more states that show you have these two discrete processes and this is also an incredibly simple
00:23:07.090 process right because we have again 45 minutes so if you had something where it's like you know post this to a URL
00:23:13.690 pull it continually until it says it's done processing go hit this other one like it might be more complicated the
00:23:20.200 the example people always use is ordering a cup of coffee from Starbucks right so you like get the menu read what
00:23:25.840 the menu is put in your order it redirects you to a place where you pull to see if your coffee is done and then
00:23:30.970 make another post to get your coffee so like that would be a more complicated state machine this one's simple because we have a simple talk so from that state
00:23:38.530 machine we shrink the slides back down again and we need to now evaluate our
00:23:44.230 media type needs so unfortunately JSON cannot drive a
00:23:50.140 hyper media API I'm sorry about this I love JSON too but there's good news and
00:23:55.330 the good news is that you can build hyper media semantics on top of JSON and use JSON the serialization format to
00:24:02.290 build your API so you don't have to use XML and in fact XML suffers the same thing essentially JSON and XML are
00:24:08.980 semantically void of anything they just show you how to serialize some data right so what's the standard way to make
00:24:15.340 a link in JSON right you camps there's no standard for that so you can bill old formats on top of these things and
00:24:22.030 still use your beloved JSON like when people say you can't use JSON to drive an API they mean you can't use application JSON not a custom format
00:24:29.920 built on top of JSON so that's what we're gonna do is build a format on top of JSON now is a little word here
00:24:36.490 there's a there's a tension that goes on between using types that already exist
00:24:42.520 and building your own type ideally you should use a type that already exists and you can look up there are tons of
00:24:48.040 types there's actually two fantastic hypermedia JSON types one is named collection plus JSON and the other one
00:24:54.250 is named Hal but so if everyone makes their own individual type then we
00:24:59.860 haven't gained anything because you still need to use the same tools like individual tools on every service but if we all use one type it would be really
00:25:06.220 hard to shoebox all of those things into one idea so the idea is this healthy middle ground where we have a number of
00:25:12.790 types that do different semantic things but we share them among similar applications so we can all benefit from
00:25:18.820 sharing the tooling but not so much that it like loses all meaning or only has
00:25:24.250 super specific meaning there's a healthy medium so we're going to talk about building a custom type just so I can
00:25:30.040 show you what that process is but ideally you would say like collection plus JSON would actually work perfectly here so we could say cool we're not
00:25:35.920 designing anything we're gonna use collection plus JSON we're done so we're gonna create a type media type design is
00:25:43.630 very much an art as well as a science there's actually lots of lots of things to consider and it's a very complicated
00:25:49.179 topic and there's no right or wrong answers you kind of have to try it we got really lucky that the people that
00:25:55.630 invented all this stuff way back when like the guys who invented sgml in HTML sort of ended up accidentally doing the
00:26:02.260 right thing the idea that like Tim berners-lee is this magical superhuman who magically invented everything
00:26:08.170 perfect is totally wrong and if you don't know anything about the history if you think that's true HTML is very much a happy accident of
00:26:14.170 people who liked with Mark Anderson said something one time about like HTML was
00:26:19.300 created by sgml nerds and people who liked angle brackets so it just happened to be a very happy accident that we
00:26:25.570 stumbled across this like way of building things and that's actually what fielding did with his dissertation was
00:26:31.270 codify stuff that it existed preview like we did tons of developments and then codified it into this is what has
00:26:37.970 worked for us in the past so that's actually what people say like rest is Wang curry like rest is encoding what
00:26:43.820 we've already done and been successful at building so anyway there's lots of Awesome books and stuff you can read
00:26:49.550 about this topic so we're gonna we're gonna not go into it too too in detail but show you some of the things you basically need to consider two large
00:26:55.400 things when designing a media type you need to worry about the data that you're gonna transfer and you need to worry
00:27:00.470 about the hyper media controls that do the linking back and forth so we're
00:27:06.170 gonna build a type called w3c love validation plus JSON and it's media type designation would look like this
00:27:11.840 applications VND w3c love die validation Plus JSON if you've never dealt with
00:27:17.120 media types before you basically can break them into two parts there's like a category which is the application part
00:27:22.490 so like HTML is text slash HTML application slash JSON image slash ping
00:27:29.530 so it's like a broad category and then the second half is the details so the
00:27:34.880 plus JSON on the end means hey if you don't understand the semantics you can process this as JSON and it will still
00:27:40.250 work like we're adding semantics on top plus JSON the VND dot w3c love is a
00:27:46.940 vendor prefix so when we're building a specific type just for us for now we had we do the VND dot and then our
00:27:53.840 organization name to show that it's names based under our organization and then if other people wanted to build validation services we would work with
00:27:59.990 them to build a validation plus JSON that would work across our companies but for now since it's specific there's a vendor tree so via indeed other VIII's
00:28:06.860 love validation plus JSON which is a mouthful eventually this would be standard hopefully once it like you know
00:28:12.830 years and years of people using this awesome media type eventually it would come down to application slash validation and that would be a type but
00:28:20.090 that takes a long time and a lot of people working together and that's sort of how the standards process works which is incredibly fascinating if you've
00:28:26.300 never looked into it you are web developers you should know how web stuff works like in general right like there's
00:28:33.320 a governing body that controls what goes into browsers that controls what you were able to build so if you don't know
00:28:39.230 how that works put that on your mental list of like stuff to learn someday because it does affect you indirectly
00:28:44.540 and you have the power to change it that's a whole other talk so we're gonna need all these data elements from our
00:28:50.240 JSON before right we're gonna need to know like when it was scraped if it was successful what information comes back so we need to address those elements and
00:28:56.440 so in our media type definition we want to include some language like this a response may contain created a scrape -
00:29:03.290 scraping address blah blah blah all these things and we would say here is the stuff I'm going to give you here the
00:29:08.510 attributes there's actually one of the art things about media type design is you can either say here is a list of
00:29:15.230 keys and values with data and the the things that are being returned or you can get really specific there are pros
00:29:20.720 and cons to each approach this is a specific approach where we say what all the details are and then hypermedia
00:29:26.840 controls which are like links and forms and all the ways we connect our representations together so when we looked at our thing we knew we needed a
00:29:32.930 link to actually go from the like the form we need a form to template the URL
00:29:38.000 and then we needed a way to make that form point somewhere to show where the processing was happening so we'll say
00:29:43.010 that response can make a forms element which has an array of JSON objects they have href rel and data elements data has
00:29:49.610 keys and values that are named and value and so this is how we build a form this is sort of a little abstract it'll make
00:29:54.950 more sense when I show you an example in a second then we also want to name like link relations so any form that has the
00:30:01.880 sitemap form link relation will give you a sitemap API request any sitemap link
00:30:07.280 will process that form and give you the information about it and now we need to build it magic step five so this is
00:30:15.110 where it gets more concrete even so we would went back and talked about stuff a little bit abstract here's the details of like concrete stuff so imagine we
00:30:22.490 wrapped our web stuff so that we can make a request to a URL and provide a
00:30:27.500 media type so hit the root of the service it would return you in an example the thing that would return is
00:30:33.980 this which is a valid w3c love+ validation plus JSON response which has
00:30:39.230 two links so it's a JSON array that shows you hey if you want to process a website then go here if you want to
00:30:45.260 process a sitemap request go here and you'll notice that I did the dot dot dots because the href doesn't matter
00:30:50.300 what the URLs are is totally irrelevant in this case so what we would do is we'd make our client process this forms and
00:30:57.170 it would go through this something like pseudocode well not really pseudocode bit sort of pseudocode where it would grab the links out of the
00:31:03.680 response and then find the first one where the rel map sitemap form and grab the href attribute out of it right so we
00:31:11.240 have this list we want to grab the href attribute of the one with the rel attribute that we're looking for and
00:31:17.120 then we make a renault that URI we follow the link this is the exact same way that you interact with a web site
00:31:24.320 right like go to google.com click on a button click on a link do whatever and
00:31:30.200 then we make a request there and that returns another form that returns a thing with a forms element and that
00:31:35.450 forms says there's an href here it is a sitemap form and we need a check and
00:31:40.970 then a value so you have to fill in a value so our client would look at this form process it's a cool I need a value that would be the URL that we're gonna
00:31:47.510 actually look at and then it would say I need to submit this as a get request to
00:31:52.850 the href that exists on this form so then it would do that and we would get
00:31:58.100 our data back which would basically look the same thing as that big giant pile of data in the end we'd be able to display that information and the user because
00:32:03.950 we'd have those semantics so that's an example of this response so to recap the
00:32:12.140 server-side stuff you evaluate your business processes you create a state machine that represents those processes
00:32:18.290 and this is really useful if you don't even care about this API stuff or you think that I'm full of crap doing that
00:32:24.530 is really really useful to understanding how your service works like checking out what things go where and what steps
00:32:30.020 people need to take it's super awesome there's always that story about every time Amazon took a chunk off of their
00:32:35.720 signup process they saw a business increase right like think about when you fill out a form on the web right if it's like steps 1 of 7 you're like I'm not
00:32:42.920 using this website at all and it's the same thing with api's so examining your website as a state machine can help you
00:32:48.770 understand like Oh to order something my website takes 30 clicks no wonder we're
00:32:54.260 not making any money right and optimizing those things can help so it's useful even if you don't do this API stuff but then you can look at that
00:33:00.560 state machine and see what kinds of things you need in your media type and then you can pick a media type that exists or build your own and then
00:33:06.590 implement it on the server side and that's that's it tadam now this talk in general
00:33:12.830 is about getting you vaguely familiar with this terminology and sort of understanding what I'm talking about
00:33:18.490 this is a really deep topic like I said I devoted eight months of my life reading books and like learning stuff
00:33:24.230 and talking to people it's hard it's not simple and it's basically impossible for me to explain in half an hour all the details and make sure you really
00:33:30.409 understand it so I am writing that book which is called designing hypermedia api's calm it's not actually a book it's
00:33:36.620 a website where I post updates that are like article size things because again with that lean thing I was like wait I'm
00:33:42.260 gonna lean a book by spending six months writing big chunks of it that's stupid so then we have a forum that's free
00:33:48.649 where you can like talk about these topics and get questions and stuff it's really cool so yeah this is the end of
00:33:55.909 the slides but I still have another 12 minutes so I'm going to talk about some client stuff and show you some code on the client side since we've talking
00:34:02.269 about server stuff but yeah that's me on Twitter my website the website for the book and one of the really awesome
00:34:08.659 things that we're doing a jump start to do that at for a brief second is all of our curriculum is free online and we
00:34:15.919 actually like have it on it's it's just an octa press install that you can actually submit updates to so I've been
00:34:21.950 really enjoying like having people go through our lessons that aren't even taking hungry Academy or don't pay us to
00:34:27.859 come teach them you can come check out the stuff we do teach and submit pull requests and then I will merge them in
00:34:33.379 which is awesome so that's really cool and I enjoy it a lot so if you so check out the stuff on that tutorials jump
00:34:40.040 start lab com that's pretty it's pretty awesome all right so let's let's pull up some some clients there is a media type
00:34:49.220 for micro blogging someone made one Mike Amundsen who's an awesome dude he made a type for micro blogging so he
00:34:56.780 has a server implementation that's written in node but we won't talk about that and it exposes a hyper media API to
00:35:04.940 do micro blogging stuff so as an example I thought I would show you a client you know I use the Mac Twitter client which
00:35:13.700 is terrible but it's the best thing we have and it looks like this right and so I figured oh I'll build one that looks just like that for this you know hyper
00:35:21.050 media API so because I maintain shoes shoes and I'm gonna show you what it looks like it's very ugly and very
00:35:28.319 straightforward and doesn't have really air processing because it's an example toy app but basically you can type in a
00:35:33.779 username and type in a password to no password or whatever and then it allows
00:35:39.750 you to change the URL so you could use this with any service that complies with this and click Save and if my internet
00:35:45.720 works which should says it's working but we'll see if this actually happens or not churning churning churning since
00:35:52.559 it's on Heroku it takes a free it takes time to spin up the instance anyway you'll see an interface that sort of
00:35:57.869 looks a little bit like the sample Twitter application so you got your little box we can post stuff it shows
00:36:04.589 all the messages that exists right now it's just a list so this is like a sample desktop client
00:36:09.660 it's totally driven by hyper media so how this works is I talk really loud and
00:36:17.490 I'm a microphone so basically we require
00:36:25.710 Oh struck because it's really useful for configuration stuff and then I write little wrappers around net HTTP because
00:36:31.140 it's interface is horrible and then we grab some configuration data and we
00:36:37.109 store the route URL that we're going to use and you can't actually go check this out it gives you XHTML if you ask for it
00:36:42.900 and so you can actually view this over there but we saved this default URL and this is the only URL and the whole thing
00:36:48.750 entirely then this is sort of slightly complicated because shoes uses the idea
00:36:54.990 of URLs to map pages of interface so basically there are two screens the preference screen and then the index and
00:37:02.220 those are done by these two methods and the index we fetch the data at the
00:37:08.160 current URI that we're looking at and then if we don't have a username and password set we redirect to the
00:37:13.890 Preferences screen because authenticating this uses HTTP basic authentication and so asking for that on
00:37:19.710 every request is stupid so we save it often to some configuration stuff so if we have that configuration already what
00:37:25.289 we do is we search we take the current data that was returned and we use in my
00:37:30.869 case XPath to search can you guys see this should I make this bigger this is smaller I know
00:37:36.859 a little bit so we look to see if there's a form with a certain clasp on
00:37:43.069 it so like if if there's the ability of the current time to post a message there'll be a form with this attribute
00:37:48.410 on it so if we find it then we render we say what's happening and we render the
00:37:54.589 box where you can type in what text it is and when you push the post button it grabs the action attribute of that form
00:38:01.009 which has the URL in it and then sends a posts with our username and password and
00:38:06.049 the message text to that URL done super simple and then it redirects you back to the main page refreshes the interface
00:38:13.039 basically so that's like posting a new update and then if if there's a list of messages in the current response it
00:38:19.970 finds that certain div with those IDs and the UL because this is based on XHTML as opposed to on JSON and then it
00:38:27.140 displays all messages it goes through each list element and it displays that message text and the user text and
00:38:33.470 that's how we get all of these individual things right like this is a list with the tweet text and the person
00:38:41.329 who said it tons of testing tweets on there it's just fun and so that's it and
00:38:46.730 then there's a little refresh button down here so and then there's stuff for
00:38:52.160 there's crap for the Preferences screen which you don't really need to see so what's interesting about this is that the interface is totally driven by the
00:38:58.849 response that's returned from the server so if we didn't include the list of messages that list just wouldn't appear
00:39:04.970 in the interface if we didn't include the ability to post messages that would just disappear from the interface and so
00:39:11.150 we can actually change the way that our clients work by changing the way our server works and this is really powerful
00:39:17.839 for pushing updates right like this is a desktop app but it has that really nice property about the web where you get to
00:39:23.299 push updates to users instantaneously and it's because we've decoupled the logic of what the business process is
00:39:31.130 instead of like having a gem that works on the server and works on the client where we duplicate our logic we have all
00:39:38.779 our logic on the server and the client knows how to show the end points of that logic and perform this process but it
00:39:44.989 doesn't worry about the internal details of like what does updating a message we mean how does that work it doesn't
00:39:50.940 know it just submits links and forms this is like one of the worst I actually don't
00:39:56.460 I don't hate node I don't like node but one of the worst examples I've ever heard of people saying that you can use
00:40:02.160 node is like why it's a good idea is like oh but you can you duplicate your models on the client side and the server side sins is both in JavaScript and like
00:40:09.450 that's the same thing as copying and pasting your models in one file into another like you're using two bits of
00:40:14.790 code like you're you're using the same model in two places that's wrong you should have a canonical source and you
00:40:19.830 know client should be clients and service should be service which is another rant but basically like you can
00:40:25.290 see how this is an interface that's not a web browser that's being driven by the response from the server if we wanted to
00:40:31.620 have more things there's a lot more to the spec so like for example we could actually make the user links clickable
00:40:37.680 and the display a user page like that exists the ability to sign up through the service like that all exists I just
00:40:42.900 didn't want to build out everything but you can see how these two interface elements would appear disappear based on
00:40:48.630 what the server returns so like if we had an overload from the server say we couldn't we had a fail whale right
00:40:55.110 rather than having a box that fails to post the message we could actually not
00:41:00.300 display the box at all like if you turned off the post a message response part of what your API is returning the
00:41:07.440 box to post a message would just disappear and maybe we leave a message saying like the server is overloaded instead and then our clients would just
00:41:14.310 like not let you I frickin hate how the Twitter client liked it if it doesn't go through it just pops up a message that's
00:41:21.000 like yo I couldn't post that stuff and at least it's it there right like if I can't post something don't give me the ability to post something because it's
00:41:27.630 always like 45 seconds later which is like a year and Twitter time and so it's terrible but like we could we could
00:41:34.380 handle these situations in different ways is what I'm trying to say and it's server driven and the clients reacts to
00:41:41.010 the way that the server is implemented which allows us to do all kinds of cool things so yeah this is an application of
00:41:48.480 like building a desktop client as opposed to a web client there's also the
00:41:53.850 same strategy applies so if you go see you who does talk later for example he's going to talk about the future of rails
00:41:59.730 and how like using rails to serve to drive client-side apps is like really
00:42:05.280 cool and that's another example like you can essentially build a client-side application that's all JavaScript that reads from your API and then makes your
00:42:12.270 interface happen based on what it is is sort of very inception because you're building a client on the clients and
00:42:18.210 there's you know it's like all inside this framework which is weird but it's the same basic idea and it's really freaking cool so that is that is one
00:42:25.380 nice things about the future of all that stuff and so I think we're converging to these things in different ways I guess
00:42:31.710 so anyway I'm out of time so I hope I've piqued your interest if you want to
00:42:37.200 learn more you can read the mailing lists you can buy my junk you can come talk to me later I'll be around I have
00:42:43.140 this mohawk everyone thinks I'm Skrillex so like it's easy to find me I was in
00:42:48.510 Austin for two hours and someone yelled at a car like Skrillex Oh God it's a mohawk but it happens so yeah thanks for
00:42:57.480 coming and listening and enjoy the rest of your rails comp