Commit 3b26008f39933d623e2fac02e9d56235bd9a7974

Authored by Caio Almeida
Committed by Larissa Reis
1 parent 0e192c22

Ticket #195: Login

app/controllers/application_controller.rb
... ... @@ -121,7 +121,9 @@ class ApplicationController < ActionController::Base
121 121 end
122 122  
123 123 def user
124   - current_user.person if logged_in?
  124 + if logged_in?
  125 + current_user.person || current_user.external_person
  126 + end
125 127 end
126 128  
127 129 alias :current_person :user
... ...
app/helpers/application_helper.rb
... ... @@ -813,7 +813,7 @@ module ApplicationHelper
813 813 {s_('contents|More viewed') => {href: url_for({host: host, controller: 'search', action: 'contents', filter: 'more_popular'})}},
814 814 {s_('contents|Most commented') => {href: url_for({host: host, controller: 'search', action: 'contents', filter: 'more_comments'})}}
815 815 ]
816   - if logged_in?
  816 + if logged_in? && !current_user.external_person_id
817 817 links.push(_('New content') => modal_options({:href => url_for({:controller => 'cms', :action => 'new', :profile => current_user.login, :cms => true})}))
818 818 end
819 819  
... ... @@ -829,7 +829,7 @@ module ApplicationHelper
829 829 {s_('people|More active') => {href: url_for({host: host, controller: 'search', action: 'people', filter: 'more_active'})}},
830 830 {s_('people|More popular') => {href: url_for({host: host, controller: 'search', action: 'people', filter: 'more_popular'})}}
831 831 ]
832   - if logged_in?
  832 + if logged_in? && !current_user.external_person_id
833 833 links.push(_('My friends') => {:href => url_for({:profile => current_user.login, :controller => 'friends'})})
834 834 links.push(_('Invite friends') => {:href => url_for({:profile => current_user.login, :controller => 'invite', :action => 'friends'})})
835 835 end
... ... @@ -846,7 +846,7 @@ module ApplicationHelper
846 846 {s_('communities|More active') => {href: url_for({host: host, controller: 'search', action: 'communities', filter: 'more_active'})}},
847 847 {s_('communities|More popular') => {href: url_for({host: host, controller: 'search', action: 'communities', filter: 'more_popular'})}}
848 848 ]
849   - if logged_in?
  849 + if logged_in? && !current_user.external_person_id
850 850 links.push(_('My communities') => {:href => url_for({:profile => current_user.login, :controller => 'memberships'})})
851 851 links.push(_('New community') => {:href => url_for({:profile => current_user.login, :controller => 'memberships', :action => 'new_community'})})
852 852 end
... ...
app/models/concerns/external_user.rb 0 → 100644
... ... @@ -0,0 +1,62 @@
  1 +require 'ostruct'
  2 +
  3 +module ExternalUser
  4 + extend ActiveSupport::Concern
  5 +
  6 + included do
  7 + attr_accessor :external_person_id
  8 + end
  9 +
  10 + def external_person
  11 + ExternalPerson.where(id: self.external_person_id).first
  12 + end
  13 +
  14 + module ClassMethods
  15 + def webfinger_lookup(login, domain, environment)
  16 + if login && domain && environment.has_federated_network?(domain)
  17 + # Ask if network at <domain> has user with login <login>
  18 + # FIXME: Make an actual request to the federated network, which should return nil if not found
  19 + {
  20 + login: login
  21 + }
  22 + else
  23 + nil
  24 + end
  25 + end
  26 +
  27 + def external_login(login, password, domain)
  28 + # Call Noosfero /api/login
  29 + uri = URI.parse('http://' + domain + '/api/v1/login')
  30 + response = Net::HTTP.post_form(uri, { login: login, password: password })
  31 + if response.code == '301'
  32 + # Follow a redirection
  33 + uri = URI.parse(response.header['location'])
  34 + response = Net::HTTP.post_form(uri, { login: login, password: password })
  35 + end
  36 + response.code.to_i / 100 === 2 ? JSON.parse(response.body) : nil
  37 + end
  38 +
  39 + # Authenticates a user from an external social network
  40 + def external_authenticate(username, password, environment)
  41 + login, domain = username.split('@')
  42 + webfinger = User.webfinger_lookup(login, domain, environment)
  43 + if webfinger
  44 + user = User.external_login(login, password, domain)
  45 + if user
  46 + u = User.new
  47 + u.login = login
  48 + # FIXME: Instead of the struct below, we should use the "webfinger" object returned by the webfinger_lookup method
  49 + webfinger = OpenStruct.new(
  50 + identifier: user['user']['person']['identifier'],
  51 + name: user['user']['person']['name'],
  52 + domain: domain,
  53 + email_md5: Digest::MD5.hexdigest(user['user']['email'])
  54 + )
  55 + u.external_person_id = ExternalPerson.get_or_create(webfinger).id
  56 + return u
  57 + end
  58 + end
  59 + nil
  60 + end
  61 + end
  62 +end
... ...
app/models/environment.rb
... ... @@ -1009,6 +1009,11 @@ class Environment &lt; ApplicationRecord
1009 1009 HashWithIndifferentAccess.new :name => name
1010 1010 end
1011 1011  
  1012 + def has_federated_network?(domain)
  1013 + # FIXME: Should return whether "domain" is whitelisted in this environment as a federated network
  1014 + true
  1015 + end
  1016 +
1012 1017 private
1013 1018  
1014 1019 def default_language_available
... ...
app/models/user.rb
... ... @@ -149,7 +149,7 @@ class User &lt; ApplicationRecord
149 149 u.generate_private_token_if_not_exist
150 150 return u
151 151 end
152   -
  152 +
153 153 return User.external_authenticate(login, password, environment)
154 154 end
155 155  
... ...
lib/external_user.rb
... ... @@ -1,36 +0,0 @@
1   -module ExternalUser
2   - included do
3   - attr_accessor :external_person_id
4   - end
5   -
6   - def self.webfinger_lookup(login, domain, environment)
7   - if login && domain && environment.has_federated_network?(domain)
8   - # Ask if network at <domain> has user with login <login>
9   - # FIXME: Make an actual request to the federated network, which should return nil if not found
10   - {
11   - login: login
12   - }
13   - end
14   - nil
15   - end
16   -
17   - def self.external_login
18   - # Call Noosfero /api/login
19   - end
20   -
21   - # Authenticates a user from an external social network
22   - def self.external_authenticate(username, password, environment)
23   - login, domain = username.split('@')
24   - webfinger = User.webfinger_lookup(login, domain, environment)
25   - if webfinger
26   - user = User.external_login(login, password, domain)
27   - if user
28   - u = User.new
29   - # Set other fields on "u" based on information in "user" returned by API
30   - u.external_person_id = ExternalPerson.get_or_create(login, domain).id
31   - return u
32   - end
33   - end
34   - nil
35   - end
36   -end