Merge pull request #2066 from coreos-inc/select-username
Add support for temp usernames and an interstitial to confirm username
This commit is contained in:
commit
233b2be5c2
18 changed files with 388 additions and 24 deletions
|
@ -372,6 +372,22 @@ class User(BaseModel):
|
|||
Namespace = User.alias()
|
||||
|
||||
|
||||
class UserPromptKind(BaseModel):
|
||||
name = CharField(index=True)
|
||||
|
||||
|
||||
class UserPrompt(BaseModel):
|
||||
user = QuayUserField(allows_robots=False, index=True)
|
||||
kind = ForeignKeyField(UserPromptKind)
|
||||
|
||||
class Meta:
|
||||
database = db
|
||||
read_slaves = (read_slave,)
|
||||
indexes = (
|
||||
(('user', 'kind'), True),
|
||||
)
|
||||
|
||||
|
||||
class TeamRole(BaseModel):
|
||||
name = CharField(index=True)
|
||||
|
||||
|
|
|
@ -0,0 +1,47 @@
|
|||
"""Add user prompt support
|
||||
|
||||
Revision ID: 6c7014e84a5e
|
||||
Revises: c156deb8845d
|
||||
Create Date: 2016-10-31 16:26:31.447705
|
||||
|
||||
"""
|
||||
|
||||
# revision identifiers, used by Alembic.
|
||||
revision = '6c7014e84a5e'
|
||||
down_revision = 'c156deb8845d'
|
||||
|
||||
from alembic import op
|
||||
import sqlalchemy as sa
|
||||
|
||||
def upgrade(tables):
|
||||
### commands auto generated by Alembic - please adjust! ###
|
||||
op.create_table('userpromptkind',
|
||||
sa.Column('id', sa.Integer(), nullable=False),
|
||||
sa.Column('name', sa.String(length=255), nullable=False),
|
||||
sa.PrimaryKeyConstraint('id', name=op.f('pk_userpromptkind'))
|
||||
)
|
||||
op.create_index('userpromptkind_name', 'userpromptkind', ['name'], unique=False)
|
||||
op.create_table('userprompt',
|
||||
sa.Column('id', sa.Integer(), nullable=False),
|
||||
sa.Column('user_id', sa.Integer(), nullable=False),
|
||||
sa.Column('kind_id', sa.Integer(), nullable=False),
|
||||
sa.ForeignKeyConstraint(['kind_id'], ['userpromptkind.id'], name=op.f('fk_userprompt_kind_id_userpromptkind')),
|
||||
sa.ForeignKeyConstraint(['user_id'], ['user.id'], name=op.f('fk_userprompt_user_id_user')),
|
||||
sa.PrimaryKeyConstraint('id', name=op.f('pk_userprompt'))
|
||||
)
|
||||
op.create_index('userprompt_kind_id', 'userprompt', ['kind_id'], unique=False)
|
||||
op.create_index('userprompt_user_id', 'userprompt', ['user_id'], unique=False)
|
||||
op.create_index('userprompt_user_id_kind_id', 'userprompt', ['user_id', 'kind_id'], unique=True)
|
||||
### end Alembic commands ###
|
||||
|
||||
op.bulk_insert(tables.userpromptkind,
|
||||
[
|
||||
{'name':'confirm_username'},
|
||||
])
|
||||
|
||||
|
||||
def downgrade(tables):
|
||||
### commands auto generated by Alembic - please adjust! ###
|
||||
op.drop_table('userprompt')
|
||||
op.drop_table('userpromptkind')
|
||||
### end Alembic commands ###
|
|
@ -11,7 +11,8 @@ from data.database import (User, LoginService, FederatedLogin, RepositoryPermiss
|
|||
Team, Repository, TupleSelector, TeamRole, Namespace, Visibility,
|
||||
EmailConfirmation, Role, db_for_update, random_string_generator,
|
||||
UserRegion, ImageStorageLocation, QueueItem, TeamMemberInvite,
|
||||
ServiceKeyApproval, OAuthApplication, RepositoryBuildTrigger)
|
||||
ServiceKeyApproval, OAuthApplication, RepositoryBuildTrigger,
|
||||
UserPromptKind, UserPrompt)
|
||||
from data.model import (DataModelException, InvalidPasswordException, InvalidRobotException,
|
||||
InvalidUsernameException, InvalidEmailAddressException,
|
||||
TooManyLoginAttemptsException, db_transaction,
|
||||
|
@ -102,6 +103,38 @@ def change_password(user, new_password):
|
|||
notification.delete_notifications_by_kind(user, 'password_required')
|
||||
|
||||
|
||||
def has_user_prompts(user):
|
||||
try:
|
||||
UserPrompt.select().where(UserPrompt.user == user).get()
|
||||
return True
|
||||
except UserPrompt.DoesNotExist:
|
||||
return False
|
||||
|
||||
def has_user_prompt(user, prompt_name):
|
||||
prompt_kind = UserPromptKind.get(name=prompt_name)
|
||||
|
||||
try:
|
||||
UserPrompt.get(user=user, kind=prompt_kind)
|
||||
return True
|
||||
except UserPrompt.DoesNotExist:
|
||||
return False
|
||||
|
||||
|
||||
def create_user_prompt(user, prompt_name):
|
||||
prompt_kind = UserPromptKind.get(name=prompt_name)
|
||||
return UserPrompt.create(user=user, kind=prompt_kind)
|
||||
|
||||
|
||||
def remove_user_prompt(user, prompt_name):
|
||||
prompt_kind = UserPromptKind.get(name=prompt_name)
|
||||
UserPrompt.delete().where(UserPrompt.user == user, UserPrompt.kind == prompt_kind).execute()
|
||||
|
||||
|
||||
def get_user_prompts(user):
|
||||
query = UserPrompt.select().where(UserPrompt.user == user).join(UserPromptKind)
|
||||
return [prompt.kind.name for prompt in query]
|
||||
|
||||
|
||||
def change_username(user_id, new_username):
|
||||
(username_valid, username_issue) = validate_username(new_username)
|
||||
if not username_valid:
|
||||
|
@ -121,6 +154,10 @@ def change_username(user_id, new_username):
|
|||
# Rename the user
|
||||
user.username = new_username
|
||||
user.save()
|
||||
|
||||
# Remove any prompts for username.
|
||||
remove_user_prompt(user, 'confirm_username')
|
||||
|
||||
return user
|
||||
|
||||
|
||||
|
@ -305,11 +342,15 @@ def list_entity_robot_permission_teams(entity_name, include_permissions=False):
|
|||
|
||||
|
||||
def create_federated_user(username, email, service_name, service_ident,
|
||||
set_password_notification, metadata={}, email_required=True):
|
||||
set_password_notification, metadata={},
|
||||
email_required=True, confirm_username=False):
|
||||
new_user = create_user_noverify(username, email, email_required=email_required)
|
||||
new_user.verified = True
|
||||
new_user.save()
|
||||
|
||||
if confirm_username:
|
||||
create_user_prompt(new_user, 'confirm_username')
|
||||
|
||||
service = LoginService.get(LoginService.name == service_name)
|
||||
FederatedLogin.create(user=new_user, service=service,
|
||||
service_ident=service_ident,
|
||||
|
|
|
@ -52,7 +52,8 @@ class FederatedUsers(object):
|
|||
db_user = model.user.create_federated_user(valid_username, email, self._federated_service,
|
||||
username,
|
||||
set_password_notification=False,
|
||||
email_required=self._requires_email)
|
||||
email_required=self._requires_email,
|
||||
confirm_username=True)
|
||||
else:
|
||||
# Update the db attributes from the federated service.
|
||||
if email:
|
||||
|
|
Reference in a new issue