diff --git a/plugins/driven_signup/controllers/admin/driven_signup_plugin/admin_controller.rb b/plugins/driven_signup/controllers/admin/driven_signup_plugin/admin_controller.rb new file mode 100644 index 0000000..2bbef3a --- /dev/null +++ b/plugins/driven_signup/controllers/admin/driven_signup_plugin/admin_controller.rb @@ -0,0 +1,26 @@ +class DrivenSignupPlugin::AdminController < AdminController + + no_design_blocks + + protect 'edit_environment_features', :environment + + def index + + end + + def new + @auth = environment.driven_signup_auths.build + end + + def edit + @auth = environment.driven_signup_auths.where(id: params[:id]).first + @auth ||= environment.driven_signup_auths.build + @auth.update_attributes params[:auth] + end + + def destroy + @auth = environment.driven_signup_auths.where(token: params[:token]).first + @auth.destroy if @auth + end + +end diff --git a/plugins/driven_signup/controllers/driven_signup_plugin_admin_controller.rb b/plugins/driven_signup/controllers/driven_signup_plugin_admin_controller.rb new file mode 100644 index 0000000..93fb520 --- /dev/null +++ b/plugins/driven_signup/controllers/driven_signup_plugin_admin_controller.rb @@ -0,0 +1 @@ +DrivenSignupPluginAdminController = DrivenSignupPlugin::AdminController diff --git a/plugins/driven_signup/controllers/public/driven_signup_plugin/account_controller.rb b/plugins/driven_signup/controllers/public/driven_signup_plugin/account_controller.rb new file mode 100644 index 0000000..3d3afca --- /dev/null +++ b/plugins/driven_signup/controllers/public/driven_signup_plugin/account_controller.rb @@ -0,0 +1,33 @@ +class DrivenSignupPlugin::AccountController < PublicController + + def signup + return render_access_denied unless Rails.env.development? or request.post? + return render_access_denied unless self.environment.driven_signup_auths.where(token: params[:token]).first + + session[:driven_signup] = true + session[:base_organization] = params[:base_organization] + session[:find_suborganization] = params[:find_suborganization] + session[:suborganization_members_limit] = params[:suborganization_members_limit] + session[:user_template] = params[:user_template] + + user_attributes = [:login, :email] + user_params = params[:signup].slice *user_attributes + profile_params = params[:signup].except *user_attributes + + if current_user and user_params[:email].squish == current_user.email + current_user.driven_signup_complete + redirect_to session.delete(:after_signup_redirect_to) + else + self.current_user = nil + redirect_to controller: :account, action: :signup, user: user_params, profile_data: profile_params + end + end + + protected + + def default_url_options + # avoid rails' use_relative_controller! + {use_route: '/'} + end + +end diff --git a/plugins/driven_signup/db/migrate/20150625143118_create_driven_signup_plugin_token.rb b/plugins/driven_signup/db/migrate/20150625143118_create_driven_signup_plugin_token.rb new file mode 100644 index 0000000..cd016fe --- /dev/null +++ b/plugins/driven_signup/db/migrate/20150625143118_create_driven_signup_plugin_token.rb @@ -0,0 +1,16 @@ +class CreateDrivenSignupPluginToken < ActiveRecord::Migration + + def change + create_table :driven_signup_plugin_auths do |t| + t.integer :environment_id + t.string :name + t.string :token + + t.timestamps + end + add_index :driven_signup_plugin_auths, :environment_id + add_index :driven_signup_plugin_auths, :token + add_index :driven_signup_plugin_auths, [:environment_id, :token] + end + +end diff --git a/plugins/driven_signup/lib/driven_signup_plugin.rb b/plugins/driven_signup/lib/driven_signup_plugin.rb new file mode 100644 index 0000000..467c8e8 --- /dev/null +++ b/plugins/driven_signup/lib/driven_signup_plugin.rb @@ -0,0 +1,13 @@ +module DrivenSignupPlugin + + extend Noosfero::Plugin::ParentMethods + + def self.plugin_name + _'Driven signup' + end + + def self.plugin_description + _'Allow external websites to manage the signup' + end + +end diff --git a/plugins/driven_signup/lib/driven_signup_plugin/base.rb b/plugins/driven_signup/lib/driven_signup_plugin/base.rb new file mode 100644 index 0000000..715f294 --- /dev/null +++ b/plugins/driven_signup/lib/driven_signup_plugin/base.rb @@ -0,0 +1,3 @@ +class DrivenSignupPlugin::Base < Noosfero::Plugin + +end diff --git a/plugins/driven_signup/lib/ext/environment.rb b/plugins/driven_signup/lib/ext/environment.rb new file mode 100644 index 0000000..205e97e --- /dev/null +++ b/plugins/driven_signup/lib/ext/environment.rb @@ -0,0 +1,7 @@ +require_dependency 'environment' + +class Environment + + has_many :driven_signup_auths, class_name: 'DrivenSignupPlugin::Auth', dependent: :destroy + +end diff --git a/plugins/driven_signup/lib/ext/user.rb b/plugins/driven_signup/lib/ext/user.rb new file mode 100644 index 0000000..f955c58 --- /dev/null +++ b/plugins/driven_signup/lib/ext/user.rb @@ -0,0 +1,46 @@ +require_dependency 'user' + +class User + + after_create :driven_signup_complete + + protected + + def driven_signup_complete + return unless self.session and self.session.delete(:driven_signup) + + base_organization = self.environment.profiles.where(identifier: self.session.delete(:base_organization)).first + return unless base_organization + organization = base_organization + + if self.session.delete :find_suborganization + members_limit = self.session.delete(:suborganization_members_limit).to_i || 50 + suborganizations = self.environment.profiles. + where('identifier <> ?', base_organization.identifier). + where('identifier LIKE ?', "#{base_organization.identifier}%"). + order('identifier ASC') + pp suborganizations + suborganizations.each do |suborganization| + if suborganization.members.count < members_limit + organization = suborganization + break + end + end + end + + if template = self.environment.profiles.where(identifier: self.session.delete(:user_template)).first + self.person.articles.destroy_all + self.person.apply_template template + end + + # directly affiliate + organization.affiliate self.person, Profile::Roles.member(self.environment.id) + + self.person.redirection_after_login = 'custom_url' + self.person.custom_url_redirection = Noosfero::Application.routes.url_for organization.url + self.person.save + + self.session[:after_signup_redirect_to] = organization.url + end + +end diff --git a/plugins/driven_signup/models/driven_signup_plugin/auth.rb b/plugins/driven_signup/models/driven_signup_plugin/auth.rb new file mode 100644 index 0000000..67a7236 --- /dev/null +++ b/plugins/driven_signup/models/driven_signup_plugin/auth.rb @@ -0,0 +1,15 @@ +class DrivenSignupPlugin::Auth < ActiveRecord::Base + + attr_accessible :name, :token + + belongs_to :environment + + validates_presence_of :environment + validates_presence_of :token + validates_uniqueness_of :token, scope: :environment_id + + def token + self[:token] ||= SecureRandom.hex 16 + end + +end diff --git a/plugins/driven_signup/public/javascripts/driven_signup.js b/plugins/driven_signup/public/javascripts/driven_signup.js new file mode 100644 index 0000000..02f7071 --- /dev/null +++ b/plugins/driven_signup/public/javascripts/driven_signup.js @@ -0,0 +1,22 @@ +driven_signup = { + + admin: { + append: function(auth) { + return $('#auth-new').before(auth) + }, + + find: function(token) { + return $('#driven-signup-tokens [data-token='+token+']') + }, + + update: function(token, auth){ + return this.find(token).replaceWith(auth) + }, + + remove: function(token) { + return this.find(token).remove() + }, + }, + +} + diff --git a/plugins/driven_signup/public/stylesheets/driven_signup.scss b/plugins/driven_signup/public/stylesheets/driven_signup.scss new file mode 100644 index 0000000..3ed015c --- /dev/null +++ b/plugins/driven_signup/public/stylesheets/driven_signup.scss @@ -0,0 +1,14 @@ +#driven-signup-tokens { + + &.table { + display: table; + + .row { + display: table-row; + + .cell { + display: table-cell; + } + } + } +} diff --git a/plugins/driven_signup/test/functional/account_controller_test.rb b/plugins/driven_signup/test/functional/account_controller_test.rb new file mode 100644 index 0000000..8b901e9 --- /dev/null +++ b/plugins/driven_signup/test/functional/account_controller_test.rb @@ -0,0 +1,45 @@ +require 'test_helper' + +# Re-raise errors caught by the controller. +class AccountController; def rescue_action(e) raise e end; end + +class AccountControllerTest < ActionController::TestCase + + def setup + @controller = AccountController.new + @request = ActionController::TestRequest.new + @response = ActionController::TestResponse.new + + e = Environment.default + e.enable 'skip_new_user_email_confirmation', true + disable_signup_bot_check e + end + + should 'use the parameters' do + community = create Community, name: 'base', identifier: 'base1' + subcommunity = create Community, name: 'sub', identifier: 'base11' + subcommunity.reload + + # simulate DrivenSignupPlugin::AccountController + session[:driven_signup] = true + session[:base_organization] = community.identifier + session[:find_suborganization] = true + session[:suborganization_members_limit] = 50 + + post :signup, user: {login: 'quire', password: 'quire', password_confirmation: 'quire', name: 'quire', email: 'test@example.com'} + assert_response :redirect + assert_redirected_to subcommunity.url + + user = Profile['quire'] + assert user + assert_includes subcommunity.members, user + end + + private + + def disable_signup_bot_check environment = Environment.default + environment.min_signup_delay = 0 + environment.save! + end + +end diff --git a/plugins/driven_signup/views/driven_signup_plugin/account/signup.html.slim b/plugins/driven_signup/views/driven_signup_plugin/account/signup.html.slim new file mode 100644 index 0000000..e69de29 --- /dev/null +++ b/plugins/driven_signup/views/driven_signup_plugin/account/signup.html.slim diff --git a/plugins/driven_signup/views/driven_signup_plugin/admin/_auth.html.slim b/plugins/driven_signup/views/driven_signup_plugin/admin/_auth.html.slim new file mode 100644 index 0000000..b7b3477 --- /dev/null +++ b/plugins/driven_signup/views/driven_signup_plugin/admin/_auth.html.slim @@ -0,0 +1,10 @@ +div.row + = form_for auth, as: :auth, remote: true, url: {action: :edit, id: auth.id}, + html: {data: {token: auth.token}} do |f| + + span.cell= f.text_field :name, placeholder: _('name this token') + span.cell= f.text_field :token, value: auth.token + span.cell= f.submit nil, class: 'btn btn-default btn-success' + span.cell= link_to _('Remove'), {action: :destroy, token: auth.token}, remote: true, + class: 'btn btn-default btn-danger', confirm: _('Are you sure you want to delete this authorization?') + diff --git a/plugins/driven_signup/views/driven_signup_plugin/admin/destroy.js.erb b/plugins/driven_signup/views/driven_signup_plugin/admin/destroy.js.erb new file mode 100644 index 0000000..d2d4bb0 --- /dev/null +++ b/plugins/driven_signup/views/driven_signup_plugin/admin/destroy.js.erb @@ -0,0 +1,2 @@ +driven_signup.admin.remove(<%=@auth.token.to_json%>) + diff --git a/plugins/driven_signup/views/driven_signup_plugin/admin/edit.js.erb b/plugins/driven_signup/views/driven_signup_plugin/admin/edit.js.erb new file mode 100644 index 0000000..b60198b --- /dev/null +++ b/plugins/driven_signup/views/driven_signup_plugin/admin/edit.js.erb @@ -0,0 +1,2 @@ +driven_signup.admin.update(<%=@auth.token.to_json%>, <%= render('auth', auth: @auth).to_json %>) + diff --git a/plugins/driven_signup/views/driven_signup_plugin/admin/index.html.slim b/plugins/driven_signup/views/driven_signup_plugin/admin/index.html.slim new file mode 100644 index 0000000..eb11dbd --- /dev/null +++ b/plugins/driven_signup/views/driven_signup_plugin/admin/index.html.slim @@ -0,0 +1,11 @@ += content_for :head do + = stylesheet_link_tag 'plugins/driven_signup/stylesheets/driven_signup' + = javascript_include_tag 'plugins/driven_signup/javascripts/driven_signup' + +div#driven-signup-tokens.table + - environment.driven_signup_auths.each do |auth| + = render 'auth', auth: auth + + div.row id="auth-new" + td= link_to _('New'), {action: :new}, remote: true, class: 'btn btn-default fa-add' + diff --git a/plugins/driven_signup/views/driven_signup_plugin/admin/new.js.erb b/plugins/driven_signup/views/driven_signup_plugin/admin/new.js.erb new file mode 100644 index 0000000..0da726e --- /dev/null +++ b/plugins/driven_signup/views/driven_signup_plugin/admin/new.js.erb @@ -0,0 +1,2 @@ +driven_signup.admin.append(<%= render('auth', auth: @auth).to_json %>) + -- libgit2 0.21.2