 Extreme street Malorinas, you know, live on a mean street in Chicago, but today, rather than pure wedding through, rather than pure wedding through Chicago, they are now pure wedding through the coast. So, I want to introduce all of them, and they are going to talk about securing your rails application, right? So, everybody welcome, Jim and Matt. I hear the beer has already started flowing, I think, advantage of that already. Good morning. Good morning! That's better, that's better. We are here to talk about securing the rails application, and while Matt gets the video set up there, I'll just ask... Let's pass the ballot music, and I'll save that for later. How many people here write about rails applications? Leave your hands in the air if you feel that your rails application is totally secure. Okay, we've got a lot of smart people here who realize that securing is a big issue. And I got interested in this a while back. Do we read it with the slides? Yes, here we go. I got interested in this a while back by a fellow wrote an article. Patrick Buchanese took a look at the BIOSPRA Brails Code. If you're familiar with BIOSPRA, it is a Facebook replacement, and its emphasis is in privacy. It's designed to make sure that your private information is kept safe. So, with that in mind, you think it would be a very secure rails application. But as you look at it, it was struck by numerous severe security errors. And when all of a sudden none, it turns out because of coding mistakes these people made in the rails application, it was quite easy for someone to come in and hijack someone's account, and absolutely nothing. None of your private data was secured because the rails app itself was not secure. That made me stop and think about rail programs. How secure are my rails applications? I've gone through all the standard security classes. I worked at a big corporate environment where they made you go to these classes and you sat down and you learned about things like the SQL injection and all this. But I began to wonder, you know, does rails have that? It came in right. Secure rails programs and all. I really didn't get word. I had the opportunity a couple weeks ago to pair with a guy at our Hackfest after a Ruby, Cincinnati Ruby grade meeting, and he said, hey, why don't you pair with me? I said, sure, what are you doing? He says, I'm writing code that monitors the power usage of the chip on your car key, your plugger, your fob. Yes, thank you. Your key fob that you open a car door with, that has encryption on it. He's monitoring the power levels on that chip and detecting what the password is by watching the power function relations. It takes more power to flip bits than to not flip bits. So when the password is correct, these zeroes in the right password, you can see here, he's running a simulation here. He's actually figuring out that this 64-bit key is, you can see up there right above the break, dead beef dude face in X. Dude people do that. What an awesome thing to do, first of all. But who would ever think about monitoring the power on a chip to detect when the password is correct or not? And that, you can see it was at a .96. That means he's 96% sure that is the right password. The longer this program runs, the more certain it becomes what the password is. I don't think like a hacker. I would have never thought about doing things like this. So to put yourself, to get a secure Rails application, you need to think like a hacker. Okay. So a little bit of reading on work here. We're really talking at a very high level about various security concerns and concepts related to writing secure Rails applications and web applications in general. But we're not going to be pausing ourselves to security experts. If you haven't read the Rails guide on security, read it absolutely. A lot of the Rails guides are very high quality. And the security guide is one of the best. And there's plenty of great information, a lot of which, the things that we're touching on are going to be discussed in more depth here. As well as what this security guide was pulled from, it was a paper. It took 48 pages long, not too long. This should be required reading. Written by Pico Webbers for OWASP, which is the open web application security project. Also a great site and organization to remember if you want to support and claim information, the authoritative source for web application security. That says 40 pages really long, but it's really dense 40 pages. Yeah, it takes a while to work through all that. We have an OWASP guide come and speak to one of our local user groups, and it's really interesting whenever he does. Let me give you some of the basics here about Rails security. Here's architecture for your typical web application. You've got a server, you've got a browser, and you've got a database. Of these three things, what do you trust? None of them? None of them is a good answer. In particular, you can't trust the browser because you don't own the browser. That sits on the desk of the user and he can do anything he wants on that. So you can't trust anything to come from the browser. You can't trust the database because even though you think you have control if whatever goes into the database, a lot of the stuff in the database is user input. And there are sneaky ways of doing input that might sneak past your security measures. So don't think just because it's in the database is something that can be trusted. The Rails server itself, if someone's gotten in and corrupted your Rails program, you've got bigger problems of what we're going to address here. So we're going to concentrate mainly on browser issues and database issues in this particular talk. That's not to say that there aren't security issues around the server itself. They are more related to admin issues. So let's talk about the very first issue, SQL injection. How many people have heard of SQL injection? Okay, very much. This is the common one. Everybody covers this in your basic security programs. So let's suppose we have a little controller method that looks like this. This goes in and it wants to find users who have a name like some kind of filter text in there, matches the filter text and who's not an admin. So it's a little bit of SQL from there. And notice this. What's wrong with this right here? It's not a scheme. You are putting filter text which presumably comes from a user right into the text of your SQL query. And if you're not careful, that is a big, big security hole. Let's demonstrate that, Matt. Sure. We'll go ahead and take a crack at this one. Matt is my local hacker, isn't he? No, not exactly. The purpose of this talk, yes. So we have a very simple example app. Of course it's very dark, unfortunately. But it's written to schedule movie nights with your friends. So you get together and you watch movies and you have to hear them. And for the purposes of this talk, we put in this extra little page here which gives us access to certain things to make examples out of. But we see here a list of users that are in the system. And then we've got four users that have signed up. It's a very education-centric user base at this point. But if we click, we like our movie. It's true. As you can see, there's one administrator of the site, which is Joe Brian, who happens to be our boss. So even though there's only four users here, and perhaps this is too overwhelming for me, there's an opportunity I can go and filter this a little further down. So I'm going to filter by Jerry. Okay, now the only users being shown is Jerry, who's our designer today. If we can go up and look into the URL, we see that we've got a query parameter, a filter equal Jerry, as being our... as the way the filter is being done, which tells us that we may have an opportunity here to do some injection with a copy, or something for a cheatable... I'll say, I'll test that out and see if that's the case. Even if you don't have a comment there. There we go. So now, in filtering, you can see they're coming back. Instead of just plain users, you can see that now we're going to be administrative. Because what we've done, we've... by injecting this one equal one, we're going to be a national every possible user, and tossing it into comments, it's going to comment out the remainder of the SQL that we've written, which was doing the not-inadmin checks, and now we're getting everyone back. And that's the basic SQL injection rate. It's not terrifying. But if we change that up a little bit, it's something that's a little bit more complex. This long string here, and run it this time, we're giving back the administrator. And in this case, what we'll be seeing is encrypted password, but apparently to twice in a row, it's really active, of course. What we're doing. We have a lot of live code demos. Actually, there is a string there. We got working at least one point of time that we could actually dump the encrypted administrator passwords by putting in enough unions of the SQL tables. Once you got SQL injection, your entire database is open for browsing, essentially. You can put any SQL in there, essentially pull anything out, with a complex enough string. So you're going to have to pick that up and play again for a voucher. So basically, you're about to see something like that, but what a hacker will do will put code like this into your SQL that essentially comments out the rest of it and can totally control your database at that point. The fix for this is to use what Rails gives you for building up SQL queries. Use the question mark like this and put the text that you want to filter on separately. When you do this, Rails will escape that text. Make sure any quote characters are properly quoted themselves. Make sure comment characters will hurt your SQL queries and it just works. So use the built-in facilities. Little buggy tables. All right. Next security problem. And this, I think, is a common one. One we probably don't recognize too much and at least for myself, I know this is one that I've committed in the past. It's mass assignment. We have some Rails to code here. We want to update a user and we just pull the parameters off of the form, programs, sub-user. We stick all those parameters right into the user and we save them just like that. The problem is it's coming from the form and we're not doing any filtering on that data that comes from the form. Therefore, we can change any field on that user whether it was in the form or not. Yeah? Well, this one. Okay. Okay. So we've added in, this is a symbol and a user form, right? I can update a couple pieces of data that have belonged to me. One of those is my name, there's my email address, so in theory I should have the authority to change those things. But if I utilize the web developer's friend and bring up an autonomous vector, and I can look and inspect here and see the end of the form, you can see the very shell we used to. You can see these input fields and how their names went down. See that the name of this input is user bracket email, right? Because it's going to be the element for the email address and that's how the rack France parser will create the income frame patches one note. So I know that I can probably go in here and try something else if I use a little bit, make some assumptions. If there's an admin flag, I might want to set that to true. You probably figured that out by the SQL injection. Yes, I did. So now if I change that, instead of being the instead of being the email field, it's not going to be the admin field, but an update. Now, as you say, I'm no longer showing up with your users, and if I click you and thens, I'm not able to self-administer it. I'm not on the mass assignment, but a feature of Rails. What you want to do to prevent this is something along this line. You can declare on your user model what fields are not allowed in mass assignment. What fields should not be included in a mass assignment? And there's two ways to do it. You create a fight list like this where you say everything that's allowed to be changed or you can create a black list like this that should not be changed. Quick survey. Which is better? I'm going to say a white list. I'm going to say a black list. Okay, you're right. The white list is better from a security standpoint because if you forget a field, it'll be obvious that you can't edit it. However, if you create a black list and forget a field, it's very easy to miss the fact that someone can start injecting new parameters. Okay, so white list. Prefer a white list. You were going to talk about leaking work. I'll talk about leaking because I know plenty of them. I'm not going to finish that sentence. Anyway, leaking information. So this is a little more subtle topic. You're not necessarily going to talk about this, but just to talk briefly about it. Timing attacks fall in this category and what the timing attacks. Basically any time that the malicious user can well, the malicious user can gather statistical data about the timing behavior or application and clean some information from that. So let's say, for example, that we've got some sort of compare digest method and we're using that to check our session key that's being stored in a cookie, for example, against the expected value to do authentication. And it's just doing simple comparison. String comparison in this case. So what's that going to do? Well, the first sign that it sees that two strings are not equal. If A, B, C and A, B, Q well, at the point where we hit Q we know that they're not equal. So it's going to return to false, right? Basically they held that point. So what if we have a session key that looks something like this, right? A random hash. And then I decide to generate sort of a set of input, a potential input that I think might match this key. And so first I try E of 0, 0, 0 1, 0, 0, 2, 0, 0, 3, so and then I try B, 0, 0, 0 and I notice that with this one that the response, the time it takes to get a response back takes just a little bit longer. And it makes a statistically significant difference. It's not determined that okay, now we'll not cut the first byte, right? And you can continue that process and march your way through using statistical analysis. And it might seem like well, that's either very slow or that's an unlikely scenario but the reality is it's based out of a series of a few days with a relatively small and probably undetected number of bus you can determine this with some information it actually detects and smooths the session by. For a nice law article that talks more about this and some practical implications that we're not going to have as a great article, a lesson in time for your task. And then one other thing that could follow in this category is the tax social network and communication status. So if you're un-logged into Facebook then if I, if another user puts on their web page a link to some image that they know of Facebook that will resolve properly for a logged in user but will not for a non-logged in user using some JavaScript for example of either the amount of time that it takes to request that, get the result of the image request down, or the actual HTTP response code if it's a RESTful service for example. You can use that to detect whether or not another user on your site is logged in to say Twitter, Facebook what have you. What you do with that information is particularly useful and delicious. I don't know, it's the kind of information that you can pull down based off of this sort of information leakage and there's not really much you can do about that ladder issue. Cross-site scripting, another big issue. Okay, so we're talking about the browser and the database here in this particular tab and this is a tab where the user is able to get delicious information into your database. Let's double this one. Back on the job with my lead access skills which involves a lot of copying and pasting. Okay, so now we're actually going to exercise this app. The point of the application is to create a schedule movie that has to be friends, right? So I'll go ahead and schedule this new movie. We'll do the back cave. Yes, people should bring drinks. And then notes, right? So maybe I will say bring pizza and that should be important so I might want to be able to do something like this. And as the design of this application I might want to allow users the ability to do some markup in their fields and their messages, right? And that is a nice user experience in some ways. But instead of say using a bold tag I'll use something different so I wonder if this is going to work. I'll go ahead and schedule it and that does. All right. So that's, yeah. It's really in your face. There's no way my friends are going to forget to bring pizza if I have that nice pop of that. So that should be good. And that's kind of annoying. That's an obnoxious thing to be able to do but could you maybe do something that's a little bit more a little bit more dangerous and the answer is potentially yes. So if I could schedule something else and this time I'll have it at the old management on the street and use a little bit more complex piece of JavaScript in this case. So what we have here. So here we're saying document.write and then we're writing in an image tag. And that image is pointing to in this case it's pointing to a local host on a report but you know it's pointing to hacked at some dot symbolical site dot com and in fact it's also writing the document.cookie so it's writing a cookie knife to a string. Pending it to the end of this so well what's the result when we're going to save that all I see is a broken image right right here. It just winds up being an image tag because obviously that is not pointing to a valid not pointing to a valid image on the server but if I can run over here and just check the logs for you know all I did in this case was generate a new Rails app and start it up for another you can see that in now in the in the log of this third party malicious application we now see all cookie data including session data that I had as authenticated into a different site and obviously that's the problem of course in this case you should be noted that we did subvert a security measure that Rails puts in place which is to mark cookies as the session where these HTTP only so I can't manipulate my JavaScript so I guess to take on there is we'll do that but nevertheless it illustrates the kind of thing that we kind of should pick and learn once the user has the ability for JavaScript on their site that's under their control they can do a lot of bad things grabbing cookies is just one particular thing when we get to what is a cross site the forgery request we'll see another example where a running JavaScript you a piece that leads to bad things the key to this is that they put JavaScript on your page you saw just a image tag that was broken that sent off a request to an external server that was under their control that logged the session data that session data is the key to all of your information on that site once they have a session they can log in as you they can do anything on that site in your name so protecting that session key is very, very important this happened because in that notes section here we had the raw tag a raw allows all the user input to go everything in this nice not notes thing you go directly to the web page without any trying to filter it by default Rails used to do this all the time to prevent that we put the h command in our views new Rails Rails 3 does it by default filters our data by default and if you want the old behavior you have to go raw again but if you want the ability for the user to put bold tags or strong tags or block quotes or anything like that you need to allow something like raw to happen so yeah you might want to use text on our markdown so what do you do well don't use raw you recommend not using that don't use raw with anything that comes from the user if it's generated entirely by you that's a little bit better but don't use raw on user input don't use a black list and don't try to correct for example here's an example of someone who tries to correct user input to make it safe he says well we'll just remove any script tags and then we'll sanitize it until the user enters this so don't try to correct it if the input is bad, reject it don't correct it beware of javascript in unexpected places for example you might expect it in an href tag that's not unusual but as the background on a table you might not think to check there for unusual javascript so probably what you want to do is a Rails method called sanitize and it actually will go through a white list of tags you want to allow and we'll let those tags through and we'll prevent other tags from going there and sanitize is pretty well written I recommend using it rather than trying to write your own white list sir because he probably did a better job than what you would have been able to do real life process scripting incidents here 34,000 34,000 names and passwords were stolen from my space using this what they did, they used process scripting to hide content and presented a fake login screen genius, yes that was in 2007 so it was a big problem let's talk a little bit about privilege escalation this is another thing that I'm prone to do in my code that I am learning to change here we have a find command where we're finding the nights that are attached to a particular user R2 yes, finding the nights based upon this night ID and it should be restricted to the nights that a user is allowed to see however again we're using params that comes from a form which comes from the browser which is unsecure so let's demo this one okay, so we'll do a simple demo here real quick I'm logged in as myself and I can see my schedule of upcoming nights if I log out for seconds and log back in as generally because he was kind enough to give me his very complex password for this site notice that he's got a couple of upcoming movies and everything including one that looks like what it goes to but I know that I've not been invited invited Joe, invited Kevin, invited me I'm sure it's my feelings but that's the way it goes so which one were you interested in? Star Wars? well if it were me I would want to see actually I'm torn I would want to see Star Wars but technically I'm not invited but what could I do I could have noted that even though I'm not invited this night I know that I'm currently logged in as my software so but here I am viewing this movie of gents that I happen to not be invited to and not being invited I really shouldn't I shouldn't be allowed to vote I shouldn't be allowed to see this but maliciously since my feelings are hurt I'm going to vote and make them try to watch Ninja Turtles instead of Star Wars obviously we're all awesome although frankly they're all awesome movies but I'll go ahead and vote and see that okay so I got the way out and make a decision on this movie even though technically I'm not invited so that seems like that should not be the case you notice you did that by hacking the URL you just put in the idea of the night and we went and fashioned it the problem with this search is that it doesn't limit the number of the nights that you're allowed to see by the current user there's no current user involved in this and it's a very simple way to fix this instead of doing a night not fine go to the current user ask for his nights and then find based on that and this search this search will limit you to only nights owned by the current user that will restrict the number of nights you see I cannot do this in my code and it's having a foreigner over the years because I don't particularly like to do a fine on the associations I like to treat associations as kind of just objects and the fact that it's active record based I try to ignore that in my code so I will probably not do this but since it's actually safer the other way of doing it this is a better way to go so I'm changing my code habits because of this would you say you were doing that previously for testability reasons? just kind of kind of extraction reasons I like to treat my models as objects and only deal with the fact that they're active records in particular points of my code I don't like to spread the fact that this is an active record object all over my code base so I tend to limit the points where I actually do saves and finds and things okay cross site request forgery this one was a new one for me when I started researching this topic I always knew that Rails did something about this but I didn't understand what it was or what they did and how it fixed it but this is actually a very fascinating one this is a scenario you're sitting at your browser and you visit a hackers web page conveniently labeled so you know it's a hacker actually probably not and you grenade it down into your browser and it's an image that references movienight.com slash one destroy that is an image request the browser then sends out to the movienight website and since you are already logged into the movie website your session data is still in the cookie in your browser so you have permission to log in and do anything and the destroy command runs out there and bleeds your movienight okay there's a couple counters were we going to demo this one you just move plus I'd like to show off my awesome design skills that were in unsuspected pools so if we go back here and check my schedule I can see I've got several movies coming up including can I go see Blade Runner we're going to do Blade Runner I'm just going to have enough time by myself to watch Blade Runner that's number 12 that is number 12 and if you know that I'm logged in let's say some of the link comes along since we didn't ask you to email I don't know exactly where this goes from but I can direct you to this page and I cannot possibly resist the chance to click for Epic Wood you know that's just entirely irresistible so I'm going to click here on this button and it's going to tell me what this is which is hilarious yes thank you let's try that again there we go I hope you went to Elite later tonight well no I didn't that was not the Epic Wood that I was looking for and yeah I proud of home itself and how was that done was very simple it's just back to this element see the movie click on that it's just a form and the form was pointing to movie night at local slash 9 slash 12 the method post and it didn't quote it of delete and manage it for the real stressful structure there can you say that yeah I mean it could if you trigger anything you want to trigger a form so as long as in this case we're making a conceding that we know this ID that we can which of course that and it itself would be the the difference as long as you trigger a form out of post okay counters to that we rustble in other words don't use get to modify the database basic rails convention anyway so if you follow that you're somewhat safe but that won't prevent you from more sophisticated attack similar to what Matt did here we're using the post method to get in there what rails does is in every form that you generate in a rails application has this strange thing called an authenticity token that has a really long hash value that's a key and that is in every form so when you send a form to your website rails will check for that token and if it's not there it will fail so a cross site request forgery won't have that key in the form so it can't forge that pass over however if cross site scripting in other words they got JavaScript loaded onto one of your movie night pages they could detect that and they could find your token and use that as well so these things kind of cross-pollinate and are sort of just get together session spoofing I'll let you talk about this okay and I'll talk a little bit about session spoofing so who remembers this one fireshoot right so fireshoot was kind of a big deal right it was for the first time it was incredibly simple and straightforward to exploit a long known vulnerability in my applications but you could simply install browser plugin and view and spoof the sessions popular social media sites around you it didn't work based off of being on an open network an open wifi so an encrypted wifi so I can do a demo back here would anyone am I going to capture anyone's session? I'm not going to do the demo but basically how do you work around this because it was taking advantage of the fact that so it was unencrypted network traffic and you're never carved into a promiscuous mode you would capture ongoing traffic from a browser to a third party site and scoop the session information out of it and just submit that session info as your own writing on top of the react session so how can you get around that how can we use web developers and the creators websites prevent this one require SSL this is 2011 that time has come you secure cookies so by default you can do it with cookies you can mark them as HTTP only so they can't be manipulated through JavaScript by default they will be passed across either an HTTP or an HTTPS connection you can mark cookies as secure so they only be pushed up to the server on HTTPS connections and for session cookies particularly that's a great thing something else that's an upcoming I believe it's going to be an upcoming version standard search transport security it's going to be a new HTTP header that's securely in draft that a server can actually direct browsers and clients that they must operate over TLS or SSL to communicate with SSL that's at protocol level one way to quickly enable all of those things with the drop-ins there's rack SSL written by Josh Peake you can just use the rack middleware and will automatically force SSL we'll mark cookies as secure they include that the emerging header I think just within the last couple of weeks we saw Twitter finally enabled an option still off by default and now there's an option you can go to your account and force all connections over SSL you can have a while back this was entirely over H2DS which is a good thing Gmail quite a long time ago went entirely SSL or Google apps and there's a white paper that I don't think we have a link to in here but people will maybe Google published a white paper while back basically claiming that the energy and the cost impact of enabling SSL across the board was negligible with respect to the potential cost of a secure to reach the myth of the notion that SSL is too much to know or had to be computationally or what happened in the past so let's summarize here I want to state up front when I started this talk I thought I would find all kinds of problems in Rails turns out they exist but we had to do a number of things to enable them in this particular web application we had to turn off Rails protection against sending cookies to JavaScript we had to bypass the raw filtering that Rails does naturally now so Rails by default will do a lot of these things for you there's just a couple coding things that you have to be mindful of in summary trust nothing don't assume that the user is on your side because he might not be standard data security patches, get the latest patches for Rails because they constantly fix things as they find holes and if you're on a back rev you're probably missing some security issues there there is a rail security mailing list and if you're not on it you should be bypass the things that we had to bypass to do a lot of these demos always scope your finds by the proper user to make sure you only find things that are permitted avoid using raw or use a whitelist to sanitize your output here's a good one do a security audit we had an outside firm do an audit of a couple of our programs it was very enlightening and worthwhile to have a firm that knows what they're doing and ask them to look over your database and finally just be aware you and I probably don't I know I don't, don't think like a hacker but put yourself in that mindset and think of sneaky things that could be done and just be proactive about that I think we're out of time 30 seconds maybe one question in the back, yes did you guys look at the OWASP SAPI project what that does to measures and rails right now I've not looked at, have you I am I'm aware of it but I've not actually read it so who would you recommend doing so well I've always been curious I don't know enough myself to really compare and know where the holes are between them but really there's only we probably should there are automated tools that can detect some of these common faults and they'll start looking out there and look for places they can inject SQL, inject JavaScript and kind of report so I think when we did the security audit that's how I thought we'd do it okay well thank you very much