summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLuke "Jared" Bennett <lbennett@gitlab.com>2016-06-08 08:52:10 +0100
committerLuke Bennett <lukeeeebennettplus@gmail.com>2016-08-20 17:07:50 +0100
commit3ac1989c735c1c4c7a0ae9df9b903caaa18b6db3 (patch)
tree0a3d988b2dafaa5b2ead980314fc9079cf39327f
parent6a05f24621646790d1f5bccd0abc003b5386d0f0 (diff)
downloadgitlab-ce-3ac1989c735c1c4c7a0ae9df9b903caaa18b6db3.tar.gz
Added /u/:username/exists endpoint and added input debouncing for request
added error message Renamed file changed error delivery Review fixes
-rw-r--r--app/assets/javascripts/dispatcher.js2
-rw-r--r--app/assets/javascripts/username_validator.es651
-rw-r--r--app/assets/stylesheets/pages/login.scss15
-rw-r--r--app/controllers/users_controller.rb4
-rw-r--r--app/views/devise/shared/_signup_box.html.haml59
-rw-r--r--config/routes.rb1
6 files changed, 103 insertions, 29 deletions
diff --git a/app/assets/javascripts/dispatcher.js b/app/assets/javascripts/dispatcher.js
index ba64d2bcf0b..bf9c865f6eb 100644
--- a/app/assets/javascripts/dispatcher.js
+++ b/app/assets/javascripts/dispatcher.js
@@ -22,6 +22,8 @@
switch (page) {
case 'projects:boards:show':
shortcut_handler = new ShortcutsNavigation();
+ case 'signup':
+ new UsernameValidator();
break;
case 'projects:issues:index':
Issuable.init();
diff --git a/app/assets/javascripts/username_validator.es6 b/app/assets/javascripts/username_validator.es6
new file mode 100644
index 00000000000..67dacb655cc
--- /dev/null
+++ b/app/assets/javascripts/username_validator.es6
@@ -0,0 +1,51 @@
+((global) => {
+ class UsernameValidator {
+ constructor() {
+ this.debounceTimeoutDuration = 1000;
+ this.errorIconClasses = 'fa fa-exclamation-circle error';
+ this.usernameInUseMessage = 'Username "$1" is in use!';
+ this.loadingIconClasses = 'fa fa-spinner fa-spin';
+ this.successIconClasses = 'fa fa-check-circle success';
+ this.tooltipPlacement = 'left';
+
+ this.inputElement = $('#new_user_username');
+ let inputContainer = this.inputElement.parent();
+ inputContainer.append('<i></i>');
+ this.iconElement = $('i', inputContainer);
+
+ let debounceTimeout = _.debounce(this.validateUsername, debounceTimeoutDuration);
+ this.inputElement.keyup(() => this.debounceRequest(debounceTimeout));
+ }
+
+ debounceRequest(debounceTimeout) {
+ this.iconElement.removeClass().tooltip('destroy');
+ let username = this.inputElement.val();
+ if (username === '') return;
+ this.iconElement.addClass(loadingIconClasses);
+ debounceTimeout(username);
+ }
+
+ validateUsername(username) {
+ $.ajax({
+ type: 'GET',
+ url: `/u/${username}/exists`,
+ dataType: 'json',
+ success: () => {
+ this.iconElement
+ .removeClass().addClass(errorIconClasses)
+ .tooltip({
+ title: usernameInUseMessage.replace(/\$1/g, username),
+ placement: tooltipPlacement
+ });
+ },
+ error: () => {
+ this.iconElement
+ .removeClass().addClass(successIconClasses)
+ .tooltip('destroy')
+ }
+ });
+ }
+ }
+
+ global.UsernameValidator = UsernameValidator;
+})(window);
diff --git a/app/assets/stylesheets/pages/login.scss b/app/assets/stylesheets/pages/login.scss
index 403171d4532..042b17b865a 100644
--- a/app/assets/stylesheets/pages/login.scss
+++ b/app/assets/stylesheets/pages/login.scss
@@ -64,6 +64,21 @@
.nav .active a {
background: transparent;
}
+
+ .login-body .new_new_user .username {
+ position: relative;
+ i {
+ position: absolute;
+ right: 8px;
+ top: 12px;
+ &.success {
+ color: $green-normal;
+ }
+ &.error {
+ color: $red-normal;
+ }
+ }
+ }
}
.form-control {
diff --git a/app/controllers/users_controller.rb b/app/controllers/users_controller.rb
index a99632454d9..cfee71e9785 100644
--- a/app/controllers/users_controller.rb
+++ b/app/controllers/users_controller.rb
@@ -85,6 +85,10 @@ class UsersController < ApplicationController
render 'calendar_activities', layout: false
end
+ def exists
+ render json: user.id
+ end
+
private
def authorize_read_user!
diff --git a/app/views/devise/shared/_signup_box.html.haml b/app/views/devise/shared/_signup_box.html.haml
index 905a8dbcd84..5ec914763fe 100644
--- a/app/views/devise/shared/_signup_box.html.haml
+++ b/app/views/devise/shared/_signup_box.html.haml
@@ -1,30 +1,31 @@
-.login-box
- - if signin_enabled?
- .login-heading
- %h3 New user? Create an account
- - else
- .login-heading
- %h3 Create an account
- .login-body
- = form_for(resource, as: "new_#{resource_name}", url: registration_path(resource_name)) do |f|
- .devise-errors
- = devise_error_messages!
- %div
- = f.text_field :name, class: "form-control top", placeholder: "Name", required: true
- %div
- = f.text_field :username, class: "form-control middle", placeholder: "Username", required: true
- %div
- = f.email_field :email, class: "form-control middle", placeholder: "Email", required: true
- .form-group.append-bottom-20#password-strength
- = f.password_field :password, class: "form-control bottom", placeholder: "Password - minimum length #{@minimum_password_length} characters", required: true, pattern: ".{#{@minimum_password_length},}", title: "Minimum length is #{@minimum_password_length} characters"
- %div
- - if current_application_settings.recaptcha_enabled
- = recaptcha_tags
- %div
- = f.submit "Sign up", class: "btn-create btn"
+%body{ data: { page: 'signup' } }
+ .login-box
+ - if signin_enabled?
+ .login-heading
+ %h3 New user? Create an account
+ - else
+ .login-heading
+ %h3 Create an account
+ .login-body
+ = form_for(resource, as: "new_#{resource_name}", url: registration_path(resource_name)) do |f|
+ .devise-errors
+ = devise_error_messages!
+ %div
+ = f.text_field :name, class: "form-control top", placeholder: "Name", required: true
+ %div.username
+ = f.text_field :username, class: "form-control middle", placeholder: "Username", required: true
+ %div
+ = f.email_field :email, class: "form-control middle", placeholder: "Email", required: true
+ .form-group.append-bottom-20#password-strength
+ = f.password_field :password, class: "form-control bottom", placeholder: "Password - minimum length #{@minimum_password_length} characters", required: true, pattern: ".{#{@minimum_password_length},}", title: "Minimum length is #{@minimum_password_length} characters"
+ %div
+ - if current_application_settings.recaptcha_enabled
+ = recaptcha_tags
+ %div
+ = f.submit "Sign up", class: "btn-create btn"
-.clearfix.prepend-top-20
- %p
- %span.light Didn't receive a confirmation email?
- = succeed '.' do
- = link_to "Request a new one", new_confirmation_path(resource_name)
+ .clearfix.prepend-top-20
+ %p
+ %span.light Didn't receive a confirmation email?
+ = succeed '.' do
+ = link_to "Request a new one", new_confirmation_path(resource_name)
diff --git a/config/routes.rb b/config/routes.rb
index e93b640fbc0..fde03dd07c3 100644
--- a/config/routes.rb
+++ b/config/routes.rb
@@ -395,6 +395,7 @@ Rails.application.routes.draw do
get :projects
get :contributed, as: :contributed_projects
get :snippets
+ get :exists
get '/', action: :show
end