Commit 97db792e350fc9dad1b30214d89d2f772e67a4a3

Authored by Antonio Terceiro
1 parent f7d6ffda

ActionItem1032: allowing login with custom domain

app/controllers/my_profile/profile_editor_controller.rb
@@ -11,6 +11,7 @@ class ProfileEditorController < MyProfileController @@ -11,6 +11,7 @@ class ProfileEditorController < MyProfileController
11 # edits the profile info (posts back) 11 # edits the profile info (posts back)
12 def edit 12 def edit
13 @profile_data = profile 13 @profile_data = profile
  14 + @possible_domains = profile.possible_domains
14 if request.post? 15 if request.post?
15 if profile.update_attributes(params[:profile_data]) 16 if profile.update_attributes(params[:profile_data])
16 redirect_to :action => 'index' 17 redirect_to :action => 'index'
app/helpers/application_helper.rb
@@ -130,21 +130,6 @@ module ApplicationHelper @@ -130,21 +130,6 @@ module ApplicationHelper
130 link_to text, p.url, options 130 link_to text, p.url, options
131 end 131 end
132 132
133 - def link_to_myprofile(text, url = {}, profile = nil, options = {})  
134 - p = if profile  
135 - Profile[profile]  
136 - else  
137 - user  
138 - end  
139 - link_to text, p.admin_url.merge(url), options  
140 - end  
141 -  
142 - def link_to_document(doc, text = nil, html_options = {}, url_options = {})  
143 - text ||= doc.title  
144 - path = doc.path.split(/\//)  
145 - link_to text, homepage_path({:profile => doc.profile.identifier , :page => path, :view => true}.merge(url_options)), html_options  
146 - end  
147 -  
148 def link_if_permitted(link, permission = nil, target = nil) 133 def link_if_permitted(link, permission = nil, target = nil)
149 if permission.nil? || current_user.person.has_permission?(permission, target) 134 if permission.nil? || current_user.person.has_permission?(permission, target)
150 link 135 link
@@ -736,9 +721,7 @@ module ApplicationHelper @@ -736,9 +721,7 @@ module ApplicationHelper
736 end 721 end
737 722
738 def login_url 723 def login_url
739 - options = { :controller => 'account', :action => 'login' }  
740 - options.merge!(:protocol => 'https://', :host => request.host) unless ENV['RAILS_ENV'] == 'development' || environment.disable_ssl  
741 - url_for(options) 724 + url_for(Noosfero.url_options.merge({ :controller => 'account', :action => 'login', :host => request.host }))
742 end 725 end
743 726
744 def base_url 727 def base_url
app/helpers/profile_editor_helper.rb
@@ -117,4 +117,20 @@ module ProfileEditorHelper @@ -117,4 +117,20 @@ module ProfileEditorHelper
117 select(object, method, [[_('[Select ...]'), nil]] + ProfileEditorHelper::SCHOOLING_STATUS.map{|s| [gettext(s), s]}, {}, options) 117 select(object, method, [[_('[Select ...]'), nil]] + ProfileEditorHelper::SCHOOLING_STATUS.map{|s| [gettext(s), s]}, {}, options)
118 end 118 end
119 119
  120 + def select_preferred_domain(object)
  121 + profile = instance_variable_get("@#{object}")
  122 + domains = []
  123 + if profile
  124 + if profile.preferred_domain
  125 + # FIXME should be able to change
  126 + return ''
  127 + else
  128 + domains = profile.possible_domains
  129 + end
  130 + else
  131 + domains = environment.domains
  132 + end
  133 + labelled_form_field(__('Preferred domain name:'), select(object, :preferred_domain_id, domains.map {|item| [item.name, item.id]}, :prompt => '<' + _('Select domain') + '>'))
  134 + end
  135 +
120 end 136 end
app/models/domain.rb
@@ -63,4 +63,25 @@ class Domain < ActiveRecord::Base @@ -63,4 +63,25 @@ class Domain < ActiveRecord::Base
63 end 63 end
64 end 64 end
65 65
  66 + @hosting = {}
  67 +
  68 + # Tells whether the given domain name is hosting a profile or not.
  69 + #
  70 + # Since this is going to be called a lot, The queries are cached so the
  71 + # database is hit only for the first query for a given domain name. This way,
  72 + # transfering a domain from a profile to an environment of vice-versa
  73 + # requires restarting the application.
  74 + def self.hosting_profile_at(domainname)
  75 + @hosting[domainname] ||=
  76 + begin
  77 + domain = Domain.find_by_name(domainname)
  78 + !domain.nil? && (domain.owner_type == 'Profile')
  79 + end
  80 + end
  81 +
  82 + # clears the cache of hosted domains. Used for testing.
  83 + def self.clear_cache
  84 + @hosting = {}
  85 + end
  86 +
66 end 87 end
app/models/environment.rb
@@ -45,6 +45,7 @@ class Environment < ActiveRecord::Base @@ -45,6 +45,7 @@ class Environment < ActiveRecord::Base
45 'warn_obsolete_browser' => _('Enable warning of obsolete browser'), 45 'warn_obsolete_browser' => _('Enable warning of obsolete browser'),
46 'wysiwyg_editor_for_environment_home' => _('Use WYSIWYG editor to edit environment home page'), 46 'wysiwyg_editor_for_environment_home' => _('Use WYSIWYG editor to edit environment home page'),
47 'media_panel' => _('Media panel in WYSIWYG editor'), 47 'media_panel' => _('Media panel in WYSIWYG editor'),
  48 + 'select_preferred_domain' => _('Select preferred domains per profile'),
48 } 49 }
49 end 50 end
50 51
app/models/person.rb
@@ -42,6 +42,7 @@ class Person < Profile @@ -42,6 +42,7 @@ class Person < Profile
42 end 42 end
43 43
44 FIELDS = %w[ 44 FIELDS = %w[
  45 + preferred_domain
45 nickname 46 nickname
46 sex 47 sex
47 address 48 address
app/models/profile.rb
@@ -94,6 +94,7 @@ class Profile < ActiveRecord::Base @@ -94,6 +94,7 @@ class Profile < ActiveRecord::Base
94 belongs_to :user 94 belongs_to :user
95 95
96 has_many :domains, :as => :owner 96 has_many :domains, :as => :owner
  97 + belongs_to :preferred_domain, :class_name => 'Domain', :foreign_key => 'preferred_domain_id'
97 belongs_to :environment 98 belongs_to :environment
98 99
99 has_many :articles, :dependent => :destroy 100 has_many :articles, :dependent => :destroy
@@ -327,19 +328,15 @@ class Profile < ActiveRecord::Base @@ -327,19 +328,15 @@ class Profile < ActiveRecord::Base
327 end 328 end
328 329
329 def url 330 def url
330 - @url ||= if self.domains.empty?  
331 - generate_url(:controller => 'content_viewer', :action => 'view_page', :page => [])  
332 - else  
333 - Noosfero.url_options.merge({ :host => self.domains.first.name, :controller => 'content_viewer', :action => 'view_page', :page => []})  
334 - end 331 + @url ||= generate_url(:controller => 'content_viewer', :action => 'view_page', :page => [])
335 end 332 end
336 333
337 def admin_url 334 def admin_url
338 - generate_url(:controller => 'profile_editor', :action => 'index') 335 + { :profile => identifier, :controller => 'profile_editor', :action => 'index' }
339 end 336 end
340 337
341 def public_profile_url 338 def public_profile_url
342 - generate_url(:controller => 'profile', :action => 'index') 339 + generate_url(:profile => identifier, :controller => 'profile', :action => 'index')
343 end 340 end
344 341
345 def generate_url(options) 342 def generate_url(options)
@@ -347,7 +344,25 @@ class Profile < ActiveRecord::Base @@ -347,7 +344,25 @@ class Profile < ActiveRecord::Base
347 end 344 end
348 345
349 def url_options 346 def url_options
350 - Noosfero.url_options.merge({ :host => self.environment.default_hostname, :profile => self.identifier}) 347 + options = { :host => default_hostname, :profile => (hostname ? nil : self.identifier) }
  348 + Noosfero.url_options.merge(options)
  349 + end
  350 +
  351 + def default_hostname
  352 + @default_hostname ||= (hostname || environment.default_hostname)
  353 + end
  354 +
  355 + def hostname
  356 + if preferred_domain
  357 + return preferred_domain.name
  358 + else
  359 + domain = self.domains.first
  360 + domain ? domain.name : nil
  361 + end
  362 + end
  363 +
  364 + def possible_domains
  365 + environment.domains + domains
351 end 366 end
352 367
353 # FIXME this can be SLOW 368 # FIXME this can be SLOW
app/models/profile_list_block.rb
@@ -64,12 +64,10 @@ class ProfileListBlock < Block @@ -64,12 +64,10 @@ class ProfileListBlock < Block
64 title = self.title 64 title = self.title
65 nl = "\n" 65 nl = "\n"
66 lambda do 66 lambda do
67 - #list = profiles.map {|item| content_tag( 'li', profile_image_link(item) ) }.join("\n ")  
68 count=0 67 count=0
69 list = profiles.map {|item| 68 list = profiles.map {|item|
70 count+=1 69 count+=1
71 profile_image_link( item ) #+ 70 profile_image_link( item ) #+
72 - #( ( count%2 == 0 && count < profiles.size ) ? nl+'</tr><tr>' : '' )  
73 }.join("\n ") 71 }.join("\n ")
74 if list.empty? 72 if list.empty?
75 list = '<div class="common-profile-list-block-none">'+ _('None') +'</div>' 73 list = '<div class="common-profile-list-block-none">'+ _('None') +'</div>'
app/views/account/index.rhtml
@@ -6,7 +6,7 @@ @@ -6,7 +6,7 @@
6 </p> 6 </p>
7 7
8 <p> 8 <p>
9 -<%= link_to_myprofile _('Edit Personal details.'), :controller => 'profile_editor' %> 9 +<%= link_to _('Edit Personal details.'), :controller => 'profile_editor', :profile => user.identifier, :action => 'index' %>
10 <%= _('You can change your personal details.') %> 10 <%= _('You can change your personal details.') %>
11 </p> 11 </p>
12 12
@@ -16,7 +16,7 @@ @@ -16,7 +16,7 @@
16 </p> 16 </p>
17 17
18 <p> 18 <p>
19 -<%= link_to_myprofile(_('Manage content.'), :controller => 'cms') %> 19 +<%= link_to(_('Manage content.'), :controller => 'cms', :profile => user.identifier, :action => 'index') %>
20 <%= _('Manage your content.') %> 20 <%= _('Manage your content.') %>
21 </p> 21 </p>
22 22
app/views/blocks/profile_info.rhtml
@@ -19,7 +19,7 @@ @@ -19,7 +19,7 @@
19 <li><%= link_to _('View profile'), block.owner.public_profile_url %></li> 19 <li><%= link_to _('View profile'), block.owner.public_profile_url %></li>
20 <li><%= link_to(_('Products/Services'), :controller => 'catalog', :profile => block.owner.identifier) if block.owner.enterprise? && !block.owner.environment.enabled?('disable_products_for_enterprises') %></li> 20 <li><%= link_to(_('Products/Services'), :controller => 'catalog', :profile => block.owner.identifier) if block.owner.enterprise? && !block.owner.environment.enabled?('disable_products_for_enterprises') %></li>
21 <% if !user.nil? and user.has_permission?('edit_profile', profile) %> 21 <% if !user.nil? and user.has_permission?('edit_profile', profile) %>
22 - <li><%= link_to _('Control panel'), :controller => 'profile_editor' %></li> 22 + <li><%= link_to _('Control panel'), block.owner.admin_url %></li>
23 <% end %> 23 <% end %>
24 <% if profile.person? %> 24 <% if profile.person? %>
25 <li><%= _('Since %{year}/%{month}') % { :year => block.owner.created_at.year, :month => block.owner.created_at.month } %></li> 25 <li><%= _('Since %{year}/%{month}') % { :year => block.owner.created_at.year, :month => block.owner.created_at.month } %></li>
app/views/cms/view.rhtml
@@ -7,7 +7,7 @@ @@ -7,7 +7,7 @@
7 <h1 id='article-full-path'> 7 <h1 id='article-full-path'>
8 <%= icon('cms') %> 8 <%= icon('cms') %>
9 <%= link_to profile.identifier, :action => 'index' %> 9 <%= link_to profile.identifier, :action => 'index' %>
10 - <%= @article.hierarchy.map {|item| " / " + ((item == @article) ? item.name : link_to_document(item)) } %> 10 + <%= @article.hierarchy.map {|item| " / " + ((item == @article) ? item.name : link_to(item.slug, :id => item.id)) } %>
11 </h1> 11 </h1>
12 <% end %> 12 <% end %>
13 13
@@ -42,7 +42,7 @@ @@ -42,7 +42,7 @@
42 </td> 42 </td>
43 <td> 43 <td>
44 <%= link_to _('Properties'), :action => 'edit', :id => folder.id %> 44 <%= link_to _('Properties'), :action => 'edit', :id => folder.id %>
45 - <%= link_to_document(folder, _('Public view')) %> 45 + <%= link_to _('Public view'), folder.url %>
46 <%= link_to _('Use as homepage'), { :action => 'set_home_page', :id => folder.id }, :method => :post %> 46 <%= link_to _('Use as homepage'), { :action => 'set_home_page', :id => folder.id }, :method => :post %>
47 <%= link_to _('Delete'), { :action => 'destroy', :id => folder.id }, :method => :post, :confirm => _('Are you sure that you want to remove this folder? Note that all the items inside it will also be removed!') %> 47 <%= link_to _('Delete'), { :action => 'destroy', :id => folder.id }, :method => :post, :confirm => _('Are you sure that you want to remove this folder? Note that all the items inside it will also be removed!') %>
48 </td> 48 </td>
@@ -68,7 +68,7 @@ @@ -68,7 +68,7 @@
68 </td> 68 </td>
69 <td> 69 <td>
70 <%= link_to _('Edit'), :action => 'edit', :id => item.id %> 70 <%= link_to _('Edit'), :action => 'edit', :id => item.id %>
71 - <%= link_to_document(item, _('Public view')) %> 71 + <%= link_to _('Public view'), item.url %>
72 <%= link_to _('Spread this'), :action => 'publish', :id => item.id %> 72 <%= link_to _('Spread this'), :action => 'publish', :id => item.id %>
73 <%= link_to _('Use as homepage'), { :action => 'set_home_page', :id => item.id }, :method => :post %> 73 <%= link_to _('Use as homepage'), { :action => 'set_home_page', :id => item.id }, :method => :post %>
74 <%= link_to _('Delete'), { :action => 'destroy', :id => item.id }, :method => :post, :confirm => _('Are you sure that you want to remove this item?') %> 74 <%= link_to _('Delete'), { :action => 'destroy', :id => item.id }, :method => :post, :confirm => _('Are you sure that you want to remove this item?') %>
app/views/content_viewer/_article.rhtml
1 -<%= link_to_document(article, '', :class => article.css_class_name) %>  
2 -<span><%= link_to_document(article) %></span> 1 +<%= link_to '', article.url, '', :class => article.css_class_name) %>
  2 +<span><%= link_to article.title, article.view_url %></span>
app/views/content_viewer/_uploaded_file.rhtml
1 <% if uploaded_file.image? %> 1 <% if uploaded_file.image? %>
2 - <div> <%= link_to_document(uploaded_file, image_tag(uploaded_file.public_filename(:thumb))) %> </div> 2 + <div> <%= link_to image_tag(uploaded_file.public_filename(:thumb)), uploaded_file.view_url %> </div>
3 <% else %> 3 <% else %>
4 <%= render :partial => 'article', :object => uploaded_file %> 4 <%= render :partial => 'article', :object => uploaded_file %>
5 <% end %> 5 <% end %>
app/views/content_viewer/view_page.rhtml
@@ -34,24 +34,24 @@ @@ -34,24 +34,24 @@
34 <div id="article-actions" class="hidden"> 34 <div id="article-actions" class="hidden">
35 <% unless @page.blog? %> 35 <% unless @page.blog? %>
36 <%= link_to content_tag( 'span', label_for_edit_article(@page) ), 36 <%= link_to content_tag( 'span', label_for_edit_article(@page) ),
37 - { :controller => 'cms', :action => 'edit', :id => @page }, 37 + profile.admin_url.merge({ :controller => 'cms', :action => 'edit', :id => @page.id }),
38 :class => 'button with-text icon-edit' %> 38 :class => 'button with-text icon-edit' %>
39 <% end %> 39 <% end %>
40 <% if !(profile.kind_of?(Enterprise) && environment.enabled?('disable_cms')) %> 40 <% if !(profile.kind_of?(Enterprise) && environment.enabled?('disable_cms')) %>
41 <% if @page != profile.home_page %> 41 <% if @page != profile.home_page %>
42 <%= link_to content_tag( 'span', _('Delete') ), 42 <%= link_to content_tag( 'span', _('Delete') ),
43 - { :controller => 'cms', :action => 'destroy', :id => @page }, 43 + profile.admin_url.merge({ :controller => 'cms', :action => 'destroy', :id => @page }),
44 :class => 'button with-text icon-delete' %> 44 :class => 'button with-text icon-delete' %>
45 <% end %> 45 <% end %>
46 <% if profile.kind_of?(Person) && !environment.enabled?('disable_cms') %> 46 <% if profile.kind_of?(Person) && !environment.enabled?('disable_cms') %>
47 <%= link_to content_tag( 'span', _('Spread this') ), 47 <%= link_to content_tag( 'span', _('Spread this') ),
48 - { :controller => 'cms', :action => 'publish', :id => @page }, 48 + profile.admin_url.merge({ :controller => 'cms', :action => 'publish', :id => @page }),
49 :class => 'button with-text icon-spread' %> 49 :class => 'button with-text icon-spread' %>
50 <% end %> 50 <% end %>
51 <% if @page.display_as_gallery? %> 51 <% if @page.display_as_gallery? %>
52 - <%= button('upload-file', _('Upload files'), :controller => 'cms', :action => 'upload_files', :parent_id => (@page.folder? ? @page : @page.parent)) %> 52 + <%= button('upload-file', _('Upload files'), profile.admin_url.merge(:controller => 'cms', :action => 'upload_files', :parent_id => (@page.folder? ? @page : @page.parent))) %>
53 <% else %> 53 <% else %>
54 - <%= lightbox_button(:new, label_for_new_article(@page), :controller => 'cms', :action => 'new', :parent_id => (@page.folder? ? @page : (@page.parent.nil? ? nil : @page.parent))) %> 54 + <%= lightbox_button(:new, label_for_new_article(@page), profile.admin_url.merge(:controller => 'cms', :action => 'new', :parent_id => (@page.folder? ? @page : (@page.parent.nil? ? nil : @page.parent)))) %>
55 <% end %> 55 <% end %>
56 <% end %> 56 <% end %>
57 </div> 57 </div>
@@ -73,7 +73,7 @@ @@ -73,7 +73,7 @@
73 73
74 <% if @page.parent && !@page.parent.path.blank? %> 74 <% if @page.parent && !@page.parent.path.blank? %>
75 <div id="article-parent"> 75 <div id="article-parent">
76 - <%= link_to_document(@page.parent, _('Go back')) %> 76 + <%= link_to _('Go back'), @page.parent.url %>
77 </div> 77 </div>
78 <% end %> 78 <% end %>
79 79
app/views/layouts/application.rhtml
@@ -49,7 +49,6 @@ @@ -49,7 +49,6 @@
49 <%= icon_theme_stylesheet_tag %> 49 <%= icon_theme_stylesheet_tag %>
50 50
51 <%= stylesheet_link_tag 'iepngfix/iepngfix.css' %> 51 <%= stylesheet_link_tag 'iepngfix/iepngfix.css' %>
52 - <base href="<%= base_url %>"/>  
53 </head> 52 </head>
54 53
55 <body class='noosfero category<%= category_color %><%= 54 <body class='noosfero category<%= category_color %><%=
@@ -110,7 +109,7 @@ @@ -110,7 +109,7 @@
110 109
111 <div id="navigation_bar"> 110 <div id="navigation_bar">
112 <%= link_to "<span>"+ @environment.name() +"</span>", 111 <%= link_to "<span>"+ @environment.name() +"</span>",
113 - { :controller=>"home" }, 112 + @environment.top_url,
114 :id=>"menu_link_to_envhome", 113 :id=>"menu_link_to_envhome",
115 :title=>@environment.name %> 114 :title=>@environment.name %>
116 <% unless environment.enabled?(:disable_categories) %> 115 <% unless environment.enabled?(:disable_categories) %>
app/views/manage_products/index.rhtml
@@ -47,6 +47,6 @@ @@ -47,6 +47,6 @@
47 <%= button :add, _('Add raw material'), :action => 'new_consumption' %> 47 <%= button :add, _('Add raw material'), :action => 'new_consumption' %>
48 48
49 <p> 49 <p>
50 -<%= link_to_myprofile( '<span>'+ _('Back') +'</span>', {}, @profile.identifier, :class => 'button with-text icon-back' ) %> 50 +<%= link_to( '<span>'+ _('Back') +'</span>', { :controller => 'profile_editor', :profile => @profile.identifier, :action => 'index' }, :class => 'button with-text icon-back' ) %>
51 </p> 51 </p>
52 52
app/views/profile_editor/_person_form.rhtml
@@ -9,6 +9,7 @@ @@ -9,6 +9,7 @@
9 </div> 9 </div>
10 <% end %> 10 <% end %>
11 11
  12 +<%= optional_field(@person, 'preferred_domain', select_preferred_domain(:profile_data)) %>
12 <%= optional_field(@person, 'contact_information', f.text_field(:contact_information)) %> 13 <%= optional_field(@person, 'contact_information', f.text_field(:contact_information)) %>
13 <%= optional_field(@person, 'contact_phone', labelled_form_field(_('Home phone'), text_field(:profile_data, :contact_phone))) %> 14 <%= optional_field(@person, 'contact_phone', labelled_form_field(_('Home phone'), text_field(:profile_data, :contact_phone))) %>
14 <%= optional_field(@person, 'cell_phone', f.text_field(:cell_phone)) %> 15 <%= optional_field(@person, 'cell_phone', f.text_field(:cell_phone)) %>
app/views/profile_editor/edit.rhtml
@@ -13,6 +13,7 @@ @@ -13,6 +13,7 @@
13 <% end %> 13 <% end %>
14 </div> 14 </div>
15 15
  16 +
16 <h2><%= _('Privacy options') %></h2> 17 <h2><%= _('Privacy options') %></h2>
17 <p> 18 <p>
18 <%= _('This profile is:') %> 19 <%= _('This profile is:') %>
app/views/shared/user_menu.rhtml
@@ -27,10 +27,9 @@ @@ -27,10 +27,9 @@
27 </li> 27 </li>
28 <% end %> 28 <% end %>
29 29
30 - <li><%= link_to_myprofile( '<span class="icon-menu-ctrl-panel"></span>'+ _('Control panel'),  
31 - {}, nil, :id => 'link_edit_profile',  
32 - :help => _('Control panel: change your picture, edit your personal information, create content or change the way your home page looks.')  
33 - ) %></li> 30 + <li>
  31 + <%= link_to('<span class="icon-menu-ctrl-panel"></span>'+ _('Control panel'), { :controller => 'profile_editor', :action => 'index', :profile => user.identifier }, :id => 'link_edit_profile', :help => _('Control panel: change your picture, edit your personal information, create content or change the way your home page looks.')) %>
  32 + </li>
34 33
35 <% if user.is_admin?(environment) %> 34 <% if user.is_admin?(environment) %>
36 <li><%= link_to( '<span class="icon-menu-"></span>'+ _('Admin'), 35 <li><%= link_to( '<span class="icon-menu-"></span>'+ _('Admin'),
config/routes.rb
@@ -15,18 +15,11 @@ ActionController::Routing::Routes.draw do |map| @@ -15,18 +15,11 @@ ActionController::Routing::Routes.draw do |map|
15 ## Public controllers 15 ## Public controllers
16 ###################################################### 16 ######################################################
17 17
18 - # You can have the root of your site routed by hooking up ''  
19 - hosted_domain_matcher = lambda do |env|  
20 - domain = Domain.find_by_name(env[:host])  
21 - domain && (domain.owner_type == 'Profile')  
22 - end  
23 - map.connect 'profile/:profile/:action/:id', :controller => 'profile', :id => /.*/, :profile => /#{Noosfero.identifier_format}/, :conditions => { :if => hosted_domain_matcher }  
24 - map.connect '*page', :controller => 'content_viewer', :action => 'view_page', :conditions => { :if => hosted_domain_matcher }  
25 -  
26 map.connect 'test/:controller/:action/:id' , :controller => /.*test.*/ 18 map.connect 'test/:controller/:action/:id' , :controller => /.*test.*/
27 19
28 # -- just remember to delete public/index.html. 20 # -- just remember to delete public/index.html.
29 - map.connect '', :controller => "home" 21 + # You can have the root of your site routed by hooking up ''
  22 + map.connect '', :controller => "home", :conditions => { :if => lambda { |env| !Domain.hosting_profile_at(env[:host]) } }
30 23
31 # user account controller 24 # user account controller
32 map.connect 'account/new_password/:code', :controller => 'account', :action => 'new_password' 25 map.connect 'account/new_password/:code', :controller => 'account', :action => 'new_password'
@@ -83,7 +76,9 @@ ActionController::Routing::Routes.draw do |map| @@ -83,7 +76,9 @@ ActionController::Routing::Routes.draw do |map|
83 # cache stuff - hack 76 # cache stuff - hack
84 map.cache 'public/:action/:id', :controller => 'public' 77 map.cache 'public/:action/:id', :controller => 'public'
85 78
86 - # *content viewing* 79 + # match requests for content in domains hosted for profiles
  80 + map.connect '*page', :controller => 'content_viewer', :action => 'view_page', :conditions => { :if => lambda { |env| Domain.hosting_profile_at(env[:host])} }
  81 +
87 # XXX this route must come last so other routes have priority over it. 82 # XXX this route must come last so other routes have priority over it.
88 map.homepage ':profile/*page', :controller => 'content_viewer', :action => 'view_page', :profile => /#{Noosfero.identifier_format}/ 83 map.homepage ':profile/*page', :controller => 'content_viewer', :action => 'view_page', :profile => /#{Noosfero.identifier_format}/
89 84
@@ -9,7 +9,7 @@ @@ -9,7 +9,7 @@
9 # 9 #
10 # It's strongly recommended to check this file into your version control system. 10 # It's strongly recommended to check this file into your version control system.
11 11
12 -ActiveRecord::Schema.define(:version => 65) do 12 +ActiveRecord::Schema.define(:version => 66) do
13 13
14 create_table "article_versions", :force => true do |t| 14 create_table "article_versions", :force => true do |t|
15 t.integer "article_id" 15 t.integer "article_id"
@@ -87,8 +87,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do @@ -87,8 +87,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do
87 t.boolean "virtual", :default => false 87 t.boolean "virtual", :default => false
88 end 88 end
89 89
90 - add_index "articles_categories", ["article_id"], :name => "index_articles_categories_on_article_id"  
91 add_index "articles_categories", ["category_id"], :name => "index_articles_categories_on_category_id" 90 add_index "articles_categories", ["category_id"], :name => "index_articles_categories_on_category_id"
  91 + add_index "articles_categories", ["article_id"], :name => "index_articles_categories_on_article_id"
92 92
93 create_table "blocks", :force => true do |t| 93 create_table "blocks", :force => true do |t|
94 t.string "title" 94 t.string "title"
@@ -128,8 +128,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do @@ -128,8 +128,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do
128 t.boolean "virtual", :default => false 128 t.boolean "virtual", :default => false
129 end 129 end
130 130
131 - add_index "categories_profiles", ["profile_id"], :name => "index_categories_profiles_on_profile_id"  
132 add_index "categories_profiles", ["category_id"], :name => "index_categories_profiles_on_category_id" 131 add_index "categories_profiles", ["category_id"], :name => "index_categories_profiles_on_category_id"
  132 + add_index "categories_profiles", ["profile_id"], :name => "index_categories_profiles_on_profile_id"
133 133
134 create_table "comments", :force => true do |t| 134 create_table "comments", :force => true do |t|
135 t.string "title" 135 t.string "title"
@@ -207,8 +207,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do @@ -207,8 +207,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do
207 t.datetime "updated_at" 207 t.datetime "updated_at"
208 end 208 end
209 209
210 - add_index "product_categorizations", ["product_id"], :name => "index_product_categorizations_on_product_id"  
211 add_index "product_categorizations", ["category_id"], :name => "index_product_categorizations_on_category_id" 210 add_index "product_categorizations", ["category_id"], :name => "index_product_categorizations_on_category_id"
  211 + add_index "product_categorizations", ["product_id"], :name => "index_product_categorizations_on_product_id"
212 212
213 create_table "products", :force => true do |t| 213 create_table "products", :force => true do |t|
214 t.integer "enterprise_id" 214 t.integer "enterprise_id"
@@ -230,7 +230,7 @@ ActiveRecord::Schema.define(:version =&gt; 65) do @@ -230,7 +230,7 @@ ActiveRecord::Schema.define(:version =&gt; 65) do
230 t.string "type" 230 t.string "type"
231 t.string "identifier" 231 t.string "identifier"
232 t.integer "environment_id" 232 t.integer "environment_id"
233 - t.boolean "active", :default => true 233 + t.boolean "active", :default => true
234 t.string "address" 234 t.string "address"
235 t.string "contact_phone" 235 t.string "contact_phone"
236 t.integer "home_page_id" 236 t.integer "home_page_id"
@@ -241,13 +241,14 @@ ActiveRecord::Schema.define(:version =&gt; 65) do @@ -241,13 +241,14 @@ ActiveRecord::Schema.define(:version =&gt; 65) do
241 t.float "lat" 241 t.float "lat"
242 t.float "lng" 242 t.float "lng"
243 t.integer "geocode_precision" 243 t.integer "geocode_precision"
244 - t.boolean "enabled", :default => true  
245 - t.string "nickname", :limit => 16 244 + t.boolean "enabled", :default => true
  245 + t.string "nickname", :limit => 16
246 t.text "custom_header" 246 t.text "custom_header"
247 t.text "custom_footer" 247 t.text "custom_footer"
248 t.string "theme" 248 t.string "theme"
249 - t.boolean "public_profile", :default => true 249 + t.boolean "public_profile", :default => true
250 t.date "birth_date" 250 t.date "birth_date"
  251 + t.integer "preferred_domain_id"
251 end 252 end
252 253
253 add_index "profiles", ["environment_id"], :name => "index_profiles_on_environment_id" 254 add_index "profiles", ["environment_id"], :name => "index_profiles_on_environment_id"
@@ -285,8 +286,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do @@ -285,8 +286,8 @@ ActiveRecord::Schema.define(:version =&gt; 65) do
285 t.datetime "created_at" 286 t.datetime "created_at"
286 end 287 end
287 288
288 - add_index "taggings", ["tag_id"], :name => "index_taggings_on_tag_id"  
289 add_index "taggings", ["taggable_id", "taggable_type"], :name => "index_taggings_on_taggable_id_and_taggable_type" 289 add_index "taggings", ["taggable_id", "taggable_type"], :name => "index_taggings_on_taggable_id_and_taggable_type"
  290 + add_index "taggings", ["tag_id"], :name => "index_taggings_on_tag_id"
290 291
291 create_table "tags", :force => true do |t| 292 create_table "tags", :force => true do |t|
292 t.string "name" 293 t.string "name"
lib/zen3_terminology.rb
@@ -65,6 +65,7 @@ class Zen3Terminology &lt; Noosfero::Terminology::Custom @@ -65,6 +65,7 @@ class Zen3Terminology &lt; Noosfero::Terminology::Custom
65 'Disable activation of enterprises' => N_('Disable activation of organizations'), 65 'Disable activation of enterprises' => N_('Disable activation of organizations'),
66 'Manage community fields' => N_('Manage group fields'), 66 'Manage community fields' => N_('Manage group fields'),
67 'Create a new community' => N_('Create a new group'), 67 'Create a new community' => N_('Create a new group'),
  68 + 'Preferred domain name:' => N_('Choose your host community:'),
68 }) 69 })
69 end 70 end
70 71
test/functional/account_controller_test.rb
@@ -600,6 +600,7 @@ class AccountControllerTest &lt; Test::Unit::TestCase @@ -600,6 +600,7 @@ class AccountControllerTest &lt; Test::Unit::TestCase
600 end 600 end
601 601
602 should 'not point to SSL URL in login popup when in development mode' do 602 should 'not point to SSL URL in login popup when in development mode' do
  603 + @request.stubs(:ssl?).returns(false)
603 ENV.expects(:[]).with('RAILS_ENV').returns('development').at_least_once 604 ENV.expects(:[]).with('RAILS_ENV').returns('development').at_least_once
604 get :login_popup 605 get :login_popup
605 assert_no_tag :tag => 'form', :attributes => { :action => /^https:\/\// } 606 assert_no_tag :tag => 'form', :attributes => { :action => /^https:\/\// }
test/functional/application_controller_test.rb
@@ -234,32 +234,6 @@ class ApplicationControllerTest &lt; Test::Unit::TestCase @@ -234,32 +234,6 @@ class ApplicationControllerTest &lt; Test::Unit::TestCase
234 assert_no_tag :tag => 'div', :attributes => { :id => 'user_box' }, :descendant => { :tag => 'a', :attributes => { :href => 'http://web.mail/' } } 234 assert_no_tag :tag => 'div', :attributes => { :id => 'user_box' }, :descendant => { :tag => 'a', :attributes => { :href => 'http://web.mail/' } }
235 end 235 end
236 236
237 - should 'use environment top_url as base' do  
238 - Environment.any_instance.expects(:top_url).returns('http://www.lala.net')  
239 - get :index  
240 - assert_tag :tag => 'base', :attributes => { :href => 'http://www.lala.net' }  
241 - end  
242 -  
243 - should 'request environment top_url with ssl when under ssl for base' do  
244 - Environment.any_instance.expects(:top_url).with(true).returns('https://www.lala.net/')  
245 - @request.expects(:ssl?).returns(true).at_least_once  
246 - get :index  
247 - assert_tag :tag => 'base', :attributes => { :href => 'https://www.lala.net/' }  
248 - end  
249 -  
250 - should 'use correct environment for base tag' do  
251 - default = Environment.default  
252 - Environment.stubs(:default).returns(default)  
253 - default.stubs(:top_url).returns('http://default.com/')  
254 -  
255 - current = Environment.create!(:name => 'test environment')  
256 - current.domains.create!(:name => 'example.com')  
257 -  
258 - @request.expects(:host).returns('example.com').at_least_once  
259 - get :index  
260 - assert_tag :tag => 'base', :attributes => { :href => 'http://example.com' }  
261 - end  
262 -  
263 should 'display theme test panel when testing theme' do 237 should 'display theme test panel when testing theme' do
264 @request.session[:theme] = 'my-test-theme' 238 @request.session[:theme] = 'my-test-theme'
265 theme = mock 239 theme = mock
test/functional/profile_editor_controller_test.rb
@@ -632,4 +632,39 @@ class ProfileEditorControllerTest &lt; Test::Unit::TestCase @@ -632,4 +632,39 @@ class ProfileEditorControllerTest &lt; Test::Unit::TestCase
632 assert_tag :tag => 'a', :attributes => { :href => "/myprofile/default_user/cms/edit/#{profile.blog.id}" } 632 assert_tag :tag => 'a', :attributes => { :href => "/myprofile/default_user/cms/edit/#{profile.blog.id}" }
633 end 633 end
634 634
  635 + should 'not show select preferred domain if not enabled in environment' do
  636 + profile.environment.custom_person_fields = {}; profile.environment.save!
  637 +
  638 + get :edit, :profile => profile.identifier
  639 + assert_no_tag :tag => 'select', :attributes => { :name => 'profile_data[preferred_domain_id]' }
  640 + end
  641 +
  642 + should 'be able to choose preferred domain' do
  643 + profile.environment.custom_person_fields = {'preferred_domain' => {'required' => 'true', 'active' => 'true'} }; profile.environment.save!
  644 +
  645 + profile.domains << Domain.new(:name => 'myowndomain.net')
  646 + profile.environment.domains << Domain.new(:name => 'myenv.net')
  647 +
  648 + get :edit, :profile => profile.identifier
  649 + assert_tag :tag => 'select', :attributes => { :name => 'profile_data[preferred_domain_id]' }, :descendant => { :tag => "option", :content => 'myowndomain.net' }
  650 + assert_tag :tag => 'select', :attributes => { :name => 'profile_data[preferred_domain_id]' }, :descendant => { :tag => "option", :content => 'myenv.net' }
  651 +
  652 + post :edit, :profile => profile.identifier, :profile_data => { :preferred_domain_id => profile.domains.first.id.to_s }
  653 +
  654 + assert_equal 'myowndomain.net', Profile.find(profile.id).preferred_domain.name
  655 + end
  656 +
  657 + should 'be able to set no preferred domain at all' do
  658 + profile.environment.custom_person_fields = {'preferred_domain' => {'required' => 'true', 'active' => 'true'} }; profile.environment.save!
  659 +
  660 + profile.domains << Domain.new(:name => 'myowndomain.net')
  661 + profile.environment.domains << Domain.new(:name => 'myenv.net')
  662 +
  663 + get :edit, :profile => profile.identifier
  664 + assert_tag :tag => "select", :attributes => { :name => 'profile_data[preferred_domain_id]'}, :descendant => { :tag => 'option', :content => '&lt;Select domain&gt;', :attributes => { :value => '' } }
  665 +
  666 + post :edit, :profile => profile.identifier, :profile_data => { :preferred_domain_id => '' }
  667 + assert_nil Profile.find(profile.id).preferred_domain
  668 + end
  669 +
635 end 670 end
test/integration/routing_test.rb
@@ -2,6 +2,10 @@ require &quot;#{File.dirname(__FILE__)}/../test_helper&quot; @@ -2,6 +2,10 @@ require &quot;#{File.dirname(__FILE__)}/../test_helper&quot;
2 2
3 class RoutingTest < ActionController::IntegrationTest 3 class RoutingTest < ActionController::IntegrationTest
4 4
  5 + def setup
  6 + Domain.clear_cache
  7 + end
  8 +
5 # home page 9 # home page
6 ################################################################ 10 ################################################################
7 def test_homepage 11 def test_homepage
@@ -165,7 +169,6 @@ class RoutingTest &lt; ActionController::IntegrationTest @@ -165,7 +169,6 @@ class RoutingTest &lt; ActionController::IntegrationTest
165 end 169 end
166 170
167 def test_hosted_domain_routing 171 def test_hosted_domain_routing
168 -  
169 user = create_user('testuser').person 172 user = create_user('testuser').person
170 domain = Domain.create!(:name => 'example.com', :owner => user) 173 domain = Domain.create!(:name => 'example.com', :owner => user)
171 174
@@ -174,6 +177,15 @@ class RoutingTest &lt; ActionController::IntegrationTest @@ -174,6 +177,15 @@ class RoutingTest &lt; ActionController::IntegrationTest
174 assert_routing('/work/free-software', :controller => 'content_viewer', :action => 'view_page', :page => [ 'work', 'free-software'] ) 177 assert_routing('/work/free-software', :controller => 'content_viewer', :action => 'view_page', :page => [ 'work', 'free-software'] )
175 end 178 end
176 179
  180 + def test_root_of_hosted_domain
  181 + user = create_user('testuser').person
  182 + domain = Domain.create!(:name => 'example.com', :owner => user)
  183 +
  184 + ActionController::TestRequest.any_instance.expects(:host).returns('www.example.com')
  185 +
  186 + assert_routing('', :controller => 'content_viewer', :action => 'view_page', :page => [])
  187 + end
  188 +
177 def test_profile_under_hosted_domain 189 def test_profile_under_hosted_domain
178 community = Community.create!(:identifier => 'testcomm', :name => "test community") 190 community = Community.create!(:identifier => 'testcomm', :name => "test community")
179 domain = Domain.create!(:name => 'example.com', :owner => community) 191 domain = Domain.create!(:name => 'example.com', :owner => community)
test/unit/application_helper_test.rb
@@ -202,6 +202,9 @@ class ApplicationHelperTest &lt; Test::Unit::TestCase @@ -202,6 +202,9 @@ class ApplicationHelperTest &lt; Test::Unit::TestCase
202 environment = mock 202 environment = mock
203 environment.expects(:disable_ssl).returns(true).at_least_once 203 environment.expects(:disable_ssl).returns(true).at_least_once
204 stubs(:environment).returns(environment) 204 stubs(:environment).returns(environment)
  205 + request = mock
  206 + request.stubs(:host).returns('localhost')
  207 + stubs(:request).returns(request)
205 208
206 expects(:url_for).with(has_entries(:protocol => 'https://')).never 209 expects(:url_for).with(has_entries(:protocol => 'https://')).never
207 expects(:url_for).with(has_key(:controller)).returns("LALALA") 210 expects(:url_for).with(has_key(:controller)).returns("LALALA")
test/unit/domain_test.rb
@@ -3,6 +3,10 @@ require File.dirname(__FILE__) + &#39;/../test_helper&#39; @@ -3,6 +3,10 @@ require File.dirname(__FILE__) + &#39;/../test_helper&#39;
3 class DomainTest < Test::Unit::TestCase 3 class DomainTest < Test::Unit::TestCase
4 fixtures :domains, :environments, :profiles, :users 4 fixtures :domains, :environments, :profiles, :users
5 5
  6 + def setup
  7 + Domain.clear_cache
  8 + end
  9 +
6 # Replace this with your real tests. 10 # Replace this with your real tests.
7 def test_domain_name_format 11 def test_domain_name_format
8 c = Domain.new 12 c = Domain.new
@@ -83,4 +87,17 @@ class DomainTest &lt; Test::Unit::TestCase @@ -83,4 +87,17 @@ class DomainTest &lt; Test::Unit::TestCase
83 assert_nil Domain.find_by_name('colivre.net').profile 87 assert_nil Domain.find_by_name('colivre.net').profile
84 end 88 end
85 89
  90 + def test_hosted_domain
  91 + assert_equal false, Domain.hosting_profile_at('example.com')
  92 +
  93 + profile = create_user('hosted_user').person
  94 + Domain.create!(:name => 'example.com', :owner => profile)
  95 + assert_equal true, Domain.hosting_profile_at('example.com')
  96 + end
  97 +
  98 + def test_not_report_profile_hosted_for_environment_domains
  99 + Domain.create!(:name => 'example.com', :owner => Environment.default)
  100 + assert_equal false, Domain.hosting_profile_at('example.com')
  101 + end
  102 +
86 end 103 end
test/unit/profile_test.rb
1 require File.dirname(__FILE__) + '/../test_helper' 1 require File.dirname(__FILE__) + '/../test_helper'
2 2
3 class ProfileTest < Test::Unit::TestCase 3 class ProfileTest < Test::Unit::TestCase
4 - fixtures :profiles, :environments, :users, :roles 4 + fixtures :profiles, :environments, :users, :roles, :domains
5 5
6 def test_identifier_validation 6 def test_identifier_validation
7 p = Profile.new 7 p = Profile.new
@@ -284,7 +284,7 @@ class ProfileTest &lt; Test::Unit::TestCase @@ -284,7 +284,7 @@ class ProfileTest &lt; Test::Unit::TestCase
284 should "use own domain name instead of environment's for home page url" do 284 should "use own domain name instead of environment's for home page url" do
285 profile = Profile.create!(:name => "Test Profile", :identifier => 'testprofile', :environment_id => create_environment('mycolivre.net').id) 285 profile = Profile.create!(:name => "Test Profile", :identifier => 'testprofile', :environment_id => create_environment('mycolivre.net').id)
286 profile.domains << Domain.new(:name => 'micojones.net') 286 profile.domains << Domain.new(:name => 'micojones.net')
287 - assert_equal({:host => 'micojones.net', :controller => 'content_viewer', :action => 'view_page', :page => []}, profile.url) 287 + assert_equal({:host => 'micojones.net', :profile => nil, :controller => 'content_viewer', :action => 'view_page', :page => []}, profile.url)
288 end 288 end
289 289
290 should 'help developers by adding a suitable port to url options' do 290 should 'help developers by adding a suitable port to url options' do
@@ -1258,6 +1258,44 @@ class ProfileTest &lt; Test::Unit::TestCase @@ -1258,6 +1258,44 @@ class ProfileTest &lt; Test::Unit::TestCase
1258 assert_nil person.find_in_all_tasks(task2.id) 1258 assert_nil person.find_in_all_tasks(task2.id)
1259 end 1259 end
1260 1260
  1261 + should 'use environment hostname by default' do
  1262 + profile = Profile.new
  1263 + env = mock
  1264 + env.stubs(:default_hostname).returns('myenvironment.net')
  1265 + profile.stubs(:environment).returns(env)
  1266 + assert_equal 'myenvironment.net', profile.default_hostname
  1267 + end
  1268 +
  1269 + should 'use its first domain hostname name if available' do
  1270 + profile = create_user('testuser').person
  1271 + profile.domains << Domain.new(:name => 'myowndomain.net')
  1272 + assert_equal 'myowndomain.net', profile.default_hostname
  1273 + end
  1274 +
  1275 + should 'have a preferred domain name' do
  1276 + person = create_user('testuser').person
  1277 + domain = Domain.create!(:name => 'myowndomain.net', :owner => person)
  1278 + person.preferred_domain = domain
  1279 + person.save!
  1280 +
  1281 + assert_equal domain, Person.find(person.id).preferred_domain(true)
  1282 + end
  1283 +
  1284 + should 'use preferred domain for hostname' do
  1285 + profile = Profile.new
  1286 + profile.stubs(:preferred_domain).returns(Domain.new(:name => 'preferred.net'))
  1287 + assert_equal 'preferred.net', profile.url[:host]
  1288 + end
  1289 +
  1290 + should 'provide a list of possible preferred domain names' do
  1291 + profile = create_user('testuser').person
  1292 + domain1 = Domain.create!(:name => 'envdomain.net', :owner => profile.environment)
  1293 + domain2 = Domain.create!(:name => 'profiledomain.net', :owner => profile)
  1294 +
  1295 + assert_includes profile.possible_domains, domain1
  1296 + assert_includes profile.possible_domains, domain2
  1297 + end
  1298 +
1261 private 1299 private
1262 1300
1263 def assert_invalid_identifier(id) 1301 def assert_invalid_identifier(id)