Saturday, October 31, 2015

Auth with Rails, Angular, and UI-router across domains


     So let me be the first to say that although I normally hate mixing front end with back end systems, especially opinionated MVCs like angular. Its really not as bad once you get used to it. But its not simple or easy most of the time, mainly because you need to understand the backend and front end systems like the back of your hand to fully appreciate how they work together. And I am no expert in rails or angular, but like many developers, my job expects me to get my shit together and make it work.

   Our first problem was that we could not use Devise, because we are sharing across domains, and we cant use CORS because some of our users still use vista. So we are instead sharing tokens and data using JSONP, and encrypting and decrypting with a custom build. Not really perfect, and I would have loved to use CORS instead, but sometimes you need to get creative.


    So I am starting this tutorial assuming you already have a rails/angular app created and integrated. If not i would suggest this tutorial to start you off. And I am also assuming you need to build your own auth that does not use devise. So first some stuff you will need to use and might want to read up on in case you have not yet. First thing, services, they are great, and if your new to angular you might not have used them yet, especially if your project is still young and mostly in controllers. Two, localstorage, this will keep our important variables saved even after page refreshes. Which by the way services will also help prevent as you will see soon.

  So well start with the routes first, I am assuming you are using ui-router, and if not, I would HIGHLY suggest you try it out. Its much better at routing then the standby angular comes with, at least for large projects, and especially projects living inside backend systems.



 Just to make sure we are all on the same page. Your rails routes should look something like this, and your controller should look like this.




While your angular routes should be way more robust.


    As im sure you can guess you'll need to add authenticate to your routes, put true if you want them lock them up from non-logged in users, and false otherwise. Also just in case you dont know this yet, please keep in mind that the home route is the route that will feed in from your application.html.erb file.


   As you can see i have a few more routes, including login and all have authenticate on them. Make sure you add the otherwise to the bottom of your routes, and set it to your login page(if thats what you desire).





    So then make sure you have ngstorage installed, i link to it earlier in the tutorial. Make sure its in the app and in the require slot, all that good stuff. Then we can start to get into the fun stuff. Lets put all of this into a file called auth.js, or if you want, authService.js/authCtrl.js, does not really matter.




 So what this does is every time your application starts running and you are changing your routes, like clicking to new pages. It checks to see if you need to be authenticated, which we specified on the routes earlier, and then what your AuthService says, either true or false. If you are not authenticated then it takes you to the login page. Thats what state.transitionTo is for.


So your service will look something like this, you at least probably need a few of these, but you can omit filter.  And inside your service we will have three functions, log in, log out, and isAuthenticated. We will call these functions in the app.run and in our controller. Well start with isAuthenticated.


So this is pretty damn simple, we saved a boolean value in a local storage variable called AuthAccept, and when we call that variable we are looking to see if its still true or false. So now we can go check out our log in function which has all the magic.

 Okay so when we call this in our controller we are going to pass it two variables, the email and password. As you can see we send these values in a JSONP object that returns a failure or success message. If it fails we pop up error messages, and if they are a real user we save a few things to local storage. Now if your using CORS you will do this with a post request, and will have way less code, and all the power to you. But if your unlucky and have to use JSONP your code will look closer to this. Once you confirm that the user is a real one, then you need to set AuthAccept = true, and put it in local storage, this saves that our user is logged in. And you can set the state.go to home, or wherever you want your users to be directed.


 This is the logout function, basically you just need to clear out all your local storage variables, especially AuthAccept, and send them back to the login page.


So now we can look at our controller, its pretty simple, just calling the functions in AuthService from a click event. But what you might take not of, is if you need your local storage variables in the scope you will need to set them equal to a scope variable, as im doing here. I use this to hide my footer and nav bar among other things.

And thats basically the gist of this tutorial, if anyone has questions or concerns feel free to comment.









Sunday, October 18, 2015

Practice makes Perfect

      So now that I have finally settled down into my job, which has taken longer then I expected. I plan to start writing for the blog again once a week, with a combination of technical advice too actual blogs about my technical feats. Though i must admit that I dont find it to be a good idea to post what I am accomplishing at work, which is a shame, because im doing all kinds of cool stuff, but i digress.

    This post is mostly for us newbie programers, and maybe some of our older more experienced developers as well. But I have realized that it is important to continuously practice interview problems. Now I know what your thinking, they suck, you dont need them because you have a good job/loads of experience. But I think its important for us to do these problems when we are NOT trying to find a job, even once a week would be enough. You know why? Because they suck horribly when your looking for a job, they are stressful and you are constantly questioning yourself while doing them. They dont even really help you with becoming a better programmer, they just make you dread the interview experience. No matter how great of a developer you are, these problems probably stress you out, especially since they can range anywhere from normal 15 minute questions to 3 hour long I need a degree in math to solve this crap hard. And if your interviewer is worth his salt he will make sure to give you one to match your skill level, which means even our most experienced developers should be ready to have these hard problems thrown at them.

     We all need to know right now that the way these problems are used in an interview setting and non interview setting are totally different. I would wager most of them are not actually meant to be interview questions, its just easier for everyone if we use these instead of creating our own, which honestly gives us developers a leg up. In an interview settings its all about solve this problem with none of the normal tools you would have at your disposal and in an uncomfortable setting on this whiteboard with an eraser that hardly works, have fun. You could say not all interviews are like this, some people let you use the internet, and allow you to use your computer, even run the code a few times, but a good chunk of interviews will be like i described. It was this kind of interviewing that made me HATE these problems with a burning passion hotter then the sun, I hated every second of doing them. But once i got a job i decided to go back to them and give them a second chance but this time without me being stressed to do them perfectly, or fast, or without the help of stack overflow and docs.

     I realized how great these problems were, and honestly how much fun they can be. They gave me a chance to solve problems that i would never get at my job, they reintroduced me to math terms and equations i hadn't heard for years. Once i had solved problems in my most capable way I also normally went to stack-overflow to see how the professionals solve the problem, and I always learn something new from them. They can take ten lines of code and turn it into one, they can show you a new way to solve problems that takes up less space and has a better run time. These problems are a great way to get you to think outside the box, read the docs, and find great tricks and tips. The best part is its okay if you cant solve the problem in less then 5 minutes, its okay if its been 5 months since you needed to convert a dictionary into a list and you need to review the docs. Because the point is to learn and get better, thats the ultimate goal of most developers. We want to solve problems better, faster, and smarter. But to do that takes time and practice, so im linking the sites I use as practice.


https://www.interviewcake.com/ - Subscribe to their weekly interview email, its great practice, and the problems are always original, out of the box, and never easy. Although they are more geared towards interviewing questions, the problems are great even if you aren't interviewing. Be ready to spend about 30 minutes to an hour on their problems.


https://projecteuler.net/archives  - Project Euler problems are pretty popular, they are a lot of peoples go to when interviewing, but they are way better when your not. You can go through their archives, it will probably take you at least a year to finish them all, and then you can move to the most recent.

http://coderbyte.com/CodingArea/ - Coderbyte is really great if you need to practice problems in more then one language, which is why I love them. Their interface and problems are easy and fun, and are organized from easy to hard.


I would start with these sources before going to crazy on anything else, and remember, practice makes perfect, but fun turns into passion and talent.