From 7fadc012939faf063bbe9ad3a2f35067ce16a4b2 Mon Sep 17 00:00:00 2001 From: David Ripton Date: Wed, 5 Jun 2013 15:14:31 -0400 Subject: Use an inner join on aggregate_hosts in aggregate_get_by_host Fixes bug 1187708 By default, sqlalchemy.orm.joinedload does a left outer join. But in aggregate_get_by_host, we only want to get aggregates rows with aggregate_hosts rows that match the host, and a left outer join also gave us aggregates rows with no matching aggregate_hosts row. Also improve test_aggregate_get_by_host to catch this bug. Change-Id: Ida9647af02ab58229abe3c50dc3d2c7ec9792a5e --- nova/db/sqlalchemy/api.py | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-) (limited to 'nova/db') diff --git a/nova/db/sqlalchemy/api.py b/nova/db/sqlalchemy/api.py index adacc6ead..094b73fa0 100644 --- a/nova/db/sqlalchemy/api.py +++ b/nova/db/sqlalchemy/api.py @@ -4614,12 +4614,19 @@ def aggregate_get(context, aggregate_id): @require_admin_context def aggregate_get_by_host(context, host, key=None): - query = _aggregate_get_query(context, models.Aggregate, - models.AggregateHost.host, host) + """Return rows that match host (mandatory) and metadata key (optional). + + :param host matches host, and is required. + :param key Matches metadata key, if not None. + """ + query = model_query(context, models.Aggregate) + query = query.options(joinedload('_hosts', innerjoin=True)) + query = query.options(joinedload('_metadata')) + query = query.filter(models.AggregateHost.host == host) if key: query = query.join("_metadata").filter( - models.AggregateMetadata.key == key) + models.AggregateMetadata.key == key) return query.all() -- cgit