From 2b8c2464762194d13a3eec19590c9022151b02b2 Mon Sep 17 00:00:00 2001 From: Jake Moshenko Date: Thu, 20 Nov 2014 15:36:39 -0500 Subject: [PATCH] Temporarily put user rename behind a feature flag. Switch queue names back to using the username for namespace while we figure out a real migration strategy. --- config.py | 3 + ...fb36d4be80d_remove_the_namespace_column.py | 30 ++++++++++ ...translate_the_queue_names_to_reference_.py | 59 ------------------- endpoints/api/repositorynotification.py | 2 +- endpoints/api/user.py | 3 +- endpoints/common.py | 2 +- endpoints/notificationhelper.py | 2 +- endpoints/registry.py | 4 +- static/partials/user-admin.html | 6 +- 9 files changed, 44 insertions(+), 67 deletions(-) create mode 100644 data/migrations/versions/2fb36d4be80d_remove_the_namespace_column.py delete mode 100644 data/migrations/versions/2fb36d4be80d_translate_the_queue_names_to_reference_.py diff --git a/config.py b/config.py index ddb6b54f7..de581939e 100644 --- a/config.py +++ b/config.py @@ -160,6 +160,9 @@ class DefaultConfig(object): # Feature Flag: Whether users can be created (by non-super users). FEATURE_USER_CREATION = True + # Feature Flag: Whether users can be renamed + FEATURE_USER_RENAME = False + DISTRIBUTED_STORAGE_CONFIG = { 'local_eu': ['LocalStorage', {'storage_path': 'test/data/registry/eu'}], 'local_us': ['LocalStorage', {'storage_path': 'test/data/registry/us'}], diff --git a/data/migrations/versions/2fb36d4be80d_remove_the_namespace_column.py b/data/migrations/versions/2fb36d4be80d_remove_the_namespace_column.py new file mode 100644 index 000000000..19b9582f3 --- /dev/null +++ b/data/migrations/versions/2fb36d4be80d_remove_the_namespace_column.py @@ -0,0 +1,30 @@ +"""remove the namespace column. + +Revision ID: 2430f55c41d5 +Revises: 17f11e265e13 +Create Date: 2014-09-30 17:31:33.308490 + +""" + +# revision identifiers, used by Alembic. +revision = '2fb36d4be80d' +down_revision = '17f11e265e13' + +from alembic import op +import sqlalchemy as sa + +import re +from app import app + + +NAMESPACE_EXTRACTOR = re.compile(r'^([a-z]+/)([a-z0-9_]+)(/.*$)') + + +def upgrade(tables): + op.create_index('repository_namespace_user_id', 'repository', ['namespace_user_id'], unique=False) + op.drop_column('repository', 'namespace') + + +def downgrade(tables): + op.add_column('repository', sa.Column('namespace', sa.String(length=255))) + op.drop_index('repository_namespace_user_id', table_name='repository') diff --git a/data/migrations/versions/2fb36d4be80d_translate_the_queue_names_to_reference_.py b/data/migrations/versions/2fb36d4be80d_translate_the_queue_names_to_reference_.py deleted file mode 100644 index 5d7e2f672..000000000 --- a/data/migrations/versions/2fb36d4be80d_translate_the_queue_names_to_reference_.py +++ /dev/null @@ -1,59 +0,0 @@ -"""Translate the queue names to reference namespace by id, remove the namespace column. - -Revision ID: 2430f55c41d5 -Revises: 17f11e265e13 -Create Date: 2014-09-30 17:31:33.308490 - -""" - -# revision identifiers, used by Alembic. -revision = '2fb36d4be80d' -down_revision = '17f11e265e13' - -from alembic import op -import sqlalchemy as sa - -import re -from app import app -from data.database import QueueItem, User, db - - -NAMESPACE_EXTRACTOR = re.compile(r'^([a-z]+/)([a-z0-9_]+)(/.*$)') - - -def upgrade(tables): - # Rename the namespace component of the existing queue items to reference user ids - with app.config['DB_TRANSACTION_FACTORY'](db): - for item in QueueItem.select(): - namespace_match = NAMESPACE_EXTRACTOR.match(item.queue_name) - if namespace_match is not None: - namespace_name = namespace_match.group(2) - namespace_user = User.get(User.username == namespace_name) - item.queue_name = '%s%s%s' % (namespace_match.group(1), str(namespace_user.id), - namespace_match.group(3)) - item.save() - else: - raise RuntimeError('Invalid queue name: %s' % item.queue_name) - - op.create_index('repository_namespace_user_id', 'repository', ['namespace_user_id'], unique=False) - op.drop_column('repository', 'namespace') - - -def downgrade(tables): - # Add the namespace column back in and fill it in - op.add_column('repository', sa.Column('namespace', sa.String(length=255))) - op.drop_index('repository_namespace_user_id', table_name='repository') - - # Rename the namespace component of existing queue items to reference namespace strings - with app.config['DB_TRANSACTION_FACTORY'](db): - for item in QueueItem.select(): - namespace_match = NAMESPACE_EXTRACTOR.match(item.queue_name) - if namespace_match is not None: - namespace_id = namespace_match.group(2) - namespace_user = User.get(User.id == namespace_id) - item.queue_name = '%s%s%s' % (namespace_match.group(1), - str(namespace_user.username), - namespace_match.group(3)) - item.save() - else: - raise RuntimeError('Invalid queue name: %s' % item.queue_name) diff --git a/endpoints/api/repositorynotification.py b/endpoints/api/repositorynotification.py index cc9bcb848..d9f84a8bc 100644 --- a/endpoints/api/repositorynotification.py +++ b/endpoints/api/repositorynotification.py @@ -144,7 +144,7 @@ class TestRepositoryNotification(RepositoryParamResource): event_info = NotificationEvent.get_event(notification.event.name) sample_data = event_info.get_sample_data(repository=notification.repository) notification_data = build_notification_data(notification, sample_data) - notification_queue.put([str(notification.repository.namespace_user.id), repository, + notification_queue.put([notification.repository.namespace_user.username, repository, notification.event.name], json.dumps(notification_data)) return {} diff --git a/endpoints/api/user.py b/endpoints/api/user.py index cb0602010..8cad4b30a 100644 --- a/endpoints/api/user.py +++ b/endpoints/api/user.py @@ -198,7 +198,8 @@ class User(ApiResource): else: model.update_email(user, new_email, auto_verify=not features.MAILING) - if 'username' in user_data and user_data['username'] != user.username: + if ('username' in user_data and user_data['username'] != user.username and + features.USER_RENAME): new_username = user_data['username'] if model.get_user_or_org(new_username) is not None: # Username already used diff --git a/endpoints/common.py b/endpoints/common.py index 0251bc06c..7d91137c3 100644 --- a/endpoints/common.py +++ b/endpoints/common.py @@ -238,7 +238,7 @@ def start_build(repository, dockerfile_id, tags, build_name, subdir, manual, dockerfile_id, build_name, trigger, pull_robot_name=pull_robot_name) - dockerfile_build_queue.put([str(repository.namespace_user.id), repository.name], json.dumps({ + dockerfile_build_queue.put([repository.namespace_user.username, repository.name], json.dumps({ 'build_uuid': build_request.uuid, 'pull_credentials': model.get_pull_credentials(pull_robot_name) if pull_robot_name else None }), retries_remaining=1) diff --git a/endpoints/notificationhelper.py b/endpoints/notificationhelper.py index 8ac23e985..0b73513d9 100644 --- a/endpoints/notificationhelper.py +++ b/endpoints/notificationhelper.py @@ -58,5 +58,5 @@ def spawn_notification(repo, event_name, extra_data={}, subpage=None, pathargs=[ event_name=event_name) for notification in list(notifications): notification_data = build_notification_data(notification, event_data, performer_data) - path = [str(repo.namespace_user.id), repo.name, event_name] + pathargs + path = [repo.namespace_user.username, repo.name, event_name] + pathargs notification_queue.put(path, json.dumps(notification_data)) diff --git a/endpoints/registry.py b/endpoints/registry.py index 0f63c7751..9209d1f3a 100644 --- a/endpoints/registry.py +++ b/endpoints/registry.py @@ -259,7 +259,7 @@ def put_image_layer(namespace, repository, image_id): # process it. profile.debug('Adding layer to diff queue') repo = model.get_repository(namespace, repository) - image_diff_queue.put([str(repo.namespace_user.id), repository, image_id], json.dumps({ + image_diff_queue.put([repo.namespace_user.username, repository, image_id], json.dumps({ 'namespace_user_id': repo.namespace_user.id, 'repository': repository, 'image_id': image_id, @@ -333,7 +333,7 @@ def put_image_checksum(namespace, repository, image_id): # process it. profile.debug('Adding layer to diff queue') repo = model.get_repository(namespace, repository) - image_diff_queue.put([str(repo.namespace_user.id), repository, image_id], json.dumps({ + image_diff_queue.put([repo.namespace_user.username, repository, image_id], json.dumps({ 'namespace_user_id': repo.namespace_user.id, 'repository': repository, 'image_id': image_id, diff --git a/static/partials/user-admin.html b/static/partials/user-admin.html index ffe4258f7..d7d9b583e 100644 --- a/static/partials/user-admin.html +++ b/static/partials/user-admin.html @@ -38,7 +38,9 @@
  • Usage Logs
  • -
  • Change Username
  • +
  • + Change Username +
  • Convert to Organization
  • @@ -236,7 +238,7 @@ -
    +
    Change Username