Search code examples
clojurebasic-authenticationcompojure

basic http auth in Clojure/Friend


I am trying to make a basic auth for an API in Clojure with friend.

Here is the login request :

curl -X POST -H "Content-Type: application/x-www-form-urlencoded" -d 'user=myuser%40email.com&pass=super-secret-password' http://localhost:3000/login/

I am using compojure as well, but I'm not sure how to reuse the linked example. Here are the parts that I don't know how to change :

  • How do I replace the username/password fields with user/pass fields like in my curl request ? I am able to extract them from the raw request, but I don't know how to pass it to Friend (do I need to change the credential-fn?).

  • Replace the user atom with data from the database. I have a auth [email password] that returns true or false (fetching from the database and using bcrypt). I can also fetch the user role from the database. How do I use the database (specifically I use mongo/monger) instead of the user atom ?


Solution

  • You can provide a totally different credential-fn, or stick to the demo where credential-fn is implemented using cemerick.friend.credentials/bcrypt-credential-fn. Read the doc of bcrypt-credential-fn at https://github.com/cemerick/friend/blob/master/src/cemerick/friend/credentials.clj, it is quite long. It expects a load-credentials-fn that loads a user given a username string, then checks if the password matches. In the demo, the load-credentials-fn is a map in the users atom, but if you have a database you would want to provide a different load-credentials-fn function that would lookup the database, you don't want to load your users table in the map in the atom.