Remove the old db implementation.
This commit is contained in:
parent
f14822571d
commit
6102857bd9
171
ironic/db/api.py
171
ironic/db/api.py
@ -1,171 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# Copyright (c) 2011 X.commerce, a business unit of eBay Inc.
|
||||
# Copyright 2010 United States Government as represented by the
|
||||
# Administrator of the National Aeronautics and Space Administration.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
"""Defines interface for DB access.
|
||||
|
||||
The underlying driver is loaded as a :class:`LazyPluggable`.
|
||||
|
||||
Functions in this module are imported into the ironic.db
|
||||
namespace. Call these functions from ironic.db namespace, not
|
||||
the ironic.db.api namespace.
|
||||
|
||||
All functions in this module return objects that implement a dictionary-like
|
||||
interface. Currently, many of these objects are sqlalchemy objects that
|
||||
implement a dictionary interface. However, a future goal is to have all of
|
||||
these objects be simple dictionaries.
|
||||
|
||||
|
||||
**Related Flags**
|
||||
|
||||
:db_backend: string to lookup in the list of LazyPluggable backends.
|
||||
`sqlalchemy` is the only supported backend right now.
|
||||
|
||||
:sql_connection: string specifying the sqlalchemy connection to
|
||||
use, like: `sqlite:///var/lib/ironic/ironic.sqlite`.
|
||||
|
||||
"""
|
||||
|
||||
from oslo.config import cfg
|
||||
|
||||
from ironic.common import utils
|
||||
from ironic.openstack.common.db import api as db_api
|
||||
|
||||
|
||||
_BACKEND_MAPPING = {'sqlalchemy': 'ironic.db.sqlalchemy.api'}
|
||||
|
||||
IMPL = db_api.DBAPI(backend_mapping=_BACKEND_MAPPING)
|
||||
|
||||
|
||||
def bm_node_get_all(context, service_host=None):
|
||||
return IMPL.bm_node_get_all(context,
|
||||
service_host=service_host)
|
||||
|
||||
|
||||
def bm_node_get_associated(context, service_host=None):
|
||||
return IMPL.bm_node_get_associated(context,
|
||||
service_host=service_host)
|
||||
|
||||
|
||||
def bm_node_get_unassociated(context, service_host=None):
|
||||
return IMPL.bm_node_get_unassociated(context,
|
||||
service_host=service_host)
|
||||
|
||||
|
||||
def bm_node_find_free(context, service_host=None,
|
||||
memory_mb=None, cpus=None, local_gb=None):
|
||||
return IMPL.bm_node_find_free(context,
|
||||
service_host=service_host,
|
||||
memory_mb=memory_mb,
|
||||
cpus=cpus,
|
||||
local_gb=local_gb)
|
||||
|
||||
|
||||
def bm_node_get(context, bm_node_id):
|
||||
return IMPL.bm_node_get(context, bm_node_id)
|
||||
|
||||
|
||||
def bm_node_get_by_instance_uuid(context, instance_uuid):
|
||||
return IMPL.bm_node_get_by_instance_uuid(context,
|
||||
instance_uuid)
|
||||
|
||||
|
||||
def bm_node_get_by_node_uuid(context, node_uuid):
|
||||
return IMPL.bm_node_get_by_node_uuid(context, node_uuid)
|
||||
|
||||
|
||||
def bm_node_create(context, values):
|
||||
return IMPL.bm_node_create(context, values)
|
||||
|
||||
|
||||
def bm_node_destroy(context, bm_node_id):
|
||||
return IMPL.bm_node_destroy(context, bm_node_id)
|
||||
|
||||
|
||||
def bm_node_update(context, bm_node_id, values):
|
||||
return IMPL.bm_node_update(context, bm_node_id, values)
|
||||
|
||||
|
||||
def bm_node_associate_and_update(context, node_uuid, values):
|
||||
return IMPL.bm_node_associate_and_update(context, node_uuid, values)
|
||||
|
||||
|
||||
def bm_pxe_ip_create(context, address, server_address):
|
||||
return IMPL.bm_pxe_ip_create(context, address, server_address)
|
||||
|
||||
|
||||
def bm_pxe_ip_create_direct(context, bm_pxe_ip):
|
||||
return IMPL.bm_pxe_ip_create_direct(context, bm_pxe_ip)
|
||||
|
||||
|
||||
def bm_pxe_ip_destroy(context, ip_id):
|
||||
return IMPL.bm_pxe_ip_destroy(context, ip_id)
|
||||
|
||||
|
||||
def bm_pxe_ip_destroy_by_address(context, address):
|
||||
return IMPL.bm_pxe_ip_destroy_by_address(context, address)
|
||||
|
||||
|
||||
def bm_pxe_ip_get_all(context):
|
||||
return IMPL.bm_pxe_ip_get_all(context)
|
||||
|
||||
|
||||
def bm_pxe_ip_get(context, ip_id):
|
||||
return IMPL.bm_pxe_ip_get(context, ip_id)
|
||||
|
||||
|
||||
def bm_pxe_ip_get_by_bm_node_id(context, bm_node_id):
|
||||
return IMPL.bm_pxe_ip_get_by_bm_node_id(context, bm_node_id)
|
||||
|
||||
|
||||
def bm_pxe_ip_associate(context, bm_node_id):
|
||||
return IMPL.bm_pxe_ip_associate(context, bm_node_id)
|
||||
|
||||
|
||||
def bm_pxe_ip_disassociate(context, bm_node_id):
|
||||
return IMPL.bm_pxe_ip_disassociate(context, bm_node_id)
|
||||
|
||||
|
||||
def bm_interface_get(context, if_id):
|
||||
return IMPL.bm_interface_get(context, if_id)
|
||||
|
||||
|
||||
def bm_interface_get_all(context):
|
||||
return IMPL.bm_interface_get_all(context)
|
||||
|
||||
|
||||
def bm_interface_destroy(context, if_id):
|
||||
return IMPL.bm_interface_destroy(context, if_id)
|
||||
|
||||
|
||||
def bm_interface_create(context, bm_node_id, address, datapath_id, port_no):
|
||||
return IMPL.bm_interface_create(context, bm_node_id, address,
|
||||
datapath_id, port_no)
|
||||
|
||||
|
||||
def bm_interface_set_vif_uuid(context, if_id, vif_uuid):
|
||||
return IMPL.bm_interface_set_vif_uuid(context, if_id, vif_uuid)
|
||||
|
||||
|
||||
def bm_interface_get_by_vif_uuid(context, vif_uuid):
|
||||
return IMPL.bm_interface_get_by_vif_uuid(context, vif_uuid)
|
||||
|
||||
|
||||
def bm_interface_get_all_by_bm_node_id(context, bm_node_id):
|
||||
return IMPL.bm_interface_get_all_by_bm_node_id(context, bm_node_id)
|
@ -1,14 +0,0 @@
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
@ -1,418 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# Copyright (c) 2011 X.commerce, a business unit of eBay Inc.
|
||||
# Copyright 2010 United States Government as represented by the
|
||||
# Administrator of the National Aeronautics and Space Administration.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
"""Implementation of SQLAlchemy backend."""
|
||||
|
||||
import sys
|
||||
import uuid
|
||||
|
||||
from sqlalchemy.sql.expression import asc
|
||||
from sqlalchemy.sql.expression import literal_column
|
||||
|
||||
from ironic.common import exception
|
||||
from ironic.openstack.common.db import exception as db_exc
|
||||
from ironic.openstack.common.db.sqlalchemy import session as db_session
|
||||
from ironic.openstack.common import log as logging
|
||||
from ironic.openstack.common import timeutils
|
||||
from ironic.openstack.common import uuidutils
|
||||
from ironic.db.sqlalchemy import models
|
||||
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
get_engine = db_session.get_engine
|
||||
get_session = db_session.get_session
|
||||
|
||||
|
||||
def get_backend():
|
||||
"""The backend is this module itself."""
|
||||
return sys.modules[__name__]
|
||||
|
||||
|
||||
def model_query(context, model, *args, **kwargs):
|
||||
"""Query helper that accounts for context's `read_deleted` field.
|
||||
|
||||
:param context: context to query under
|
||||
:param session: if present, the session to use
|
||||
:param read_deleted: if present, overrides context's read_deleted field.
|
||||
:param base_model: Where model_query is passed a "model" parameter which is
|
||||
not a subclass of IronicBase, we should pass an extra base_model
|
||||
parameter that is a subclass of IronicBase and corresponds to the
|
||||
model parameter.
|
||||
"""
|
||||
session = kwargs.get('session') or get_session()
|
||||
read_deleted = kwargs.get('read_deleted') or context.read_deleted
|
||||
|
||||
def issubclassof_ironic_base(obj):
|
||||
return isinstance(obj, type) and issubclass(obj, models.IronicBase)
|
||||
|
||||
base_model = model
|
||||
if not issubclassof_ironic_base(base_model):
|
||||
base_model = kwargs.get('base_model', None)
|
||||
if not issubclassof_nova_base(base_model):
|
||||
raise Exception(_("model or base_model parameter should be "
|
||||
"subclass of IronicBase"))
|
||||
|
||||
query = session.query(model, *args)
|
||||
|
||||
default_deleted_value = base_model.__mapper__.c.deleted.default.arg
|
||||
if read_deleted == 'no':
|
||||
query = query.filter(base_model.deleted == default_deleted_value)
|
||||
elif read_deleted == 'yes':
|
||||
pass # omit the filter to include deleted and active
|
||||
elif read_deleted == 'only':
|
||||
query = query.filter(base_model.deleted != default_deleted_value)
|
||||
else:
|
||||
raise Exception(_("Unrecognized read_deleted value '%s'")
|
||||
% read_deleted)
|
||||
|
||||
return query
|
||||
|
||||
|
||||
def _build_node_order_by(query):
|
||||
query = query.order_by(asc(models.BareMetalNode.memory_mb))
|
||||
query = query.order_by(asc(models.BareMetalNode.cpus))
|
||||
query = query.order_by(asc(models.BareMetalNode.local_gb))
|
||||
return query
|
||||
|
||||
|
||||
def bm_node_get_all(context, service_host=None):
|
||||
query = model_query(context, models.BareMetalNode, read_deleted="no")
|
||||
if service_host:
|
||||
query = query.filter_by(service_host=service_host)
|
||||
return query.all()
|
||||
|
||||
|
||||
def bm_node_get_associated(context, service_host=None):
|
||||
query = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter(models.BareMetalNode.instance_uuid != None)
|
||||
if service_host:
|
||||
query = query.filter_by(service_host=service_host)
|
||||
return query.all()
|
||||
|
||||
|
||||
def bm_node_get_unassociated(context, service_host=None):
|
||||
query = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter(models.BareMetalNode.instance_uuid == None)
|
||||
if service_host:
|
||||
query = query.filter_by(service_host=service_host)
|
||||
return query.all()
|
||||
|
||||
|
||||
def bm_node_find_free(context, service_host=None,
|
||||
cpus=None, memory_mb=None, local_gb=None):
|
||||
query = model_query(context, models.BareMetalNode, read_deleted="no")
|
||||
query = query.filter(models.BareMetalNode.instance_uuid == None)
|
||||
if service_host:
|
||||
query = query.filter_by(service_host=service_host)
|
||||
if cpus is not None:
|
||||
query = query.filter(models.BareMetalNode.cpus >= cpus)
|
||||
if memory_mb is not None:
|
||||
query = query.filter(models.BareMetalNode.memory_mb >= memory_mb)
|
||||
if local_gb is not None:
|
||||
query = query.filter(models.BareMetalNode.local_gb >= local_gb)
|
||||
query = _build_node_order_by(query)
|
||||
return query.first()
|
||||
|
||||
|
||||
def bm_node_get(context, bm_node_id):
|
||||
# bm_node_id may be passed as a string. Convert to INT to improve DB perf.
|
||||
bm_node_id = int(bm_node_id)
|
||||
result = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter_by(id=bm_node_id).\
|
||||
first()
|
||||
|
||||
if not result:
|
||||
raise exception.NodeNotFound(node_id=bm_node_id)
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_node_get_by_instance_uuid(context, instance_uuid):
|
||||
if not uuidutils.is_uuid_like(instance_uuid):
|
||||
raise exception.InstanceNotFound(instance_id=instance_uuid)
|
||||
|
||||
result = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter_by(instance_uuid=instance_uuid).\
|
||||
first()
|
||||
|
||||
if not result:
|
||||
raise exception.InstanceNotFound(instance_id=instance_uuid)
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_node_get_by_node_uuid(context, bm_node_uuid):
|
||||
result = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter_by(uuid=bm_node_uuid).\
|
||||
first()
|
||||
|
||||
if not result:
|
||||
raise exception.NodeNotFoundByUUID(node_uuid=bm_node_uuid)
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_node_create(context, values):
|
||||
if not values.get('uuid'):
|
||||
values['uuid'] = str(uuid.uuid4())
|
||||
bm_node_ref = models.BareMetalNode()
|
||||
bm_node_ref.update(values)
|
||||
bm_node_ref.save()
|
||||
return bm_node_ref
|
||||
|
||||
|
||||
def bm_node_update(context, bm_node_id, values):
|
||||
rows = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter_by(id=bm_node_id).\
|
||||
update(values)
|
||||
|
||||
if not rows:
|
||||
raise exception.NodeNotFound(node_id=bm_node_id)
|
||||
|
||||
|
||||
def bm_node_associate_and_update(context, node_uuid, values):
|
||||
"""Associate an instance to a node safely
|
||||
|
||||
Associate an instance to a node only if that node is not yet assocated.
|
||||
Allow the caller to set any other fields they require in the same
|
||||
operation. For example, this is used to set the node's task_state to
|
||||
BUILDING at the beginning of driver.spawn().
|
||||
|
||||
"""
|
||||
if 'instance_uuid' not in values:
|
||||
raise exception.NovaException(_(
|
||||
"instance_uuid must be supplied to bm_node_associate_and_update"))
|
||||
|
||||
session = db_session.get_session()
|
||||
with session.begin():
|
||||
query = model_query(context, models.BareMetalNode,
|
||||
session=session, read_deleted="no").\
|
||||
filter_by(uuid=node_uuid)
|
||||
|
||||
count = query.filter_by(instance_uuid=None).\
|
||||
update(values, synchronize_session=False)
|
||||
if count != 1:
|
||||
raise exception.NovaException(_(
|
||||
"Failed to associate instance %(i_uuid)s to baremetal node "
|
||||
"%(n_uuid)s.") % {'i_uuid': values['instance_uuid'],
|
||||
'n_uuid': node_uuid})
|
||||
ref = query.first()
|
||||
return ref
|
||||
|
||||
|
||||
def bm_node_destroy(context, bm_node_id):
|
||||
# First, delete all interfaces belonging to the node.
|
||||
# Delete physically since these have unique columns.
|
||||
session = db_session.get_session()
|
||||
with session.begin():
|
||||
model_query(context, models.BareMetalInterface, read_deleted="no").\
|
||||
filter_by(bm_node_id=bm_node_id).\
|
||||
delete()
|
||||
rows = model_query(context, models.BareMetalNode, read_deleted="no").\
|
||||
filter_by(id=bm_node_id).\
|
||||
update({'deleted': True,
|
||||
'deleted_at': timeutils.utcnow(),
|
||||
'updated_at': literal_column('updated_at')})
|
||||
|
||||
if not rows:
|
||||
raise exception.NodeNotFound(node_id=bm_node_id)
|
||||
|
||||
|
||||
def bm_pxe_ip_get_all(context):
|
||||
query = model_query(context, models.BareMetalPxeIp, read_deleted="no")
|
||||
return query.all()
|
||||
|
||||
|
||||
def bm_pxe_ip_create(context, address, server_address):
|
||||
ref = models.BareMetalPxeIp()
|
||||
ref.address = address
|
||||
ref.server_address = server_address
|
||||
ref.save()
|
||||
return ref
|
||||
|
||||
|
||||
def bm_pxe_ip_create_direct(context, bm_pxe_ip):
|
||||
ref = bm_pxe_ip_create(context,
|
||||
address=bm_pxe_ip['address'],
|
||||
server_address=bm_pxe_ip['server_address'])
|
||||
return ref
|
||||
|
||||
|
||||
def bm_pxe_ip_destroy(context, ip_id):
|
||||
# Delete physically since it has unique columns
|
||||
model_query(context, models.BareMetalPxeIp, read_deleted="no").\
|
||||
filter_by(id=ip_id).\
|
||||
delete()
|
||||
|
||||
|
||||
def bm_pxe_ip_destroy_by_address(context, address):
|
||||
# Delete physically since it has unique columns
|
||||
model_query(context, models.BareMetalPxeIp, read_deleted="no").\
|
||||
filter_by(address=address).\
|
||||
delete()
|
||||
|
||||
|
||||
def bm_pxe_ip_get(context, ip_id):
|
||||
result = model_query(context, models.BareMetalPxeIp, read_deleted="no").\
|
||||
filter_by(id=ip_id).\
|
||||
first()
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_pxe_ip_get_by_bm_node_id(context, bm_node_id):
|
||||
result = model_query(context, models.BareMetalPxeIp, read_deleted="no").\
|
||||
filter_by(bm_node_id=bm_node_id).\
|
||||
first()
|
||||
|
||||
if not result:
|
||||
raise exception.NodeNotFound(node_id=bm_node_id)
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_pxe_ip_associate(context, bm_node_id):
|
||||
session = db_session.get_session()
|
||||
with session.begin():
|
||||
# Check if the node really exists
|
||||
node_ref = model_query(context, models.BareMetalNode,
|
||||
read_deleted="no", session=session).\
|
||||
filter_by(id=bm_node_id).\
|
||||
first()
|
||||
if not node_ref:
|
||||
raise exception.NodeNotFound(node_id=bm_node_id)
|
||||
|
||||
# Check if the node already has a pxe_ip
|
||||
ip_ref = model_query(context, models.BareMetalPxeIp,
|
||||
read_deleted="no", session=session).\
|
||||
filter_by(bm_node_id=bm_node_id).\
|
||||
first()
|
||||
if ip_ref:
|
||||
return ip_ref.id
|
||||
|
||||
# with_lockmode('update') and filter_by(bm_node_id=None) will lock all
|
||||
# records. It may cause a performance problem in high-concurrency
|
||||
# environment.
|
||||
ip_ref = model_query(context, models.BareMetalPxeIp,
|
||||
read_deleted="no", session=session).\
|
||||
filter_by(bm_node_id=None).\
|
||||
with_lockmode('update').\
|
||||
first()
|
||||
|
||||
# this exception is not caught in nova/compute/manager
|
||||
if not ip_ref:
|
||||
raise exception.NovaException(_("No more PXE IPs available"))
|
||||
|
||||
ip_ref.bm_node_id = bm_node_id
|
||||
session.add(ip_ref)
|
||||
return ip_ref.id
|
||||
|
||||
|
||||
def bm_pxe_ip_disassociate(context, bm_node_id):
|
||||
model_query(context, models.BareMetalPxeIp, read_deleted="no").\
|
||||
filter_by(bm_node_id=bm_node_id).\
|
||||
update({'bm_node_id': None})
|
||||
|
||||
|
||||
def bm_interface_get(context, if_id):
|
||||
result = model_query(context, models.BareMetalInterface,
|
||||
read_deleted="no").\
|
||||
filter_by(id=if_id).\
|
||||
first()
|
||||
|
||||
if not result:
|
||||
raise exception.NovaException(_("Baremetal interface %s "
|
||||
"not found") % if_id)
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_interface_get_all(context):
|
||||
query = model_query(context, models.BareMetalInterface,
|
||||
read_deleted="no")
|
||||
return query.all()
|
||||
|
||||
|
||||
def bm_interface_destroy(context, if_id):
|
||||
# Delete physically since it has unique columns
|
||||
model_query(context, models.BareMetalInterface, read_deleted="no").\
|
||||
filter_by(id=if_id).\
|
||||
delete()
|
||||
|
||||
|
||||
def bm_interface_create(context, bm_node_id, address, datapath_id, port_no):
|
||||
ref = models.BareMetalInterface()
|
||||
ref.bm_node_id = bm_node_id
|
||||
ref.address = address
|
||||
ref.datapath_id = datapath_id
|
||||
ref.port_no = port_no
|
||||
ref.save()
|
||||
return ref.id
|
||||
|
||||
|
||||
def bm_interface_set_vif_uuid(context, if_id, vif_uuid):
|
||||
session = db_session.get_session()
|
||||
with session.begin():
|
||||
bm_interface = model_query(context, models.BareMetalInterface,
|
||||
read_deleted="no", session=session).\
|
||||
filter_by(id=if_id).\
|
||||
with_lockmode('update').\
|
||||
first()
|
||||
if not bm_interface:
|
||||
raise exception.NovaException(_("Baremetal interface %s "
|
||||
"not found") % if_id)
|
||||
|
||||
bm_interface.vif_uuid = vif_uuid
|
||||
try:
|
||||
session.add(bm_interface)
|
||||
session.flush()
|
||||
except db_exc.DBError as e:
|
||||
# TODO(deva): clean up when db layer raises DuplicateKeyError
|
||||
if str(e).find('IntegrityError') != -1:
|
||||
raise exception.NovaException(_("Baremetal interface %s "
|
||||
"already in use") % vif_uuid)
|
||||
else:
|
||||
raise e
|
||||
|
||||
|
||||
def bm_interface_get_by_vif_uuid(context, vif_uuid):
|
||||
result = model_query(context, models.BareMetalInterface,
|
||||
read_deleted="no").\
|
||||
filter_by(vif_uuid=vif_uuid).\
|
||||
first()
|
||||
|
||||
if not result:
|
||||
raise exception.NovaException(_("Baremetal virtual interface %s "
|
||||
"not found") % vif_uuid)
|
||||
|
||||
return result
|
||||
|
||||
|
||||
def bm_interface_get_all_by_bm_node_id(context, bm_node_id):
|
||||
result = model_query(context, models.BareMetalInterface,
|
||||
read_deleted="no").\
|
||||
filter_by(bm_node_id=bm_node_id).\
|
||||
all()
|
||||
|
||||
if not result:
|
||||
raise exception.NodeNotFound(node_id=bm_node_id)
|
||||
|
||||
return result
|
@ -1,14 +0,0 @@
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
@ -1,20 +0,0 @@
|
||||
[db_settings]
|
||||
# Used to identify which repository this database is versioned under.
|
||||
# You can use the name of your project.
|
||||
repository_id=nova_bm
|
||||
|
||||
# The name of the database table used to track the schema version.
|
||||
# This name shouldn't already be used by your project.
|
||||
# If this is changed once a database is under version control, you'll need to
|
||||
# change the table name in each database too.
|
||||
version_table=migrate_version
|
||||
|
||||
# When committing a change script, Migrate will attempt to generate the
|
||||
# sql for all supported databases; normally, if one of them fails - probably
|
||||
# because you don't have that database installed - it is ignored and the
|
||||
# commit continues, perhaps ending successfully.
|
||||
# Databases in this list MUST compile successfully during a commit, or the
|
||||
# entire commit will fail. List the databases your application will actually
|
||||
# be using to ensure your updates to that database work properly.
|
||||
# This must be a list; example: ['postgres','sqlite']
|
||||
required_dbs=[]
|
@ -1,119 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
from sqlalchemy import Boolean, Column, DateTime
|
||||
from sqlalchemy import Index, Integer, MetaData, String, Table
|
||||
|
||||
|
||||
def upgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
bm_nodes = Table('bm_nodes', meta,
|
||||
Column('created_at', DateTime),
|
||||
Column('updated_at', DateTime),
|
||||
Column('deleted_at', DateTime),
|
||||
Column('deleted', Boolean),
|
||||
Column('id', Integer, primary_key=True, nullable=False),
|
||||
Column('cpus', Integer),
|
||||
Column('memory_mb', Integer),
|
||||
Column('local_gb', Integer),
|
||||
Column('pm_address', String(length=255)),
|
||||
Column('pm_user', String(length=255)),
|
||||
Column('pm_password', String(length=255)),
|
||||
Column('service_host', String(length=255)),
|
||||
Column('prov_mac_address', String(length=255)),
|
||||
Column('instance_uuid', String(length=36)),
|
||||
Column('registration_status', String(length=16)),
|
||||
Column('task_state', String(length=255)),
|
||||
Column('prov_vlan_id', Integer),
|
||||
Column('terminal_port', Integer),
|
||||
mysql_engine='InnoDB',
|
||||
#mysql_charset='utf8'
|
||||
)
|
||||
|
||||
bm_interfaces = Table('bm_interfaces', meta,
|
||||
Column('created_at', DateTime),
|
||||
Column('updated_at', DateTime),
|
||||
Column('deleted_at', DateTime),
|
||||
Column('deleted', Boolean),
|
||||
Column('id', Integer, primary_key=True, nullable=False),
|
||||
Column('bm_node_id', Integer),
|
||||
Column('address', String(length=255), unique=True),
|
||||
Column('datapath_id', String(length=255)),
|
||||
Column('port_no', Integer),
|
||||
Column('vif_uuid', String(length=36), unique=True),
|
||||
mysql_engine='InnoDB',
|
||||
#mysql_charset='utf8'
|
||||
)
|
||||
|
||||
bm_pxe_ips = Table('bm_pxe_ips', meta,
|
||||
Column('created_at', DateTime),
|
||||
Column('updated_at', DateTime),
|
||||
Column('deleted_at', DateTime),
|
||||
Column('deleted', Boolean),
|
||||
Column('id', Integer, primary_key=True, nullable=False),
|
||||
Column('address', String(length=255), unique=True),
|
||||
Column('bm_node_id', Integer),
|
||||
Column('server_address', String(length=255), unique=True),
|
||||
mysql_engine='InnoDB',
|
||||
#mysql_charset='utf8'
|
||||
)
|
||||
|
||||
bm_deployments = Table('bm_deployments', meta,
|
||||
Column('created_at', DateTime),
|
||||
Column('updated_at', DateTime),
|
||||
Column('deleted_at', DateTime),
|
||||
Column('deleted', Boolean),
|
||||
Column('id', Integer, primary_key=True, nullable=False),
|
||||
Column('bm_node_id', Integer),
|
||||
Column('key', String(length=255)),
|
||||
Column('image_path', String(length=255)),
|
||||
Column('pxe_config_path', String(length=255)),
|
||||
Column('root_mb', Integer),
|
||||
Column('swap_mb', Integer),
|
||||
mysql_engine='InnoDB',
|
||||
#mysql_charset='utf8'
|
||||
)
|
||||
|
||||
bm_nodes.create()
|
||||
bm_interfaces.create()
|
||||
bm_pxe_ips.create()
|
||||
bm_deployments.create()
|
||||
|
||||
Index('idx_bm_nodes_service_host_deleted',
|
||||
bm_nodes.c.service_host, bm_nodes.c.deleted)\
|
||||
.create(migrate_engine)
|
||||
Index('idx_bm_nodes_instance_uuid_deleted',
|
||||
bm_nodes.c.instance_uuid, bm_nodes.c.deleted)\
|
||||
.create(migrate_engine)
|
||||
Index('idx_bm_nodes_hmcld',
|
||||
bm_nodes.c.service_host, bm_nodes.c.memory_mb, bm_nodes.c.cpus,
|
||||
bm_nodes.c.local_gb, bm_nodes.c.deleted)\
|
||||
.create(migrate_engine)
|
||||
|
||||
Index('idx_bm_interfaces_bm_node_id_deleted',
|
||||
bm_interfaces.c.bm_node_id, bm_interfaces.c.deleted)\
|
||||
.create(migrate_engine)
|
||||
|
||||
Index('idx_bm_pxe_ips_bm_node_id_deleted',
|
||||
bm_pxe_ips.c.bm_node_id, bm_pxe_ips.c.deleted)\
|
||||
.create(migrate_engine)
|
||||
|
||||
|
||||
def downgrade(migrate_engine):
|
||||
raise NotImplementedError('Downgrade from 001_init is unsupported.')
|
@ -1,68 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright 2013 Hewlett-Packard Development Company, L.P.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
from sqlalchemy import Column, Index, MetaData, Table
|
||||
from sqlalchemy import Integer, String, DateTime, Boolean
|
||||
|
||||
|
||||
def upgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
bm_nodes = Table('bm_nodes', meta, autoload=True)
|
||||
|
||||
image_path = Column('image_path', String(length=255))
|
||||
pxe_config_path = Column('pxe_config_path', String(length=255))
|
||||
deploy_key = Column('deploy_key', String(length=255))
|
||||
root_mb = Column('root_mb', Integer())
|
||||
swap_mb = Column('swap_mb', Integer())
|
||||
|
||||
for c in [image_path, pxe_config_path, deploy_key, root_mb, swap_mb]:
|
||||
bm_nodes.create_column(c)
|
||||
|
||||
deploy_key_idx = Index('deploy_key_idx', bm_nodes.c.deploy_key)
|
||||
deploy_key_idx.create(migrate_engine)
|
||||
|
||||
bm_deployments = Table('bm_deployments', meta, autoload=True)
|
||||
bm_deployments.drop()
|
||||
|
||||
|
||||
def downgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
bm_nodes = Table('bm_nodes', meta, autoload=True)
|
||||
|
||||
for c in ['image_path', 'pxe_config_path', 'deploy_key', 'root_mb',
|
||||
'swap_mb']:
|
||||
bm_nodes.drop_column(c)
|
||||
|
||||
bm_deployments = Table('bm_deployments', meta,
|
||||
Column('created_at', DateTime),
|
||||
Column('updated_at', DateTime),
|
||||
Column('deleted_at', DateTime),
|
||||
Column('deleted', Boolean),
|
||||
Column('id', Integer, primary_key=True, nullable=False),
|
||||
Column('bm_node_id', Integer),
|
||||
Column('key', String(length=255)),
|
||||
Column('image_path', String(length=255)),
|
||||
Column('pxe_config_path', String(length=255)),
|
||||
Column('root_mb', Integer),
|
||||
Column('swap_mb', Integer),
|
||||
mysql_engine='InnoDB',
|
||||
)
|
||||
bm_deployments.create()
|
@ -1,39 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright 2013 Hewlett-Packard Development Company, L.P.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
from sqlalchemy import Column, MetaData, String, Table, Index
|
||||
|
||||
|
||||
def upgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
t = Table('bm_nodes', meta, autoload=True)
|
||||
uuid_col = Column('uuid', String(36))
|
||||
t.create_column(uuid_col)
|
||||
|
||||
uuid_ux = Index('uuid_ux', t.c.uuid, unique=True)
|
||||
uuid_ux.create(migrate_engine)
|
||||
|
||||
|
||||
def downgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
t = Table('bm_nodes', meta, autoload=True)
|
||||
|
||||
t.drop_column('uuid')
|
@ -1,35 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright 2013 Hewlett-Packard Development Company, L.P.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
from sqlalchemy import Column, MetaData, String, Table
|
||||
|
||||
|
||||
def upgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
t = Table('bm_nodes', meta, autoload=True)
|
||||
name_col = Column('instance_name', String(255))
|
||||
t.create_column(name_col)
|
||||
|
||||
|
||||
def downgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
t = Table('bm_nodes', meta, autoload=True)
|
||||
t.drop_column('instance_name')
|
@ -1,35 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2013 NTT DOCOMO, INC.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
from sqlalchemy import Column, String, Integer, MetaData, Table
|
||||
|
||||
|
||||
def upgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
nodes = Table('bm_nodes', meta, autoload=True)
|
||||
nodes.drop_column('prov_vlan_id')
|
||||
nodes.drop_column('registration_status')
|
||||
|
||||
|
||||
def downgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
nodes = Table('bm_nodes', meta, autoload=True)
|
||||
nodes.create_column(Column('prov_vlan_id', Integer))
|
||||
nodes.create_column(Column('registration_status', String(length=16)))
|
@ -1,84 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2013 NTT DOCOMO, INC.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
from ironic.openstack.common import log as logging
|
||||
from sqlalchemy import and_, MetaData, select, Table, exists
|
||||
from sqlalchemy import exc
|
||||
|
||||
LOG = logging.getLogger(__name__)
|
||||
|
||||
|
||||
def upgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
nodes = Table('bm_nodes', meta, autoload=True)
|
||||
ifs = Table('bm_interfaces', meta, autoload=True)
|
||||
|
||||
q = select([nodes.c.id, nodes.c.prov_mac_address],
|
||||
from_obj=nodes)
|
||||
|
||||
# Iterate all elements before starting insert since IntegrityError
|
||||
# may disturb the iteration.
|
||||
node_address = {}
|
||||
for node_id, address in q.execute():
|
||||
node_address[node_id] = address
|
||||
|
||||
i = ifs.insert()
|
||||
for node_id, address in node_address.iteritems():
|
||||
try:
|
||||
i.execute({'bm_node_id': node_id, 'address': address})
|
||||
except exc.IntegrityError:
|
||||
# The address is registered in both bm_nodes and bm_interfaces.
|
||||
# It is expected.
|
||||
pass
|
||||
|
||||
|
||||
def downgrade(migrate_engine):
|
||||
meta = MetaData()
|
||||
meta.bind = migrate_engine
|
||||
|
||||
nodes = Table('bm_nodes', meta, autoload=True)
|
||||
ifs = Table('bm_interfaces', meta, autoload=True)
|
||||
|
||||
subq = exists().where(and_(ifs.c.bm_node_id == nodes.c.id,
|
||||
ifs.c.address == nodes.c.prov_mac_address))
|
||||
|
||||
ifs.delete().where(subq).execute()
|
||||
|
||||
# NOTE(arata):
|
||||
# In fact, this downgrade may not return the db to the previous state.
|
||||
# It seems to be not so match a problem, so this is just for memo.
|
||||
#
|
||||
# Think these two state before upgrading:
|
||||
#
|
||||
# (A) address 'x' is duplicate
|
||||
# bm_nodes.prov_mac_address='x'
|
||||
# bm_interfaces.address=['x', 'y']
|
||||
#
|
||||
# (B) no address is duplicate
|
||||
# bm_nodes.prov_mac_address='x'
|
||||
# bm_interfaces.address=['y']
|
||||
#
|
||||
# Upgrading them results in the same state:
|
||||
#
|
||||
# bm_nodes.prov_mac_address='x'
|
||||
# bm_interfaces.address=['x', 'y']
|
||||
#
|
||||
# Downgrading this results in B, even if the actual initial status was A
|
||||
# Of course we can change it to downgrade to B, but then we cannot
|
||||
# downgrade to A; it is an exclusive choice since we do not have
|
||||
# information about the initial state.
|
@ -1,14 +0,0 @@
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
@ -1,80 +0,0 @@
|
||||
# vim: tabstop=4 shiftwidth=4 softtabstop=4
|
||||
|
||||
# Copyright (c) 2012 NTT DOCOMO, INC.
|
||||
# All Rights Reserved.
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
|
||||
"""
|
||||
SQLAlchemy models for baremetal data.
|
||||
"""
|
||||
|
||||
from sqlalchemy import Column, Boolean, Integer, String
|
||||
from sqlalchemy.ext.declarative import declarative_base
|
||||
from sqlalchemy import ForeignKey, Text, DateTime, Float
|
||||
|
||||
from ironic.openstack.common.db.sqlalchemy import models
|
||||
|
||||
BASE = declarative_base()
|
||||
|
||||
|
||||
class IronicBase(models.SoftDeleteMixin,
|
||||
models.TimestampMixin,
|
||||
models.ModelBase):
|
||||
metadata = None
|
||||
|
||||
|
||||
class BareMetalNode(BASE, IronicBase):
|
||||
"""Represents a bare metal node."""
|
||||
|
||||
__tablename__ = 'bm_nodes'
|
||||
id = Column(Integer, primary_key=True)
|
||||
deleted = Column(Boolean, default=False)
|
||||
uuid = Column(String(36))
|
||||
service_host = Column(String(255))
|
||||
instance_uuid = Column(String(36), nullable=True)
|
||||
instance_name = Column(String(255), nullable=True)
|
||||
cpus = Column(Integer)
|
||||
memory_mb = Column(Integer)
|
||||
local_gb = Column(Integer)
|
||||
pm_address = Column(Text)
|
||||
pm_user = Column(Text)
|
||||
pm_password = Column(Text)
|
||||
prov_mac_address = Column(Text)
|
||||
task_state = Column(String(255))
|
||||
terminal_port = Column(Integer)
|
||||
image_path = Column(String(255), nullable=True)
|
||||
pxe_config_path = Column(String(255), nullable=True)
|
||||
deploy_key = Column(String(255), nullable=True)
|
||||
root_mb = Column(Integer)
|
||||
swap_mb = Column(Integer)
|
||||
|
||||
|
||||
class BareMetalPxeIp(BASE, IronicBase):
|
||||
__tablename__ = 'bm_pxe_ips'
|
||||
id = Column(Integer, primary_key=True)
|
||||
deleted = Column(Boolean, default=False)
|
||||
address = Column(String(255), unique=True)
|
||||
server_address = Column(String(255), unique=True)
|
||||
bm_node_id = Column(Integer, ForeignKey('bm_nodes.id'), nullable=True)
|
||||
|
||||
|
||||
class BareMetalInterface(BASE, IronicBase):
|
||||
__tablename__ = 'bm_interfaces'
|
||||
id = Column(Integer, primary_key=True)
|
||||
deleted = Column(Boolean, default=False)
|
||||
bm_node_id = Column(Integer, ForeignKey('bm_nodes.id'), nullable=True)
|
||||
address = Column(String(255), unique=True)
|
||||
datapath_id = Column(String(255))
|
||||
port_no = Column(Integer)
|
||||
vif_uuid = Column(String(36), unique=True)
|
Loading…
x
Reference in New Issue
Block a user