Permalink
Browse files

Add authentication, localize some more

  • Loading branch information...
manveru committed Jan 1, 2009
1 parent 8c6574d commit e3682bf148307bb29fb94a98375a38cb8308d73c
Showing with 232 additions and 25 deletions.
  1. +14 −0 helper/localize.rb
  2. +123 −0 helper/user.rb
  3. +10 −5 layout/default.haml
  4. +5 −0 locale/locale_en.yaml
  5. +50 −0 node/auth.rb
  6. +1 −0 node/init.rb
  7. +5 −11 node/page.rb
  8. +11 −0 view/auth/login.haml
  9. +3 −3 view/diff.haml
  10. +5 −3 view/index.haml
  11. +5 −3 view/show.haml
View
@@ -0,0 +1,14 @@
+module Innate
+ module Helper
+ module Localize
+ def locale
+ locale = session[:language] || Innate::Options.for(:wiki).default_language
+ response['Content-Language'] = locale
+ end
+
+ def l(*strings)
+ strings.map{|s| "((#{s}))" }.join(' ')
+ end
+ end
+ end
+end
View
@@ -0,0 +1,123 @@
+module Innate
+ module Helper
+ module User
+ def user
+ session[:user]
+ end
+
+ def logged_in?
+ session[:user]
+ end
+ end
+ end
+end
+
+__END__
+
+ # This helper provides a convenience wrapper for handling authentication
+ # and persistence of users.
+ #
+ # Example:
+ #
+ # class MainController < Ramaze::Controller
+ # def index
+ # if logged_in?
+ # "Hello #{user.name}"
+ # else
+ # A('login', :href => Rs(:login))
+ # end
+ # end
+ #
+ # def login
+ # user_login if reuqest.post?
+ # end
+ # end
+
+ module User
+ # return existing or instantiate User::Wrapper
+ def user
+ model = ancestral_trait[:user_model] ||= ::User
+ callback = ancestral_trait[:user_callback] ||= nil
+ STATE[:user] ||= Wrapper.new(model, callback)
+ end
+
+ # shortcut for user.user_login but default argument are request.params
+
+ def user_login(creds = request.params)
+ user._login(creds)
+ end
+
+ # shortcut for user.user_logout
+
+ def user_logout
+ user._logout
+ end
+
+ def logged_in?
+ user._logged_in?
+ end
+
+ # Wrapper for the ever-present "user" in your application.
+ # It wraps around an arbitrary instance and worries about authentication
+ # and storing information about the user in the session.
+ #
+ # In order to not interfere with the wrapped instance/model we start our
+ # methods with an underscore.
+ # Suggestions on improvements as usual welcome.
+ class Wrapper < BlankSlate
+ attr_accessor :_model, :_callback, :_user
+
+ def initialize(model, callback)
+ @_model, @_callback = model, callback
+ @_user = nil
+ _login
+ end
+
+ def _login(creds = _persistence)
+ if @_user = _would_login?(creds)
+ self._persistence = creds
+ end
+ end
+
+ # The callback should return an instance of the user, otherwise it
+ # should answer with nil.
+ #
+ # This will not actually login, just check whether the credentials
+ # would result in a user.
+ def _would_login?(creds)
+ if c = @_callback
+ c.call(creds)
+ elsif _model.respond_to?(:authenticate)
+ _model.authenticate(creds)
+ else
+ Log.warn("Helper::User has no callback and there is no %p::authenticate" % _model)
+ nil
+ end
+ end
+
+ def _logout
+ _persistence.clear
+ STATE[:user] = nil
+ end
+
+ def _logged_in?
+ !!_user
+ end
+
+ def _persistence=(creds)
+ Current.session[:USER] = creds
+ end
+
+ def _persistence
+ Current.session[:USER] || {}
+ end
+
+ # Refer everything not known
+ def method_missing(meth, *args, &block)
+ return unless _user
+ _user.send(meth, *args, &block)
+ end
+ end
+ end
+ end
+end
View
@@ -3,7 +3,7 @@
%html
%head
- %title Ramaze Wiki
+ %title= l('Ramaze Wiki')
%link{:rel => 'stylesheet', :href => '/css/screen.css', :type => 'text/css'}
%link{:rel => 'stylesheet', :href => '/css/coderay.css', :type => 'text/css'}
- if uv_style = session[:uv_style]
@@ -12,12 +12,17 @@
.head
.title
%a{:href => '/Home', :alt => 'Home'}
- %h1 Ramaze Wiki
- %h2 A minimal git based wiki
+ %h1= l('Ramaze Wiki')
+ %h2= l('A minimal git based wiki')
.menu
- %a{:href => '/list'} List Pages
- %a{:href => r(:random)} Random Page
+ %a{:href => '/list'}= l('List Pages')
+ %a{:href => r(:random)}= l('Random Page')
+ - if logged_in?
+ %a{:href => Auth.r(:logout)}= l('Log out')
+ - else
+ %a{:href => Auth.r(:login)}= l('Log in')
.locale
%a{:href => r(:language, 'en')} English
+ %a{:href => r(:language, 'de')} Deutsch
%a{:href => r(:language, 'ja')} 日本語
.content= content
View
@@ -17,3 +17,8 @@ Move to different page: Move to different page
Text: Text
Create: Create
Wiki index: Wiki index
+Ramaze Wiki: Ramaze Wiki
+A minimal git based wiki: A minimal git based wiki
+List Pages: List Pages
+Random Page: Random Page
+Log out: Log out
View
@@ -0,0 +1,50 @@
+require 'yaml/store'
+
+class User
+ ACCOUNTS = YAML::Store.new('accounts.yaml')
+
+ def self.register(name, pass)
+ sync do |acc|
+ acc[name] = digestify(pass)
+ end
+ end
+
+ def self.check(name, pass)
+ sync do |acc|
+ return acc[name] == digestify(pass)
+ end
+ end
+
+ def self.sync
+ Innate.sync{ ACCOUNTS.transaction{ yield(ACCOUNTS) } }
+ end
+
+ def self.digestify(pass)
+ Digest::SHA1.hexdigest(pass)
+ end
+end
+
+class Auth
+ include Innate::Node
+ map '/auth'
+ layout :default
+ provide :html => :haml
+ helper :user, :localize
+
+ def login
+ redirect PageNode.r('/') if logged_in?
+ return unless request.post?
+
+ user, pass = request[:user, :pass]
+
+ if ::User.check(user.to_s.strip, pass.to_s.strip)
+ session[:user] = user
+ redirect_referrer
+ end
+ end
+
+ def logout
+ session.delete(:user)
+ redirect_referrer
+ end
+end
View
@@ -1,2 +1,3 @@
require 'node/css'
require 'node/page'
+require 'node/auth'
View
@@ -2,6 +2,7 @@ class PageNode
include Innate::Node
map '/'
layout 'default'
+ helper :user, :localize
provide :html => :haml
@@ -14,14 +15,15 @@ def index(*name)
end
def edit(*name)
- redirect_referrer if name.empty?
+ redirect_referrer if name.empty? || !logged_in?
@name = name.join('/')
@page = page_of(@name)
@title = to_title(@name)
@text = @page.content
end
def save
+ redirect_referrer unless logged_in?
name, text = request[:name, :text]
page = page_of(name)
@@ -34,6 +36,7 @@ def save
end
def move
+ redirect_referrer unless logged_in?
from, to = request[:from, :to]
if from and to
@@ -45,6 +48,7 @@ def move
end
def delete(name)
+ redirect_referrer unless logged_in?
raise "change"
page_of(name).delete
@@ -85,18 +89,8 @@ def language(name)
redirect_referrer
end
- def locale
- locale = session[:language] || Innate::Options.for(:wiki).default_language
- p :locale => locale
- response['Content-Language'] = locale
- end
-
private
- def l(*strings)
- strings.map{|s| "((#{s}))" }.join(' ')
- end
-
def page_of(name)
page = Page[name]
page.language = locale
View
@@ -0,0 +1,11 @@
+#login
+ %form{:method => :post}
+ %fieldset
+ %legend= l('Log in')
+ .pair
+ %label{:for => :form_user}= l('Username')
+ %input#form_user{:type => :text, :name => :user}
+ .pair
+ %label{:for => :form_pass}= l('Password')
+ %input#form_pass{:type => :password, :name => :pass}
+ %input{:type => :submit, :value => l('Log in')}
View
@@ -1,11 +1,11 @@
%h1
- l("Diff")
+ = l("Diff")
%a{:href => r(:show, @sha, @name)}= h(@sha)
- l("to")
+ = l("to")
%a{:href => r(@name)}= h(@name)
.uv_select
- %b l("Select your style")
+ %b= l("Select your style")
- current = session[:uv_style]
- @styles.each do |style|
%br/
View
@@ -1,11 +1,13 @@
.mod
%b= l('Control') + ':'
- if @page and @page.exists?
- %a{:href => r(:edit, @name)}= l('Edit')
- %a{:href => r(:delete, @name)}= l('Delete')
%a{:href => r(:history, @name)}= l('History')
+ - if logged_in?
+ %a{:href => r(:edit, @name)}= l('Edit')
+ %a{:href => r(:delete, @name)}= l('Delete')
- elsif @name
- %a{:href => r(:edit, @name)}= l('Create')
+ - if logged_in?
+ %a{:href => r(:edit, @name)}= l('Create')
.toc
%b= l('Table of Contents')
View
@@ -1,11 +1,13 @@
.mod
%b= l('Control') + ':'
- if @page and @page.exists?
- %a{:href => r(:edit, @name)}= l('Edit')
- %a{:href => r(:delete, @name)}= l('Delete')
%a{:href => r(:history, @name)}= l('History')
+ - if logged_in?
+ %a{:href => r(:edit, @name)}= l('Edit')
+ %a{:href => r(:delete, @name)}= l('Delete')
- elsif @name
- %a{:href => r(:edit, @name)}= l('Create')
+ - if logged_in?
+ %a{:href => r(:edit, @name)}= l('Create')
.toc
%b= l('Table of Contents')

0 comments on commit e3682bf

Please sign in to comment.