diff options
Diffstat (limited to 'lib')
| -rw-r--r-- | lib/extensions/couchrest.rb | 95 | ||||
| -rw-r--r-- | lib/leap_web.rb | 4 | ||||
| -rw-r--r-- | lib/tasks/leap_web_core_tasks.rake | 25 | ||||
| -rw-r--r-- | lib/tasks/leap_web_users_tasks.rake | 10 | ||||
| -rw-r--r-- | lib/tasks/test.rake | 19 | ||||
| -rw-r--r-- | lib/warden/session_serializer.rb | 13 | ||||
| -rw-r--r-- | lib/warden/strategies/secure_remote_password.rb | 81 | ||||
| -rw-r--r-- | lib/webfinger.rb | 6 | ||||
| -rw-r--r-- | lib/webfinger/host_meta_presenter.rb | 30 | ||||
| -rw-r--r-- | lib/webfinger/user_presenter.rb | 35 | 
10 files changed, 301 insertions, 17 deletions
| diff --git a/lib/extensions/couchrest.rb b/lib/extensions/couchrest.rb new file mode 100644 index 0000000..95f5d92 --- /dev/null +++ b/lib/extensions/couchrest.rb @@ -0,0 +1,95 @@ +module CouchRest +  module Model +    module Designs + +      class View + +        # so we can called Ticket.method.descending or Ticket.method.ascending +        def ascending +          self +        end +      end + +      class DesignMapper +        def load_views(dir) +          Dir.glob("#{dir}/*.js") do |js| +            name = File.basename(js, '.js') +            file = File.open(js, 'r') +            view name.to_sym, +              :map => file.read, +              :reduce => "function(key, values, rereduce) { return sum(values); }" +          end +        end +      end +    end + +    module Connection + +      module ClassMethods + +        def use_database(db) +          @database = prepare_database(db) +        rescue RestClient::Exception, +          Errno::EHOSTUNREACH, +          Errno::ECONNREFUSED => e +          message = "Could not connect to couch database #{db} due to #{e.to_s}" +          Rails.logger.warn message +          raise e.class.new(message) if APP_CONFIG[:reraise_errors] +        end +      end + +    end + +    module Utils +      module Migrate +        def self.load_all_models_with_engines +          self.load_all_models_without_engines +          return unless defined?(Rails) +          Dir[Rails.root + 'engines/*/app/models/**/*.rb'].each do |path| +            require path +          end +        end + +        class << self +          alias_method_chain :load_all_models, :engines +        end + +        def dump_all_models +          prepare_directory +          find_models.each do |model| +            model.design_docs.each do |design| +              dump_design(model, design) +            end +          end +        end + +        protected + +        def dump_design(model, design) +          dir = prepare_directory model.name.tableize +          filename = design.id.sub('_design/','') + '.json' +          puts dir + filename +          design.checksum +          File.open(dir + filename, "w") do |file| +            file.write(JSON.pretty_generate(design.to_hash)) +          end +        end + +        def prepare_directory(dir = '') +          dir = Rails.root + 'tmp' + 'designs' + dir +          Dir.mkdir(dir) unless Dir.exists?(dir) +          return dir +        end + +      end +    end + +  end + +  class ModelRailtie +    config.action_dispatch.rescue_responses.merge!( +      'CouchRest::Model::DocumentNotFound' => :not_found, +      'RestClient::ResourceNotFound' => :not_found +    ) +  end +end diff --git a/lib/leap_web.rb b/lib/leap_web.rb deleted file mode 100644 index 9495fc6..0000000 --- a/lib/leap_web.rb +++ /dev/null @@ -1,4 +0,0 @@ -require 'leap_web_core' -require 'leap_web_certs' -require 'leap_web_users' -# do we want billing and help here? diff --git a/lib/tasks/leap_web_core_tasks.rake b/lib/tasks/leap_web_core_tasks.rake new file mode 100644 index 0000000..ec6abac --- /dev/null +++ b/lib/tasks/leap_web_core_tasks.rake @@ -0,0 +1,25 @@ +namespace :couchrest do + +  desc "Dump all the design docs found in each model" +  task :dump => :environment do +    CouchRest::Model::Utils::Migrate.load_all_models +    CouchRest::Model::Utils::Migrate.dump_all_models +  end +end + +namespace :cleanup do +   +  desc "Cleanup all expired session documents" +  task :sessions => :environment do +    # make sure this is the same as in +    #   config/initializers/session_store.rb +    store = CouchRest::Session::Store.new expire_after: 1800 +    store.cleanup(store.expired) +  end + +  desc "Cleanup all expired tokens" +  task :tokens => :environment do +    Token.destroy_all_expired +  end +end + diff --git a/lib/tasks/leap_web_users_tasks.rake b/lib/tasks/leap_web_users_tasks.rake new file mode 100644 index 0000000..62bcbe9 --- /dev/null +++ b/lib/tasks/leap_web_users_tasks.rake @@ -0,0 +1,10 @@ +# desc "Explaining what the task does" +# task :leap_web_users do +#   # Task goes here +# end + +# recommended that for our setup, we should have this triggered from a cron job in puppet rather than using whenever gem +desc "Send one month warning messages" +task :leap_web_users do +  User.send_one_month_warnings +end diff --git a/lib/tasks/test.rake b/lib/tasks/test.rake index 3c87b45..d96b625 100644 --- a/lib/tasks/test.rake +++ b/lib/tasks/test.rake @@ -1,18 +1,11 @@  namespace :test do -  Rails::SubTestTask.new(:units => "test:prepare") do |t| -    t.libs << "test" -    t.pattern = '*/test/unit/**/*_test.rb' -  end - -  Rails::SubTestTask.new(:functionals => "test:prepare") do |t| -    t.libs << "test" -    t.pattern = '*/test/functional/**/*_test.rb' -  end - -  Rails::SubTestTask.new(:integration => "test:prepare") do |t| -    t.libs << "test" -    t.pattern = '*/test/integration/**/*_test.rb' +  [:units, :functionals, :integration].each do |type| +    Rails::SubTestTask.new(type => "test:prepare") do |t| +      t.libs << "test" +      subdir = type.to_s.singularize +      t.pattern = "engines/*/test/#{subdir}/**/*_test.rb" +    end    end  end diff --git a/lib/warden/session_serializer.rb b/lib/warden/session_serializer.rb new file mode 100644 index 0000000..81d7076 --- /dev/null +++ b/lib/warden/session_serializer.rb @@ -0,0 +1,13 @@ +module Warden +  # Setup Session Serialization +  class SessionSerializer +    def serialize(record) +      [record.class.name, record.id] +    end + +    def deserialize(keys) +      klass, id = keys +      klass.constantize.find(id) +    end +  end +end diff --git a/lib/warden/strategies/secure_remote_password.rb b/lib/warden/strategies/secure_remote_password.rb new file mode 100644 index 0000000..2c334c6 --- /dev/null +++ b/lib/warden/strategies/secure_remote_password.rb @@ -0,0 +1,81 @@ +module Warden +  module Strategies +    class SecureRemotePassword < Warden::Strategies::Base + +      def valid? +        handshake? || authentication? +      end + +      def authenticate! +        if authentication? +          validate! +        else  # handshake +          initialize! +        end +      end + +      protected + +      def handshake? +        params['A'] && params['login'] +      end + +      def authentication? +        params['client_auth'] && session[:handshake] +      end + +      def validate! +        if client = validate +          success!(User.find_by_login(client.username)) +        else +          Rails.logger.warn "Login attempt failed." +          Rails.logger.debug debug_info +          Rails.logger.debug "Received: #{params['client_auth']}" +          session.delete(:handshake) +          fail!(:base => "invalid_user_pass") +        end +      end + +      def validate +        session[:handshake].authenticate(params['client_auth']) +      end + +      def initialize! +        if user = User.find_by_login(id) +          client = SRP::Client.new user.username, +            :verifier => user.verifier, +            :salt => user.salt +          session[:handshake] = SRP::Session.new(client, params['A']) +          custom! json_response(session[:handshake]) +        else +          fail! :base => 'invalid_user_pass' +        end +      rescue SRP::InvalidEphemeral +        fail!(:base => "invalid_ephemeral") +      end + +      def json_response(object) +        [ 200, +          {"Content-Type" => "application/json; charset=utf-8"}, +          [object.to_json] +        ] +      end + +      def id +        params["id"] || params["login"] +      end + +      protected + +      def debug_info +        JSON.pretty_generate(session[:handshake].internal_state) +      end + +    end +  end +  Warden::Strategies.add :secure_remote_password, +    Warden::Strategies::SecureRemotePassword + +end + + diff --git a/lib/webfinger.rb b/lib/webfinger.rb new file mode 100644 index 0000000..dd49b41 --- /dev/null +++ b/lib/webfinger.rb @@ -0,0 +1,6 @@ +module Webfinger + +  autoload :HostMetaPresenter, 'webfinger/host_meta_presenter' +  autoload :UserPresenter, 'webfinger/user_presenter' + +end diff --git a/lib/webfinger/host_meta_presenter.rb b/lib/webfinger/host_meta_presenter.rb new file mode 100644 index 0000000..84ab7a9 --- /dev/null +++ b/lib/webfinger/host_meta_presenter.rb @@ -0,0 +1,30 @@ +require 'uri' + +class Webfinger::HostMetaPresenter +  def initialize(request) +    @request = request +  end + +  def to_json(options = {}) +    { +      subject: subject, +      links: links +    }.to_json(options) +  end + +  def subject +    url = URI.parse(@request.url) +    url.path = '' +    url.to_s +  end + +  def links +    { lrdd: { type: 'application/xrd+xml', template: webfinger_template } } +  end + +  protected + +  def webfinger_template(path = 'webfinger', query_param='q') +    "#{subject}/#{path}?#{query_param}={uri}" +  end +end diff --git a/lib/webfinger/user_presenter.rb b/lib/webfinger/user_presenter.rb new file mode 100644 index 0000000..329f477 --- /dev/null +++ b/lib/webfinger/user_presenter.rb @@ -0,0 +1,35 @@ +class Webfinger::UserPresenter +  include Rails.application.routes.url_helpers +  attr_accessor :user + +  def initialize(user, request) +    @user = user +    @request = request +  end + +  def to_json(options = {}) +    { +      subject: subject, +      links:   links +    }.to_json(options) +  end + +  def subject +    "acct:#{@user.email_address}" +  end + +  def links +    links = {} +    links[:public_key] = { type: 'PGP', href: key } if key +    return links +  end + +  protected + +  def key +    if @user.public_key.present? +      Base64.encode64(@user.public_key.to_s) +    end +  end + +end | 
