ansible-collections-openstack/plugins/modules/image.py

242 lines
7.3 KiB
Python

#!/usr/bin/python
# Copyright (c) 2015 Hewlett-Packard Development Company, L.P.
# Copyright (c) 2013, Benno Joy <benno@ansible.com>
# GNU General Public License v3.0+ (see COPYING or https://www.gnu.org/licenses/gpl-3.0.txt)
# TODO(mordred): we need to support "location"(v1) and "locations"(v2)
DOCUMENTATION = '''
---
module: image
short_description: Add/Delete images from OpenStack Cloud
author: OpenStack Ansible SIG
description:
- Add or Remove images from the OpenStack Image Repository
options:
name:
description:
- The name of the image when uploading - or the name/ID of the image if deleting
required: true
type: str
id:
description:
- The ID of the image when uploading an image
type: str
checksum:
description:
- The checksum of the image
type: str
disk_format:
description:
- The format of the disk that is getting uploaded
default: qcow2
choices: ['ami', 'ari', 'aki', 'vhd', 'vmdk', 'raw', 'qcow2', 'vdi', 'iso', 'vhdx', 'ploop']
type: str
container_format:
description:
- The format of the container
default: bare
choices: ['ami', 'aki', 'ari', 'bare', 'ovf', 'ova', 'docker']
type: str
owner:
description:
- The owner of the image
type: str
min_disk:
description:
- The minimum disk space (in GB) required to boot this image
type: int
min_ram:
description:
- The minimum ram (in MB) required to boot this image
type: int
is_public:
description:
- Whether the image can be accessed publicly. Note that publicizing an image requires admin role by default.
type: bool
default: false
protected:
description:
- Prevent image from being deleted
type: bool
default: 'no'
filename:
description:
- The path to the file which has to be uploaded
type: str
ramdisk:
description:
- The name of an existing ramdisk image that will be associated with this image
type: str
kernel:
description:
- The name of an existing kernel image that will be associated with this image
type: str
properties:
description:
- Additional properties to be associated with this image
default: {}
type: dict
state:
description:
- Should the resource be present or absent.
choices: [present, absent]
default: present
type: str
volume:
description:
- ID of a volume to create an image from.
- The volume must be in AVAILABLE state.
type: str
requirements:
- "python >= 3.6"
- "openstacksdk"
extends_documentation_fragment:
- openstack.cloud.openstack
'''
EXAMPLES = '''
# Upload an image from a local file named cirros-0.3.0-x86_64-disk.img
- openstack.cloud.image:
auth:
auth_url: https://identity.example.com
username: admin
password: passme
project_name: admin
openstack.cloud.identity_user_domain_name: Default
openstack.cloud.project_domain_name: Default
name: cirros
container_format: bare
disk_format: qcow2
state: present
filename: cirros-0.3.0-x86_64-disk.img
kernel: cirros-vmlinuz
ramdisk: cirros-initrd
properties:
cpu_arch: x86_64
distro: ubuntu
# Create image from volume attached to an instance
- name: create volume snapshot
openstack.cloud.volume_snapshot:
auth:
"{{ auth }}"
display_name: myvol_snapshot
volume: myvol
force: yes
register: myvol_snapshot
- name: create volume from snapshot
openstack.cloud.volume:
auth:
"{{ auth }}"
size: "{{ myvol_snapshot.snapshot.size }}"
snapshot_id: "{{ myvol_snapshot.snapshot.id }}"
display_name: myvol_snapshot_volume
wait: yes
register: myvol_snapshot_volume
- name: create image from volume snapshot
openstack.cloud.image:
auth:
"{{ auth }}"
volume: "{{ myvol_snapshot_volume.volume.id }}"
name: myvol_image
'''
from ansible_collections.openstack.cloud.plugins.module_utils.openstack import OpenStackModule
class ImageModule(OpenStackModule):
deprecated_names = ('os_image', 'openstack.cloud.os_image')
argument_spec = dict(
name=dict(required=True, type='str'),
id=dict(type='str'),
checksum=dict(type='str'),
disk_format=dict(default='qcow2',
choices=['ami', 'ari', 'aki', 'vhd', 'vmdk', 'raw', 'qcow2', 'vdi', 'iso', 'vhdx', 'ploop']),
container_format=dict(default='bare', choices=['ami', 'aki', 'ari', 'bare', 'ovf', 'ova', 'docker']),
owner=dict(type='str'),
min_disk=dict(type='int', default=0),
min_ram=dict(type='int', default=0),
is_public=dict(type='bool', default=False),
protected=dict(type='bool', default=False),
filename=dict(type='str'),
ramdisk=dict(type='str'),
kernel=dict(type='str'),
properties=dict(type='dict', default={}),
volume=dict(type='str'),
state=dict(default='present', choices=['absent', 'present']),
)
module_kwargs = dict(
mutually_exclusive=[['filename', 'volume']],
)
def run(self):
changed = False
if self.params['id']:
image = self.conn.get_image(name_or_id=self.params['id'])
elif self.params['checksum']:
image = self.conn.get_image(name_or_id=self.params['name'], filters={'checksum': self.params['checksum']})
else:
image = self.conn.get_image(name_or_id=self.params['name'])
if self.params['state'] == 'present':
if not image:
kwargs = {}
if self.params['id'] is not None:
kwargs['id'] = self.params['id']
image = self.conn.create_image(
name=self.params['name'],
filename=self.params['filename'],
disk_format=self.params['disk_format'],
container_format=self.params['container_format'],
wait=self.params['wait'],
timeout=self.params['timeout'],
is_public=self.params['is_public'],
protected=self.params['protected'],
min_disk=self.params['min_disk'],
min_ram=self.params['min_ram'],
volume=self.params['volume'],
**kwargs
)
changed = True
if not self.params['wait']:
self.exit(changed=changed, image=image, id=image.id)
self.conn.update_image_properties(
image=image,
kernel=self.params['kernel'],
ramdisk=self.params['ramdisk'],
protected=self.params['protected'],
**self.params['properties'])
image = self.conn.get_image(name_or_id=image.id)
self.exit(changed=changed, image=image, id=image.id)
elif self.params['state'] == 'absent':
if not image:
changed = False
else:
self.conn.delete_image(
name_or_id=self.params['name'],
wait=self.params['wait'],
timeout=self.params['timeout'])
changed = True
self.exit(changed=changed)
def main():
module = ImageModule()
module()
if __name__ == '__main__':
main()