Coverage for nova/virt/imagecache.py: 97%
56 statements
« prev ^ index » next coverage.py v7.6.12, created at 2025-04-17 15:08 +0000
« prev ^ index » next coverage.py v7.6.12, created at 2025-04-17 15:08 +0000
1# Copyright 2013 OpenStack Foundation
2# All Rights Reserved.
3#
4# Licensed under the Apache License, Version 2.0 (the "License"); you may
5# not use this file except in compliance with the License. You may obtain
6# a copy of the License at
7#
8# http://www.apache.org/licenses/LICENSE-2.0
9#
10# Unless required by applicable law or agreed to in writing, software
11# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
12# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
13# License for the specific language governing permissions and limitations
14# under the License.
16from nova.compute import task_states
17from nova.compute import vm_states
18import nova.conf
19from nova import objects
20from nova.virt import block_device as driver_block_device
22CONF = nova.conf.CONF
25class ImageCacheManager(object):
26 """Base class for the image cache manager.
28 This class will provide a generic interface to the image cache manager.
29 """
31 def __init__(self):
32 self.remove_unused_base_images = (
33 CONF.image_cache.remove_unused_base_images)
34 self.resize_states = [task_states.RESIZE_PREP,
35 task_states.RESIZE_MIGRATING,
36 task_states.RESIZE_MIGRATED,
37 task_states.RESIZE_FINISH]
39 def _get_base(self):
40 """Returns the base directory of the cached images."""
41 raise NotImplementedError()
43 def _list_running_instances(self, context, all_instances):
44 """List running instances (on all compute nodes).
46 This method returns a dictionary with the following keys:
47 - used_images
48 - instance_names
49 - used_swap_images
50 - used_ephemeral_images
51 """
52 used_images = {}
53 instance_names = set()
54 used_swap_images = set()
55 used_ephemeral_images = set()
56 instance_bdms = objects.BlockDeviceMappingList.bdms_by_instance_uuid(
57 context, [instance.uuid for instance in all_instances])
59 for instance in all_instances:
60 # NOTE(mikal): "instance name" here means "the name of a directory
61 # which might contain an instance" and therefore needs to include
62 # historical permutations as well as the current one.
63 instance_names.add(instance.name)
64 instance_names.add(instance.uuid)
65 if (instance.task_state in self.resize_states or
66 instance.vm_state == vm_states.RESIZED):
67 instance_names.add(instance.name + '_resize')
68 instance_names.add(instance.uuid + '_resize')
70 for image_key in ['image_ref', 'kernel_id', 'ramdisk_id']:
71 image_ref_str = getattr(instance, image_key)
72 if image_ref_str is None:
73 continue
74 local, remote, insts = used_images.get(image_ref_str,
75 (0, 0, []))
76 if instance.host == CONF.host:
77 local += 1
78 else:
79 remote += 1
80 insts.append(instance.name)
81 used_images[image_ref_str] = (local, remote, insts)
83 bdms = instance_bdms.get(instance.uuid)
84 if bdms:
85 swap = driver_block_device.convert_swap(bdms)
86 if swap: 86 ↛ 89line 86 didn't jump to line 89 because the condition on line 86 was always true
87 swap_image = 'swap_' + str(swap[0]['swap_size'])
88 used_swap_images.add(swap_image)
89 ephemeral = driver_block_device.convert_ephemerals(bdms)
90 if ephemeral:
91 os_type = nova.privsep.fs.get_fs_type_for_os_type(
92 instance.os_type)
93 file_name = nova.privsep.fs.get_file_extension_for_os_type(
94 os_type, CONF.default_ephemeral_format)
95 ephemeral_gb = str(ephemeral[0]['size'])
96 ephemeral_image = "ephemeral_%s_%s" % (
97 ephemeral_gb, file_name)
98 used_ephemeral_images.add(ephemeral_image)
100 return {'used_images': used_images,
101 'instance_names': instance_names,
102 'used_swap_images': used_swap_images,
103 'used_ephemeral_images': used_ephemeral_images}
105 def _scan_base_images(self, base_dir):
106 """Scan base images present in base_dir and populate internal
107 state.
108 """
109 raise NotImplementedError()
111 def _age_and_verify_cached_images(self, context, all_instances, base_dir):
112 """Ages and verifies cached images."""
114 raise NotImplementedError()
116 def update(self, context, all_instances):
117 """The cache manager.
119 This will invoke the cache manager. This will update the cache
120 according to the defined cache management scheme. The information
121 populated in the cached stats will be used for the cache management.
122 """
123 raise NotImplementedError()
125 def get_disk_usage(self):
126 """Return the size of the physical disk space used for the cache.
128 :returns: The disk space in bytes that is occupied from
129 CONF.instances_path or zero if the cache directory is mounted
130 to a different disk device.
131 """
132 raise NotImplementedError()