require 'base64' # # Password Protected Behavior for Radiant # created by: M@ McCray - elucidata.net/mattmccray.com # version: 0.2 # contact: mmccray@elucidata.net # # change log: 0.2 - Updated to support the new behavior filters # 0.1 - Initial version # class PasswordProtectedBehavior < Behavior::Base register "Password Protected" description %{ The Password Protected behavior allows you to post information that requires a password to view. You define the users, passwords, realm, and the error message in a config part. Example config part: protected: realm: My Realm error_message: You do not have access to this resource users: username1: password1 username2: password2 } attr_reader :username before_filter :authenticate_user, :for=>:all # Actually... The page probably can be cached now... def cache_page? false end define_tags do url = request.request_uri unless request.nil? tag "username" do |tag| username end end define_child_tags do url = request.request_uri unless request.nil? tag "username" do |tag| username end end private def authenticate_user(request, response) @username, passwd = get_auth_data(request, response) conf = page_config['protected'] || {'users'=>{}} # check if authorized # try to get user if conf['users'].has_key?(username) and passwd == conf['users'][username] true else # the user does not exist or the password was wrong response.headers["Status"] = "401 Unauthorized" response.headers["WWW-Authenticate"] = %Q(Basic realm="#{conf['realm'] || 'Radiant CMS'}") response.body = conf['error_message'] || "Access Denied" false end end def get_auth_data(request, response) user, pass = '', '' # extract authorisation credentials if request.env.has_key? 'X-HTTP_AUTHORIZATION' # try to get it where mod_rewrite might have put it authdata = request.env['X-HTTP_AUTHORIZATION'].to_s.split elsif request.env.has_key? 'Authorization' # for Apace/mod_fastcgi with -pass-header Authorization authdata = request.env['Authorization'].to_s.split elsif request.env.has_key? 'HTTP_AUTHORIZATION' # this is the regular location authdata = request.env['HTTP_AUTHORIZATION'].to_s.split elsif request.env.has_key? 'Authorization' # this is the regular location, for Apache 2 authdata = @request.env['Authorization'].to_s.split end # at the moment we only support basic authentication if authdata and authdata[0] == 'Basic' user, pass = Base64.decode64(authdata[1]).split(':')[0..1] end return [user, pass] end end