Merge pull request #1512 from coreos-inc/optimize-queries
Optimize various queries
This commit is contained in:
commit
614b9124ae
7 changed files with 80 additions and 34 deletions
|
@ -34,26 +34,41 @@ def get_repository_image_and_deriving(docker_image_id, storage_uuid):
|
|||
(Image.id == image_found.id))
|
||||
|
||||
|
||||
def get_parent_images_with_placements(namespace_name, repository_name, image_obj):
|
||||
""" Returns a list of parent Image objects starting with the most recent parent
|
||||
and ending with the base layer. The images in this query will include the storage and
|
||||
placements.
|
||||
"""
|
||||
return _get_parent_images(namespace_name, repository_name, image_obj, include_placements=True)
|
||||
|
||||
|
||||
def get_parent_images(namespace_name, repository_name, image_obj):
|
||||
""" Returns a list of parent Image objects starting with the most recent parent
|
||||
and ending with the base layer.
|
||||
and ending with the base layer. The images in this query will include the storage but
|
||||
not the placements.
|
||||
"""
|
||||
return _get_parent_images(namespace_name, repository_name, image_obj, include_placements=False)
|
||||
|
||||
|
||||
def _get_parent_images(namespace_name, repository_name, image_obj, include_placements=False):
|
||||
parents = image_obj.ancestors
|
||||
|
||||
# Ancestors are in the format /<root>/<intermediate>/.../<parent>/, with each path section
|
||||
# containing the database Id of the image row.
|
||||
parent_db_ids = parents.strip('/').split('/')
|
||||
|
||||
if parent_db_ids == ['']:
|
||||
return []
|
||||
|
||||
def filter_to_parents(query):
|
||||
return query.where(Image.id << parent_db_ids)
|
||||
|
||||
parents = get_repository_images_base(namespace_name, repository_name, filter_to_parents)
|
||||
if include_placements:
|
||||
parents = get_repository_images_base(namespace_name, repository_name, filter_to_parents)
|
||||
else:
|
||||
parents = _get_repository_images_and_storages(namespace_name, repository_name,
|
||||
filter_to_parents)
|
||||
|
||||
id_to_image = {unicode(image.id): image for image in parents}
|
||||
|
||||
return [id_to_image[parent_id] for parent_id in reversed(parent_db_ids)]
|
||||
|
||||
|
||||
|
@ -79,6 +94,19 @@ def get_repo_image_extended(namespace_name, repository_name, docker_image_id):
|
|||
return images[0]
|
||||
|
||||
|
||||
def _get_repository_images_and_storages(namespace_name, repository_name, query_modifier):
|
||||
query = (Image
|
||||
.select(Image, ImageStorage)
|
||||
.join(ImageStorage)
|
||||
.switch(Image)
|
||||
.join(Repository)
|
||||
.join(Namespace, on=(Repository.namespace_user == Namespace.id))
|
||||
.where(Repository.name == repository_name, Namespace.username == namespace_name))
|
||||
|
||||
query = query_modifier(query)
|
||||
return query
|
||||
|
||||
|
||||
def _get_repository_images(namespace_name, repository_name, query_modifier):
|
||||
query = (Image
|
||||
.select()
|
||||
|
@ -134,7 +162,7 @@ def invert_placement_query_results(placement_query):
|
|||
def lookup_repository_images(repo, docker_image_ids):
|
||||
return (Image
|
||||
.select(Image, ImageStorage)
|
||||
.join(ImageStorage) # TODO(jschorr): Remove once no longer needed in v2/manifest.py.
|
||||
.join(ImageStorage)
|
||||
.where(Image.repository == repo, Image.docker_image_id << docker_image_ids))
|
||||
|
||||
|
||||
|
|
|
@ -162,20 +162,40 @@ def garbage_collect_tags(repo):
|
|||
|
||||
logger.debug('Removed %s tags with %s manifests', num_deleted_tags, num_deleted_manifests)
|
||||
|
||||
def get_tag_image(namespace_name, repository_name, tag_name):
|
||||
def limit_to_tag(query):
|
||||
return _tag_alive(query
|
||||
.switch(Image)
|
||||
.join(RepositoryTag)
|
||||
.where(RepositoryTag.name == tag_name))
|
||||
|
||||
images = image.get_repository_images_base(namespace_name, repository_name, limit_to_tag)
|
||||
def _get_repo_tag_image(tag_name, include_storage, modifier):
|
||||
query = Image.select().join(RepositoryTag)
|
||||
|
||||
if include_storage:
|
||||
query = (Image.select(Image, ImageStorage)
|
||||
.join(ImageStorage)
|
||||
.switch(Image)
|
||||
.join(RepositoryTag))
|
||||
|
||||
images = _tag_alive(modifier(query.where(RepositoryTag.name == tag_name)))
|
||||
if not images:
|
||||
raise DataModelException('Unable to find image for tag.')
|
||||
else:
|
||||
return images[0]
|
||||
|
||||
|
||||
def get_repo_tag_image(repo, tag_name, include_storage=False):
|
||||
def modifier(query):
|
||||
return query.where(RepositoryTag.repository == repo)
|
||||
|
||||
return _get_repo_tag_image(tag_name, include_storage, modifier)
|
||||
|
||||
|
||||
def get_tag_image(namespace_name, repository_name, tag_name, include_storage=False):
|
||||
def modifier(query):
|
||||
return (query.switch(RepositoryTag)
|
||||
.join(Repository)
|
||||
.join(Namespace)
|
||||
.where(Namespace.username == namespace_name, Repository.name == repository_name))
|
||||
|
||||
return _get_repo_tag_image(tag_name, include_storage, modifier)
|
||||
|
||||
|
||||
def list_repository_tag_history(repo_obj, page=1, size=100, specific_tag=None):
|
||||
query = (RepositoryTag
|
||||
.select(RepositoryTag, Image)
|
||||
|
@ -226,7 +246,6 @@ def store_tag_manifest(namespace, repo_name, tag_name, docker_image_id, manifest
|
|||
def get_active_tag(namespace, repo_name, tag_name):
|
||||
return _tag_alive(RepositoryTag
|
||||
.select()
|
||||
.join(Image)
|
||||
.join(Repository)
|
||||
.join(Namespace, on=(Repository.namespace_user == Namespace.id))
|
||||
.where(RepositoryTag.name == tag_name, Repository.name == repo_name,
|
||||
|
@ -263,7 +282,6 @@ def _load_repo_manifests(namespace, repo_name):
|
|||
return _tag_alive(TagManifest
|
||||
.select(TagManifest, RepositoryTag)
|
||||
.join(RepositoryTag)
|
||||
.join(Image)
|
||||
.join(Repository)
|
||||
.join(Namespace, on=(Namespace.id == Repository.namespace_user))
|
||||
.where(Repository.name == repo_name, Namespace.username == namespace))
|
||||
|
|
Reference in a new issue