00:00:15.839
uh my name is Michael blle and I'm here today to talk to you about cross origin
00:00:21.680
resource sharing and why something that's really simple to implement really simple to use both on the Ruby and the
00:00:28.240
browser side um can actually have some pretty important ramifications for web
00:00:33.440
app development so a little bit of background on me um I am the co-founder and CEO of divot uh divot is an
00:00:40.840
interface builder for web applications so basically we're letting you drag and drop build uh using Twitter bootstrap
00:00:47.920
components for now but we're going to expand beyond that and sort of the difference from every other Dragon drop tool you've ever seen is that our prime
00:00:55.079
directive and our focus is on exporting clean code so you can actually you know use it
00:01:00.600
um you may have also seen some of my work um I'm also a fellow at in tridia
00:01:05.840
um I've worked on open source projects there for the last five years including omnio and grape um and yeah it's a ruby
00:01:13.479
consultancy fantastic people um so that's a little bit of background on me
00:01:19.520
um and if you'd like to follow along with the slides they are just it's HTML
00:01:25.040
so you can go follow m. github.com talk feel free all right so cross origin
00:01:32.759
resource sharing um what this basically is if you're not familiar actually let's
00:01:37.920
do a quick poll to get this out of the way um who's familiar with what cross origin resource sharing is
00:01:43.840
already okay good number of you who has used cross origin resource sharing in
00:01:49.680
either a side project or something production whatever okay um good to know so for
00:01:56.799
those of you who aren't familiar with it cross origin resource sharing is effectively cross domain Ajax so um you
00:02:03.960
know everyone's familiar with using XML HTTP requests in the browser in order to
00:02:10.080
request resources from the server without having to refresh the page well cross origin resource sharing lets you
00:02:16.040
do that same thing but rather than being restricted to the same domain that you're that the page loads on which has
00:02:22.760
been the traditional browser security case um now you're able to request from other domains um as long is on the
00:02:30.280
server side they're implementing this protocol um so you know you might you
00:02:36.080
might be familiar with Jon p as well where basically you make a request to remote endpoint that wraps it in a
00:02:42.519
callback function that is then is executed as JavaScript on your side and Json p is effectively um a hack way to
00:02:51.239
do cross doain Ajax um it only works for get requests you don't really have any
00:02:56.360
kind of error tracking error reporting custom headers there's lots of things you can't do with Json P that you can do
00:03:02.720
with Kors and like all good things Kors doesn't work that great in IE less than
00:03:08.720
10 um there is an ie equivalent of the cores called X domain request there are
00:03:17.200
also some various restrictions on how that works as opposed to the full cor standard um I'm not going to get into
00:03:23.840
that now but if you're building something that's for IE8 and N there are
00:03:29.000
a lot of things that I'm going to talk about that you'll be able to do some that you won't so dig into that a little bit
00:03:34.720
more so what is important about cores why does this cross domain Ajax actually
00:03:41.239
matter when it comes to building web applications um what it allows us to do really for the first time is we can
00:03:48.599
build an application that effectively implements service oriented architecture on the browser side so um there's
00:03:55.720
actually been a lot of talk about SOA at Ruby comp today and I think that's because more and more you know as we
00:04:01.760
mature as our applications get larger you realize that having this big monolithic application um just becomes
00:04:08.920
more and more unwieldy whether that's because your tests are taking longer and longer to run whether that's because you
00:04:14.400
have you know completely unrelated code and mass and just everything's getting out of control um you know the more you
00:04:21.440
can break your part your app apart the more you can turn it into small modules small independent things that work
00:04:28.040
together to give you the whole package uh the better off you are so to sort of
00:04:33.479
go over the oh and the other thing that I'm going to go to in a little while is that if you build a public API for your
00:04:41.199
application and you allow those developers to use cores um that can do
00:04:46.440
some really amazing things and um that's one of the things that I'd say if there's going to be a takeaway of go do
00:04:52.720
this if you have a public API for your application um figure out how you can make it work with cores because there's
00:04:58.240
some really awesome things but we'll get back to that in a little bit so um what
00:05:03.440
is Kors Kors is basically just a protocol where browsers and servers have
00:05:09.600
agreed on a set of headers that basically tell you whether or not um a
00:05:15.320
given domain is allowed to make Ajax requests um to it so basically how this
00:05:22.919
works is if you're doing a get request and it's just a vanilla get request you don't have any custom headers you need
00:05:28.240
to send or anything like that um your browser will just send that git request over to the server um and the server has
00:05:35.919
the option to respond with an um Access Control allow origin header um and the
00:05:43.639
access control allow origin header basically just says whether or not the
00:05:48.880
origin domain so if I'm on you know app. app.com and I'm making a request to
00:05:55.479
api.my app.com then api.my app.com has the opportunity to either approve or
00:06:02.840
deny that origin of app. app.com um for this request so basically in the
00:06:09.680
response headers there will either be um there will be Access Control allow origin and that can be a star which just
00:06:17.160
means any domain can make a request at any time or that'll be a specific origin
00:06:22.440
so if it's a specific origin that's either something that's going to be um just statically added to your server
00:06:28.520
somewhere in that you know I'm only ever going to allow requests from this one or you could dynamically compute what
00:06:34.520
that's going to be and send back a domain you know if it matches some wh list or some other uh specifications so
00:06:42.280
that's how it works for a get request for a post or put or delete or if you
00:06:47.360
need to send custom headers then what happens is it sends an options pre-flight request so what the browser
00:06:54.840
does is it says okay you're trying to make an Ajax request across domain and
00:07:00.120
it's not a vanilla get request you know I need to know more than just if this is allowed um because posting data to the
00:07:06.199
server could be dangerous in certain scenarios and the entire reason that browsers weren't allowed to do this
00:07:12.080
before and the entire reason that cores exist as a standard is to basically protect servers from Cross domain site
00:07:19.160
attacks so you know cross- site uh you know it's sort of a long similar principles as cross site forgery
00:07:26.120
protection and things like that by not allowing Ajax to go across domains you enable better security by default so if
00:07:33.639
you're making any request other than a vanilla get request then this options pre-flight request is sent first so the
00:07:40.479
browser before it actually sends the post or whatever you're trying to do um it'll send an options request that's
00:07:46.479
basically saying you know hey server I want to make this request is that okay
00:07:51.800
and the server will then respond with these various headers one of which is the access control allow origin which I
00:07:59.039
already talked aled about a little bit another is Access Control allow methods and this can be comma separated so if I
00:08:05.759
have the same endpoint and it can respond to get post put delete then I would add all of those to the access
00:08:12.280
control allow methods um in that options PreFlight request um there's Access Control expose
00:08:20.159
headers and allow headers so expose headers is saying these are the headers that I'm going to send that I want the
00:08:26.560
browser to be able to see um there are some basic headers that are that it's always allowed to see but if you have
00:08:32.080
any kind of custom headers that you're implementing things like that um maybe you're sending a an API rate limit along
00:08:37.519
as a header um you would need to add that to the exposed headers there's also the allowed headers which is this these
00:08:43.959
are the headers that the browser is allowed to send to the server so by the same token if I don't specify certain
00:08:50.880
headers that I'm expecting then the browser actually going to strip those headers off of the XML HTTP request
00:08:57.440
before it's sent so the server never actually sees that unless it gets the okay and again this is all done for
00:09:03.480
security sake um and this brings us back TOA in
00:09:08.519
the browser so this is sort of the really generic
00:09:14.680
idea of what is SOA um you know in a traditional application you might have a monolithic say it's a rails app doesn't
00:09:21.160
really matter what it is and that incorporates all of the different aspects of your application you know if
00:09:26.680
you have authentication user messaging and activity feed profiles you know a public API that developers can access if
00:09:33.320
that's all in a monolithic application then you know that's a single point that the browser is communicating with and
00:09:39.560
that may be a request response cycle or that may be through Ajax um you know
00:09:44.720
something more responsive like that uh but either way basically you're just communicating with one endpoint if you
00:09:50.880
take the service oriented approach then you take each of these components of your application so your authentication
00:09:56.920
your API your messaging system and you break those out into independent services and by independent services
00:10:03.720
that means um I mean it can mean a variety of things that can mean uh basically that they're logically
00:10:09.800
separate even if they're on the same Ser server so you're just basically separating all that logic these exist at
00:10:15.200
different endpoints um or they can be you know entirely different languages entirely different runtimes different
00:10:21.040
server infrastructure um different everything and what this does is it
00:10:26.240
gives you a ton of flexibility so the advantage of the advantages of a service oriented
00:10:31.800
approach is that you have scalability that works better because each of these individual Service Parts can be scaled
00:10:39.040
independently because theoretically they can all be on different infrastructure so if I have an application and 90% of
00:10:44.959
my requests have to do with user messaging and only 10% have to do with everything else it would be really nice
00:10:51.880
if I could rather than scaling up this you know giant monolithic app that maybe has a big memory footprint has a long
00:10:57.920
startup time what if I could just scale up the messaging part and have 10 times as many messaging servers running as I
00:11:04.040
have everything else so that's the basic idea behind the scalability of a service oriented design um reusability which I
00:11:12.399
completely misspelled um reusability is also important because as you build these as independent Services you might
00:11:19.480
come across say You're Building another application that can actually utilize the same service these Services um can
00:11:25.040
kind of take on a life of its own if you're familiar with Heroku add-ons um in a lot of ways once you start building
00:11:31.440
with a service oriented approach it's almost like you're creating your own add-ons for your application that do a
00:11:36.880
specific purpose that you need and if you have another application that has that same need down the road then you're
00:11:42.519
able to reuse that service without a lot of work without stripping out a bunch of code um again flexibility this just
00:11:49.639
allows you you know maybe I have parts of my application that are very non-concurrent real- time focused and so
00:11:56.200
I feel like node.js is a better fit for that part of the app but for my main application and my API I just want to
00:12:02.079
use Ruby um because I've already got code in there and it's really simple and everything like that so it allows you to
00:12:08.160
implement things in different architectures without sort of sacrificing or coming up with complex
00:12:13.760
schemes um fault tolerance so if I have part of my site go down if I have built
00:12:20.240
a service oriented architecture that's performing well it's potential that I only have a partial outage of my site
00:12:26.120
rather than it taking down the entire thing um and clean boundaries is just saying that because these services are
00:12:32.480
built independently they're able to communicate independently which means that there's always a clean separation
00:12:38.399
of responsibilities in your code so it sort of enfor it forces you to make harder and more important architectural
00:12:44.720
decisions earlier you have to really think about your app in terms of these modules and these Services rather than
00:12:51.360
just you know oh I'm going to slap some code in and we'll clean it up later so it kind of forces better coding practices a little more architectural
00:12:58.000
thinking on you up up front um which also is a bit of a disadvantage there is a bit of initial complexity to a service
00:13:04.920
oriented approach because now you're not just building one app you're not just using sort of the standard path You're
00:13:10.680
Building many applications you have to figure out how they're how and when they need to communicate with each other how
00:13:16.360
and when they need to communicate with the browser or whatever your central control point is so there is a little
00:13:21.639
bit more complexity with a server or with a service oriented architecture um cross- service communication can be
00:13:28.000
tricky um you know if I have a user's table on one server but I have another service that
00:13:34.839
needs to know some of that user information it can be a little bit tricky to figure out you know do I pull
00:13:40.240
that over and cash it for a while do I you know make a request each time to that service so figuring out the
00:13:46.160
boundaries of when and how much they should communicate with each other can be tricky um and the other thing is that
00:13:51.560
there's not really at least in the Ruby world and I'm not familiar with one that I think is particularly great um there's
00:13:58.000
not there's not sort of a framework that's like that's built from the ground up to let's make service oriented apps
00:14:04.440
you know this is an easy way to do it um there's lots of sort of tutorials there's some books out there that
00:14:09.639
describe how to do it um but there's nothing that's as easy as you know rails G controller users controller um that's
00:14:16.240
out there so those are some of the disadvantages but if you're building something that's more than a toy
00:14:21.720
application that you're expecting to spend months or even years maintaining um those disadvantages are really worth
00:14:28.720
the pain to get to the point where you're thinking architecturally you get that scal scalability and that
00:14:35.079
modularity so if you want to cheat a little bit and you want to sort of have a a service oriented architecture but
00:14:42.199
you don't really want to break it out into you know I'm going to run this on this server I'm going to run this on that server um you can use rack Cascades
00:14:49.759
so you know if you're familiar with rack all rails apps are rack apps all Sinatra apps are rack apps and so what you can
00:14:56.639
actually do is in your rack up file you can just run a rack Cascade of all of your applications so say you just have
00:15:03.360
you know a folder for each application and what rack Cascade does is if it get
00:15:08.440
if it encounters a 404 so it says resource not found then it just falls through and tries to call the next
00:15:13.759
application until something returns a non 404 response um or it returns a 404
00:15:18.920
response if it can't find one so that can sort of be a cheat where you're breaking it out into these Individual
00:15:24.040
Services but they're still all running in the same stack while you're sort of spinning things up
00:15:30.759
and my recommendation if you're going service oriented would be to keep things
00:15:35.839
lightweight um you know I'm a huge fan of Sinatra it's something that you can
00:15:41.519
just get in so quickly do a little bit of work you know everything's so clear um you know sort of a plug from my own
00:15:48.279
library but I also built grape which is a restful API framework um and these
00:15:53.800
apps tend to be a little bit easier to break apart than rails apps now that's not to say that there's not likely to be
00:15:59.920
a a place and a case for rails in your sort of service oriented architecture because you're probably going to end up
00:16:05.560
having maybe a core application that runs a lot of your logic um but not some
00:16:10.600
of these services and that might make sense as a rails app and I'm sure that people that you may have seen you know
00:16:16.839
there's the possibility of doing sort of one file rail apps and breaking that apart even more um but personally I
00:16:22.519
prefer things like Sinatra so as far as implementing cores in Ruby it's actually dead simple
00:16:29.720
because there's a gem for everything so use the rack cores gem so in your gem file you just add rack Das cores and
00:16:37.399
then it's a rack middleware so in your rack up file in an initializer for rails
00:16:42.680
you just use rack cores you have um you basically pass it in AOW block and
00:16:48.880
that's where you specify these are the origins that are okay um you can pass multiple arguments if you need to to
00:16:55.240
that one and then you can specify resources and on each resource in
00:17:00.839
addition to just specifying the path you can also specify methods which is going to give you that access control allow
00:17:07.160
methods you can supply headers expose so this is just a shorthand way to
00:17:12.959
automatically handle those options pre-flight requests um as a rack middleware so you just slip this into
00:17:20.480
your project and you're done so when I talked about if you have a public API looking to implementing cores um part of
00:17:26.240
the reason is because it's really really easy so let's dig in a little bit I built
00:17:32.720
just a really simple uh service oriented in the browser example so that we can go through both a few of the sort of
00:17:39.000
principles of what's going on and a few of the challenges you'll run into so here is my application it's very
00:17:46.960
simple obviously um and first thing I need to do is I need to sign
00:17:54.960
in oops
00:18:03.720
so now it's come back here and it asks for a status so hello
00:18:09.880
oops hello Ruby this is not my laptop and it
00:18:17.320
shows so I hit update it shows up over there um and that's all this application does so this is obviously very basic
00:18:24.720
this is not something that needs to be built in a service oriented manner but it was built in a service oriented
00:18:30.360
manner so that I could show you a few of the things that you might want to do um we're just going to go through the code on GitHub a little bit so the first
00:18:37.520
thing and this is one of the things that even though it's not terribly important I think is just really cool about what
00:18:43.360
you can do with cores and that is that the app itself is just static HTML there's no
00:18:51.080
server anything going on when you land on uh this page that's just static HTML so I could
00:18:58.280
serve that you know I could serve that using Apache I could serve that by just dumping everything onto Amazon
00:19:04.280
cloudfront and now I have it on a CDN so that gives you just a real simple power
00:19:10.080
I think to be able to serve your application that can do all of these amazing things as just static HTML and
00:19:16.400
not even worry about the server side um for your core application uh so that's
00:19:21.840
sort of the first thing and if you look basically we just have you know basic
00:19:27.440
HTML um and all of the logic takes place in application.js
00:19:35.039
oops there we go so taking a quick look at this um the
00:19:41.039
first thing that I'm doing here and this is a terrible hack that you'd want to do better in a real application uh but we
00:19:46.600
need to know the different services that we're talking to so in this case I've built two Services I've built an
00:19:52.000
authentication server yes oh yeah you bet let me is that better
00:19:59.600
all right cool um so I've built two services for this I've built an authentication Service and I've built a
00:20:06.240
stream service which is what allows me to publish and read from that stream you saw um so basically right now I'm just
00:20:12.440
setting up that these are the different these are the Ser these are the hosts of those services that I'm going to access
00:20:18.640
um so you need some way to do that usually but this is a bad way because I'm using conditional logic and
00:20:23.799
hard-coded things so don't do that um the next thing I'm doing here
00:20:29.200
is I'm setting an Ajax pre-filter so the authentication scheme that I'm using is
00:20:35.120
Loosely based on oo 2 type things in that we just have a bearer token that's generated and that Bearer token is given
00:20:41.799
to the browser and then stored locally on the browser so that it can make subsequent requests um to the stream
00:20:49.360
service excuse me using that using that
00:20:56.360
token so what I'm actually doing here is I'm using jQuery um I'm using an
00:21:02.360
Ajax pre-filter on jQuery to say if I have a token then I'm going to try to
00:21:07.880
make authenticated requests when I do Ajax requests so I'm going to add an authorization uh I'm going to add an
00:21:14.320
authorization header to my request that sends along this Bearer token so the next thing that we can look
00:21:21.919
at is what happens when the app launches and what happens here is that if you
00:21:28.039
look at the two specification um the way that you can send a bearer token to a
00:21:34.520
client side application so something where you can't trust the code you can't do have things like client Secrets
00:21:47.120
um so the way that that's dealt with at least somewhat is by passing The Token
00:21:52.159
in the location hash so because it's passed in the location hash if you're
00:21:57.440
not aware of this um anything after the pound sign in the URL is never actually
00:22:02.799
sent to the server so you want this token to be obis at least to a degree and by sending it in the location hash
00:22:09.000
that's not actually sent to the server when the request is made so you have a little bit more security there so all
00:22:14.600
I'm doing is I'm checking if there's a token when uh in the location hash when
00:22:19.760
we launch the application and if there is then I'm going to verify and make sure that that's a valid token otherwise
00:22:26.960
um we need otherwise we already have a token so I'm going to try attempt to fetch the stream of
00:22:33.600
updates um and now I think it'd probably be a good time to move over to our authentication app so that was our
00:22:41.279
static HTML browser app now our authentication app is just a onefile
00:22:47.000
synatra app that I wrote and here we're just setting up reddis
00:22:52.520
that's not a big deal um so the first thing you can see is all we're doing is
00:22:58.200
if you go to the root of this then we're going to authenticate using Twitter omnio um and that's just because that
00:23:05.400
was the simplest thing to implement so then we go through the normal omnio process if you're familiar with that but
00:23:11.880
basically it's going out making the ooth request coming back um and fetching user
00:23:17.080
inter user ID user information so that's what's happening in this call back phase is we're
00:23:23.039
just saving some user information and then we're going to generate that access token that I talked about so if you look
00:23:30.080
at this regenerate token method all we're doing is we're generating a URL
00:23:35.200
safe a URL safe token and we are saving that in reddis so that excuse me we can
00:23:43.000
look it up later and then like I said we redirect back to the apphost and include
00:23:49.640
in the hash the bearer token that we just had so that's really most of what
00:23:55.000
there is to this application the only other thing that we're doing is we have a verify method where we're
00:24:02.480
basically just checking to see if a token that's passed is associated with the user and if it is we're returning
00:24:08.559
information about that user and we'll get to that in just a second sorry about the
00:24:19.520
coughing so moving on to our stream application this again is just a oneline
00:24:25.679
Sinatra application um but this show you how you can sort of use services that talk to
00:24:32.080
each other um in general so what we're doing here is we have an authenticate
00:24:37.960
method so if you go down here I can either post to my activity stream or I can get activities from my
00:24:44.919
stream and what happens before any of that happens is I authenticate based on
00:24:50.080
the token the beer token is posted in is passed in um and so here what happens is
00:24:56.679
I'm actually making an HT TP request to that Au server to that verify endpoint
00:25:01.720
that I just talked about and I'm saying hey I just got this token but you know I'm not the Au server I'm the stream
00:25:07.080
server so can you tell me if it's okay and if the off server says yep that's a
00:25:12.559
valid token then the stream server can go ahead and complete the request and
00:25:17.799
Associate things with that token and that user ID otherwise it will send back
00:25:23.760
an unauthorized message so this is a way that Services both talk to to the browser or talk to the sort of central
00:25:30.240
controller but can also talk to each other when necessary um and so if we go back to I'm
00:25:38.480
not going to spend too much longer going through this the code is on GitHub um but just to go through sort of how the
00:25:44.520
posting works we'll go back to application.js you can
00:25:50.399
see um the verify token uh happens at the beginning when we log in just to
00:25:55.799
make sure that the token that we have stored is valid and then we have fet
00:26:01.360
fetch stream and post activity these are both just simple um and I I guess that's something that I didn't mention that I
00:26:07.360
definitely should um all of these requests all of these cores requests you do just like normal Ajax requests so on
00:26:14.480
the browser side you don't have to do anything different it will automatically do the options pre-flighting and
00:26:19.840
everything like that for you so if you're using jQuery if you're using whatever just do a normal XML HTTP
00:26:25.880
request and it'll go through um so long as the server is sending those appropriate
00:26:32.039
headers um so we can get activities we can post activities and then we're just
00:26:37.799
updating the interface so I mean that's pretty much it but what you can see is that this is really pretty simple to do
00:26:46.840
um and again I I really feel like it's something powerful where I have this application that's just static HTML and
00:26:53.720
I'm talking to this authentification service but what if I had you know a separate application but I'm using the
00:26:59.000
same user base well now that application can also talk to the authentication Service and I have this stream service
00:27:05.360
and maybe I have an email notification service that reads from the stream service to be able to push notifications
00:27:11.919
so once you start breaking things apart and modularizing them then you're able to just do a lot more sort of reusing
00:27:19.480
your code and thinking about things in terms of passing messages rather than just having this monolithic idea and
00:27:25.640
once you can do that in the browser then you just have the power to load you know if I have a messaging part
00:27:33.080
if you know if you imagine something like Facebook where you have messaging up here and and a user stream here and
00:27:39.240
you have you know a photos application and all of these things the browser can now coordinate all of those requests
00:27:45.240
they can all go to different services on different servers built with whatever the best architecture is for that and it
00:27:51.200
all just comes together nicely so um that's why I think that Kors is particularly powerful for sort of this
00:27:58.600
browser based service oriented architecture approach so I think that I just went
00:28:05.519
through all of that so we're going to go ahead and move on and talk about public apis that use cores and why that's
00:28:12.240
awesome and that is probably my favorite animated gif ever so what's so awesome about it first
00:28:19.799
of all it lowers the barrier to entry so if I build an application and I allow a
00:28:25.080
public chors API that means that the only thing thing that someone needs to do to be able to build an app that
00:28:31.039
leverages my API is have a text editor and a browser they don't need to run a server they can do this they can do this
00:28:37.840
locally they can run this from file slash so this just opens up a whole new
00:28:43.159
ability to build these super lightweight apps that do a lot more than you'd
00:28:48.279
expect they'd be able to it allows you to do mashups without servers so if you
00:28:53.720
imagine all of these you know mashup applications where it's you know let's take flicker data and mash it up with
00:28:59.960
Google Maps data um traditionally that was done by you
00:29:05.960
create a serers side application that accesses both of those apis it somehow mashes that data together and then
00:29:11.440
displays it back down to the browser in a way that's consumable but if I use
00:29:16.720
cores and I just build a website a web page that makes Kors requests out to the
00:29:21.760
flicker servers and makes Coors requests out to the Google Maps servers now I can do all of that processing on the client
00:29:27.760
side so I'm able to create powerful applications that combine multiple services that do all kinds of things
00:29:34.360
without ever needing to build some kind of custom server architecture um and that's also important because when you
00:29:39.880
think about things like Chrome extensions when you think about sort of simple downloadable Deployable HTML um
00:29:46.600
that's a really powerful Paradigm Services can become public apis
00:29:51.679
and what I mean by that is that you may build a service and at first you're using it internally but over time there
00:29:57.799
may be a greater use case for it than just your own internal use so you're actually able to expose that service to
00:30:04.640
the public without doing a lot of additional work um and finally it has
00:30:09.679
the same burden on you so you know the same requests are being made to your servers the only difference is that
00:30:14.760
you're sending these headers back but it's much less of a burden on your developer users who are building things
00:30:20.200
with your API so this is just something that I really like a lot um so as an example of
00:30:27.519
something that I've built that's sort of this Coors public API um divot alloy so
00:30:34.399
in building div shot we needed to the ability to have people edit CSS for their pages but I don't like editing CSS
00:30:41.279
I haven't done plain CSS in like four years so I wanted people to be able to use their favorite CSS
00:30:48.000
pre-processor um the problem with that is that there's multiple and there's valid reasons for using all of them so I
00:30:54.840
wanted to support SAS I wanted to support less I wanted to support stylus um and so I built alloy as a service to
00:31:02.080
allow us to do this for divot but then I realized that I had built a service that was really general purpose and useful so
00:31:10.320
um here's an example of it in divot so you know I'm in my application I have
00:31:16.120
this I'm going to give it a class let's say super class um now I'm going to edit some
00:31:23.880
stylus
00:31:33.480
so here's how we can utilize it in divot and that's great it allows me to do custom CSS on pages which is a feature
00:31:39.880
that lots of people wanted and now I was able to implement it but what it also allowed us to do is release it as an
00:31:46.480
open source public API so that anyone can use this so if you go to div shot.com alloy you can have this web API
00:31:53.440
for pre-processing CSS so whether I'm using stylus
00:31:58.760
it just compiles um I also built these bookmarklets that will actually let you click the bookmarklet and then click a
00:32:05.320
text area and then if you've written SAS or stylus in that text area it will just
00:32:11.399
convert the content of that into CSS so if you're using a website like Tumblr where it gives you the ability to have
00:32:17.480
custom CSS but you don't really want to write just CSS you want to use a pre-processor you can now use this bookmarklet instead and these were use
00:32:24.480
cases that came up because I built it in this service oriented way because I built alloy as a separate service rather
00:32:30.320
than as part of a monolith and so I think that it's just a really powerful Paradigm to allow you to
00:32:35.799
think about things that way um and famous examples the GitHub
00:32:43.679
API is 100% supporting of ches which is amazing um you can and you can see some
00:32:49.320
really awesome examples of that things that are just hosted as static HTML on GitHub that give you ways to browse your
00:32:57.039
issues browse you know everything on GitHub in some kind of intuitive or novel fashion and that's because GitHub
00:33:03.840
added this cor support in the last few months Amazon
00:33:09.639
added Coors support to S3 and that's a huge thing because now what you're able to do by leveraging S3 and cores you can
00:33:17.519
actually trigger file uploads that are uploading you know whether it's a 20K
00:33:22.960
jpeg or a 200 Meg movie you can offload all of that work on to Amazon servers
00:33:28.799
and it never even has to touch yours because by using cores the request goes straight to
00:33:34.080
Amazon so the file goes straight to Amazon and all you have to do is be able to deal with the response which is going
00:33:39.840
to be a URL of where it ended up being stored so that's what that's an example
00:33:44.960
of what I talked about where it takes the burden off of your users and doesn't add any burden to you because either way
00:33:50.720
this file was going to get uploaded S3 but in this case it was only uploaded S3 rather than uploaded to my server which
00:33:57.159
then got upload to S3 um you know one thing to think about
00:34:02.760
when you're implementing this on a public API is how to handle authentication like I said in the
00:34:08.399
browser you can't count on any kind of secrets so if you have a client secret something like that you can't count on
00:34:14.800
that being being kept um but you still want to be able to identify applications so that you can remove Bad actors things
00:34:21.560
like that um and GitHub solution for that is that they only allow cores
00:34:27.399
request from domains of registered ooth applications so if I register an ooth
00:34:33.639
application um that is em. github.com now I can actually make Coors requests
00:34:39.200
to the GitHub API from em. github.com because I registered that application
00:34:44.679
and I thought that that was a clever way to solve this problem it still lets you identify an application so it just looks
00:34:49.960
at the origin of the request and says oh this is coming from m. github.com so this is you know Michael's fancy GitHub
00:34:56.200
API application um so I just wanted to mention that as a good way to possibly handle
00:35:01.839
authentication if you do build this into a public API so now you know what you can do with
00:35:09.480
cores today um and you know this is it really is a simple technology that just
00:35:14.760
has a lot of applications and the question that I want to ask because I've only just started diving into this I
00:35:20.839
think there's a whole wealth of things that you can do that I haven't even thought of yet so I want to know what
00:35:26.040
will you do with cores tomorrow um so that's everything I'm happy to
00:35:32.000
take any questions you have and come talk to me afterwards or tomorrow or
00:35:37.200
whenever uh but thanks for your
00:35:46.960
time yeah in the GI example how is that any more secured would you still
00:35:53.680
have so it actually is less secure I mean it sort of is less secure and
00:36:00.200
there's nothing to be done about that so the reason that identifying applications is important is because if you're able
00:36:06.200
to identify the application then you're able to sort of say you know if this is
00:36:11.599
just someone that I don't know that's just created an application maybe that gets a certain permission level whereas if it's on our own servers that gets a
00:36:18.319
higher permission level because we know that it's from a trusted Source um so it just gives you the ability to identify
00:36:23.839
but um anything that's in the browser like that is sort of inherently less sec here because it can be in introspected
00:36:29.960
at any time um but as everyone found out when you know the Twitter Android keys were leaked and everything like that um
00:36:36.359
just because it's on a different platform doesn't mean it's necessarily more secure so yeah how do you do graceful
00:36:43.560
degradation for Internet Explorer um that is something that I don't worry
00:36:49.480
about myself because div shot is a tool for developers and it was something that I wanted to research for the talk but wasn't able to find sort of a quick
00:36:56.520
solution for so so I can't answer that 100% I know that there are some sort of shims out there in some libraries to um
00:37:05.119
massage cross domain XML HTTP requests into that X domain object um but I can't
00:37:10.839
tell you sort of the best way to do it yeah yui which I use at my office has a
00:37:19.839
module xdr which lets you use a native request or a flash request just by uh
00:37:26.000
configuration right um so you can that would work as an ID yeah so that's true
00:37:31.760
um so the sort of the way that people were doing cross domain requests before is that flash allows you to do it as
00:37:37.760
long as you have a I think it's domain policy. XML file something like that on
00:37:43.160
the server that allows you to do it so there's can be like a flash fallback similar to how there's a flash fallback
00:37:48.440
for websockets server side events things like that yeah and you found a paradigm for
00:37:54.359
integration testing with that kind of setup that you like um so for integration testing what's interested
00:38:00.880
about what's interesting is that because this is just standard xmlhttp requests
00:38:06.880
you can use um any of the like I I can't recall them off hand but there are
00:38:12.200
various libraries for basically mocking out xmlhttp requests and you can use those same things from the browser side
00:38:19.280
and then on the server side um you know you that would vary depending on how you're building it so if it's a Sinatra
00:38:24.760
application you can just use rack test to to hit it you if it's um you know in nodejs you'd use Jasmine or whatever you
00:38:31.920
use for nodejs um but I mean basically you test each of those independently and
00:38:37.000
then you can sort of stub out the boundaries as long as you agree on a communication protocol if that makes
00:38:43.680
sense yeah can you use cores to authenticate for other connections like
00:38:48.920
a web socket for instance um that is a good question I'm not 100% sure off the top of my head but
00:38:55.599
I believe so anybody else yeah I actually have a
00:39:01.079
question too okay would you ever actually do things allow cross policy
00:39:06.560
whatever as or you always specify a lot of examples at Asis that seems like
00:39:13.599
really um so in my opinion the asterisk is okay if
00:39:19.400
you're talking about usually something that's like a readon API or some kind of
00:39:24.839
transient data or something like that uh for anything where you're doing any kind
00:39:29.880
of real authentication something like that then yeah I think it's a better it's a much better policy to have you
00:39:35.560
know specific domains that you're allowing based on however you want to whitel list
00:39:42.800
that anybody else so what what about concerns on like exploiting these I just
00:39:48.640
can imagine like Theos and asteroids every every browser running attacks everywhere like so um I mean as far as
00:39:56.000
concerns you know it's really no less secure than any other for you know than
00:40:04.160
other kinds of you know cookie based session storage or things like that inherently there are risks when you put
00:40:11.280
data into the client but what you can do um is M mitigate those risks so in the little example application that I showed
00:40:18.560
um you know every time it loads up the application it verifies those tokens you can expire those tokens say every 10
00:40:24.880
minutes or something like that and require them to be refreshed and then you sort of minimize this window where
00:40:30.359
you know if I forget to log out someone can come back in use my token and exploit that to hit the API and do all
00:40:36.319
sorts of bad things um so I mean there are definitely things that you need to watch out for um but I think in general
00:40:43.800
it's it's not really less secure than other ways of communicating with the back end so long as you're sort of
00:40:49.680
cognizant of what you're doing and you're aware that you know you need to make sure that nothing that you consider
00:40:55.160
to be truly secret is ever shown to the browser