summaryrefslogtreecommitdiff
path: root/ironic/db/sqlalchemy/api.py
diff options
context:
space:
mode:
Diffstat (limited to 'ironic/db/sqlalchemy/api.py')
-rw-r--r--ironic/db/sqlalchemy/api.py44
1 files changed, 28 insertions, 16 deletions
diff --git a/ironic/db/sqlalchemy/api.py b/ironic/db/sqlalchemy/api.py
index 3a74605f8..d01b2359d 100644
--- a/ironic/db/sqlalchemy/api.py
+++ b/ironic/db/sqlalchemy/api.py
@@ -502,23 +502,31 @@ class Connection(api.Connection):
if count != 1:
raise exception.ChassisNotFound(chassis=chassis_id)
- def register_conductor(self, values):
- try:
- conductor = models.Conductor()
- conductor.update(values)
- # NOTE(deva): ensure updated_at field has a non-null initial value
- if not conductor.get('updated_at'):
- conductor.update({'updated_at': timeutils.utcnow()})
- conductor.save()
- return conductor
- except db_exc.DBDuplicateEntry:
- raise exception.ConductorAlreadyRegistered(
- conductor=values['hostname'])
+ def register_conductor(self, values, update_existing=False):
+ session = get_session()
+ with session.begin():
+ query = model_query(models.Conductor, session=session).\
+ filter_by(hostname=values['hostname'])
+ try:
+ ref = query.one()
+ if ref.online is True and not update_existing:
+ raise exception.ConductorAlreadyRegistered(
+ conductor=values['hostname'])
+ except NoResultFound:
+ ref = models.Conductor()
+ ref.update(values)
+ # always set online and updated_at fields when registering
+ # a conductor, especially when updating an existing one
+ ref.update({'updated_at': timeutils.utcnow(),
+ 'online': True})
+ ref.save(session)
+ return ref
def get_conductor(self, hostname):
try:
return model_query(models.Conductor).\
- filter_by(hostname=hostname).\
+ filter_by(hostname=hostname,
+ online=True).\
one()
except NoResultFound:
raise exception.ConductorNotFound(conductor=hostname)
@@ -527,8 +535,9 @@ class Connection(api.Connection):
session = get_session()
with session.begin():
query = model_query(models.Conductor, session=session).\
- filter_by(hostname=hostname)
- count = query.delete()
+ filter_by(hostname=hostname,
+ online=True)
+ count = query.update({'online': False})
if count == 0:
raise exception.ConductorNotFound(conductor=hostname)
@@ -538,7 +547,9 @@ class Connection(api.Connection):
query = model_query(models.Conductor, session=session).\
filter_by(hostname=hostname)
# since we're not changing any other field, manually set updated_at
- count = query.update({'updated_at': timeutils.utcnow()})
+ # and since we're heartbeating, make sure that online=True
+ count = query.update({'updated_at': timeutils.utcnow(),
+ 'online': True})
if count == 0:
raise exception.ConductorNotFound(conductor=hostname)
@@ -548,6 +559,7 @@ class Connection(api.Connection):
limit = timeutils.utcnow() - datetime.timedelta(seconds=interval)
result = model_query(models.Conductor).\
+ filter_by(online=True).\
filter(models.Conductor.updated_at >= limit).\
all()