How do I do a really simple Sinatra LDAP authentication?

ldap, ruby, sinatra

Solution

I'd probably go with something like this:

require 'directoryUser'
require 'sinatra'

enable :sessions

helpers do
  def authorize!
    redirect(to('/login')) unless session[:user_id]
  end
end

get '/login' do
  haml :login # with the login form
end

post '/login' do
  user = DirectoryUser.authenticate(params[:username], params[:password])

  if user
    session[:user_id] = user.id
    # Or: session[:logged_in] = true, depending on your needs.
    redirect to('/protected')
  else
    redirect to('/login')
  end
end

get '/protected' do
  authorize!
  'This route is protected'
end

get '/unprotected' do  
  'This route is unprotected'
end

Problem

I looked at the Sinatra docs and they only seem to reference HTTP authentication. I'm looking for a really simple way to control access to routes based on a user being authorised/authenticated via an LDAP server. I've already built a class that does the LDAP bit and returns an LDAP object if the user has successfully authenticated and nil if they haven't: ``` >>DirectoryUser.authenticate('user', 'password') #<DirectoryUser:0x007ffb589a2328> ``` I can use this to determine if they've successfully authenticated or not. As a next step I want to splice this into a simple Sinatra app that provides a form to collect the LDAP user and password: ``` require 'directoryUser' require 'sinatra' enable :sessions get '/form' do username = params[:username] password = params[:password] haml :form end ``` Then I want to only allow routes if the 'DirectoryUser' object exists: ``` get '/protected' do # Only if DirectoryUser object exists "This route is protected" end get '/unprotected' do "This route is unprotected" end ``` I've spent hours trying to find an answer to this but so far and can't seem to find anything that works for me.

Original source