Changed for lxc-host setup/build for multi-distro

This change updates the lxc-host setup role to build the lxc cache using the
download template based on default images found here:[0]. These images are
upsteam builds from the greater LXC/D community.

This update adds support for Ubuntu 14.04, 16.04 and RHEL/CentOS 7 container
types and the cache will be generated from the host Operating system.

[0] - https://images.linuxcontainers.org/

Change-Id: Ie13be2322d28178760481c59805101d6aeef4f36
Co-Authored-By: Jesse Pretorius <jesse.pretorius@rackspace.co.uk>
Signed-off-by: Kevin Carter <kevin.carter@rackspace.com>
This commit is contained in:
Kevin Carter 2016-04-18 22:20:07 -05:00
parent ac3e8d95ce
commit f5542103b3
No known key found for this signature in database
GPG Key ID: 69FEFFC5E2D9273F
28 changed files with 884 additions and 256 deletions

View File

@ -15,7 +15,7 @@
# lxc container rootfs directory and cache path
lxc_container_directory: "/var/lib/lxc"
lxc_container_cache_path: "/var/cache/lxc"
lxc_container_cache_path: "/var/cache/lxc/download"
# lxc container net network
lxc_net_bridge: lxcbr0
@ -44,16 +44,6 @@ lxc_container_net_name: eth0 ## name of the interface inside the container.
lxc_kernel_options:
- { key: 'fs.inotify.max_user_instances', value: 1024 }
# Default image to build from
lxc_container_user_password: "{{ lookup('pipe', 'date --rfc-3339=ns | sha512sum | base64 | head -c 32') }}"
lxc_container_template_options: >
--release {{ lxc_container_release }}
--user {{ lxc_container_user_name }}
--password {{ lxc_container_user_password }}
# Set this boolean value to remove any previously prepared base image
lxc_container_base_delete: no
lxc_pip_packages:
- lxc-python2
@ -68,16 +58,8 @@ lxc_cache_sshd_configuration:
- { regexp: "^X11Forwarding", line: "X11Forwarding no" }
- { regexp: "^PasswordAuthentication", line: "PasswordAuthentication no" }
# Validate Certificates when downloading lxc_container_caches.
# May be set to "no" when proxy server is intercepting the certificates.
lxc_cache_validate_certs: "yes"
# Prebuilt images to deploy onto hosts for use in containers.
# lxc_container_caches:
# - url: "https://rpc-repo.rackspace.com/container_images/rpc-trusty-container.tgz"
# name: "trusty.tgz"
# sha256sum: "56c6a6e132ea7d10be2f3e8104f47136ccf408b30e362133f0dc4a0a9adb4d0c"
# chroot_path: trusty/rootfs-amd64
# The compression ratio used when creating the container cache rootfs archive
lxc_image_compression_ratio: 0
# A list of files may be copied into the container image cache during its preparation.
# Example:
@ -85,3 +67,22 @@ lxc_cache_validate_certs: "yes"
# - src: "/etc/openstack_deploy/files/etc/issue"
# dest: "/etc/issue"
lxc_container_cache_files: []
lxc_image_cache_server: images.linuxcontainers.org
## Default download template options
## This can be customized to use a local build server and options.
## By default these options will be fulfilled by the distro specific
## variable files found in vars/
# lxc_cache_download_template_options: >
# --dist NAME_OF_DISTRO
# --release DISTRO_RELEASE
# --arch CONTAINER_ARCH
# --force-cache
# --server SERVER_TO_GET_IMAGES_FROM
lxc_cache_download_template_options: >
--dist {{ lxc_cache_map.distro }}
--release {{ lxc_cache_map.release }}
--arch {{ lxc_cache_map.arch }}
--force-cache
--server {{ lxc_image_cache_server }}

44
files/lxc-veth-check.sh Normal file
View File

@ -0,0 +1,44 @@
#!/usr/bin/env bash
# This is a very simple script to search a host for containers that have veth pairs that are not
# plugged into a given bridge. This can happen for a number of reasons however the most common
# one is due to a physical network interface being bounced which severs the containers connection
# to that interface. This script will identify container veth pairs. If any of the container veth
# devices are missing a master the script will attempt to locate the containers network information
# and connect the broken network link.
# Do a simple lxc command check, if the client errors assume its not installed or ready and return 0
lxc-ls --version || exit 0
# Set the default script exit status
exit_status=0
# List all containers
for container in $(lxc-ls); do
# List Links for the containers
for net_info in $(lxc-info -n "${container}" | awk '/Link/ {print $2}'); do
# If the link information is a veth and does not have a "master" continue
if ! ip -o -d link show "${net_info}" | grep veth | grep -q master; then
# Search for the interface file that contains the veth
lxc_interface_file=$(grep -l "${net_info}" /var/lib/lxc/${container}/{config,*.ini} | head -n 1)
# If an interface file is found continue
if [ ! -z "${lxc_interface_file}" ];then
# Get the first network link line from the lxc configuration file
veth_bridge_line=$(grep -hA10 ${net_info} "${lxc_interface_file}" | grep lxc.network.link | head -n 1)
# If a network interface file has a link entry continue
if [ ! -z "${veth_bridge_line}" ];then
# get the link name
veth_bridge=$(echo "${veth_bridge_line}" | awk -F'=' '{print $2}' | sed 's/\s//g')
# Plug the veth into the link
ip link set "${net_info}" master "${veth_bridge}"
echo "container ${container} had a broken veth ${net_info} not being plugged into "${veth_bridge}": this issue is now resolved"
else
# Notify the user that the issues can not be automatically fixed for a given container and veth
echo "container ${container} has a broken veth ${net_info} and an automated fix can not be found"
# Because of the inability to resolve the issue automatically set the exit_status to failure
exit_status=99
fi
fi
fi
done
done
exit "$exit_status"

View File

@ -31,5 +31,23 @@
pattern: "irqbalance"
enabled: "yes"
- name: Restart bridge
shell: "ifdown {{ lxc_net_bridge }} || true"
notify:
- Bring bridge up
- Veth check
- name: Bring bridge up
command: "ifup {{ lxc_net_bridge }}"
- name: Veth check
command: "/usr/local/bin/lxc-veth-check"
- name: Destroy base container
lxc_container:
name: "cache-{{ lxc_cache_map.distro }}"
state: absent
register: cache_destroy
retries: 3
delay: 10
until: cache_destroy|success

22
manual-test.rc Normal file
View File

@ -0,0 +1,22 @@
export VIRTUAL_ENV=$(pwd)
export ANSIBLE_HOST_KEY_CHECKING=False
export ANSIBLE_SSH_CONTROL_PATH=/tmp/%%h-%%r
# TODO (odyssey4me) These are only here as they are non-standard folder
# names for Ansible 1.9.x. We are using the standard folder names for
# Ansible v2.x. We can remove this when we move to Ansible 2.x.
export ANSIBLE_ACTION_PLUGINS=${HOME}/.ansible/plugins/action
export ANSIBLE_CALLBACK_PLUGINS=${HOME}/.ansible/plugins/callback
export ANSIBLE_FILTER_PLUGINS=${HOME}/.ansible/plugins/filter
export ANSIBLE_LOOKUP_PLUGINS=${HOME}/.ansible/plugins/lookup
# This is required as the default is the current path or a path specified
# in ansible.cfg
export ANSIBLE_LIBRARY=${HOME}/.ansible/plugins/library
# This is required as the default is '/etc/ansible/roles' or a path
# specified in ansible.cfg
export ANSIBLE_ROLES_PATH=${HOME}/.ansible/roles:$(pwd)/..
echo "Run manual functional tests by executing the following:"
echo "# ./.tox/functional/bin/ansible-playbook -i tests/inventory tests/test.yml -e \"rolename=$(pwd)\""

View File

@ -18,11 +18,15 @@ galaxy_info:
description: Deployment of LXC hosts for use in Rackspace Private Cloud
company: Rackspace
license: Apache2
min_ansible_version: 1.6.6
min_ansible_version: 1.9.4
platforms:
- name: Ubuntu
versions:
- trusty
- xenial
- name: EL
versions:
- 7
categories:
- cloud
- lxc

View File

@ -14,7 +14,13 @@
# TODO(odyssey4me) remove this once https://review.openstack.org/288634 has merged
# and the disk images are rebuilt and redeployed.
curl
wget
# Requirements for Paramiko 2.0
libssl-dev
libffi-dev
libssl-dev [platform:dpkg]
libffi-dev [platform:dpkg]
libffi-devel [platform:rpm]
openssl-devel [platform:rpm]
# For selinux
libselinux-python [platform:rpm]

View File

@ -0,0 +1,29 @@
---
features:
- The ``lxc_host`` cache prep has been updated to use the LXC download
template. This removes the last remaining dependency the project has on
the `rpc-trusty-container.tgz image <http://rpc-repo.rackspace.com/container_images/rpc-trusty-container.tgz>`_.
- The ``lxc_host`` role will build lxc cache using the download
template built from `images found here <https://images.linuxcontainers.org>`_.
These images are upstream builds from the greater LXC/D community.
- The ``lxc_host`` role introduces support for CentOS 7 and Ubuntu 16.04
container types.
upgrade:
- The ``lxc_host`` role no longer uses the distro specific lxc container
create template.
- |
The following variable changes have been made in the ``lxc_host`` role:
* **lxc_container_user_password**: Removed because the default lxc
container user is no longer created by the lxc container template.
* **lxc_container_template_options**: This option was renamed to
*lxc_cache_download_template_options*. The deprecation filter was not
used because the values provided from this option have been
fundamentally changed and potentially old overrides will cause
problems.
* **lxc_container_base_delete**: Removed because the cache will be
refreshed upon role execution.
* **lxc_cache_validate_certs**: Removed because the Ansible ``get_url``
module is no longer used.
* **lxc_container_caches**: Removed because the container create process
will build a cached image based on the host OS.

View File

@ -19,7 +19,11 @@ FUNCTIONAL_TEST=${FUNCTIONAL_TEST:-true}
# prep the host
if [ "$(which apt-get)" ]; then
apt-get install -y build-essential python2.7 python-dev git-core libssl-dev libffi-dev
apt-get update && apt-get install -y build-essential python2.7 python-dev git-core libffi-dev libssl-dev
fi
if [ "$(which yum)" ]; then
yum install -y '@Development Tools' python-devel git libffi-devel openssl-devel
fi
# get pip, if necessary
@ -33,9 +37,9 @@ pip install tox
# run through each tox env and execute the test
for tox_env in $(awk -F= '/envlist/ {print $2}' tox.ini | sed 's/,/ /g'); do
if [ "${tox_env}" != "ansible-functional" ]; then
if [ "${tox_env}" != "functional" ]; then
tox -e ${tox_env}
elif [ "${tox_env}" == "ansible-functional" ]; then
elif [ "${tox_env}" == "functional" ]; then
if ${FUNCTIONAL_TEST}; then
tox -e ${tox_env}
fi

View File

@ -13,57 +13,20 @@
# See the License for the specific language governing permissions and
# limitations under the License.
# TODO(odyssey4me)
# Ansible 1.9x only actually checks whether there's a local file - it never
# checks whether the local file matches the given sha256sum. Ansible 2.x
# fixes this, so once we move to Ansible 2.x we can pass this a sha256sum
# which will:
# a) allow us to remove force: yes
# b) allow the module to calculate the checksum of dest file which would
# result in file being downloaded only if provided and dest sha256sum
# checksums differ
# Currently 'force:yes' will always download the file, then do a sha256sum
# comparison between the downloaded file and the existing file, then replace
# the existing file if it doesn't match.
- name: Download lxc cache(s)
get_url:
url: "{{ item.url }}"
dest: "/var/cache/lxc_{{ item.name }}"
mode: "0644"
force: yes
sha256sum: "{{ item.sha256sum }}"
validate_certs: "{{ lxc_cache_validate_certs }}"
- name: Create container
lxc_container:
name: "cache-{{ lxc_cache_map.distro }}"
template: "download"
state: stopped
backing_store: "dir"
template_options: "{{ lxc_cache_download_template_options }}"
register: cache_download
retries: 3
delay: 10
until: cache_download | success
with_items: lxc_container_caches
until: cache_download|success
tags:
- lxc-cache
- lxc-cache-download
- name: Remove existing lxc cached images
file:
path: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}"
state: absent
with_items: lxc_container_caches
when: >
cache_download | changed or
lxc_container_base_delete | bool
tags:
- lxc-cache
- lxc-cache-existing-remove
- name: Move lxc cached image into place
unarchive:
src: "/var/cache/lxc_{{ item.name }}"
dest: "{{ lxc_container_cache_path }}/"
copy: "no"
with_items: lxc_container_caches
when: >
cache_download | changed or
lxc_container_base_delete | bool
tags:
- lxc-cache
- lxc-cache-unarchive
- include: lxc_cache_preparation.yml
- include: lxc_cache_create.yml

View File

@ -0,0 +1,36 @@
---
# Copyright 2016, Rackspace US, 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.
- name: Create lxc image
shell: |
rm {{ lxc_container_cache_path }}/{{ lxc_cache_map.distro }}/{{ lxc_cache_map.release }}/{{ lxc_cache_map.arch }}/default/rootfs.tar.xz
tar -Opc -C /var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs . | xz -{{ lxc_image_compression_ratio }} -c - > rootfs.tar.xz
args:
chdir: "{{ lxc_container_cache_path }}/{{ lxc_cache_map.distro }}/{{ lxc_cache_map.release }}/{{ lxc_cache_map.arch }}/default/"
notify: Destroy base container
tags:
- lxc-cache
- lxc-image-cache-create
# TODO(cloudnull) This should be removed just as soon as the lxc-container create
# play supports using the download template instead of the distro specific one.
- name: Create LEGACY LXC container cache
shell: |
mkdir -p /var/cache/lxc/{{ lxc_cache_map.release }}
cp -R /var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs /var/cache/lxc/{{ lxc_cache_map.release }}/rootfs-amd64
notify: Destroy base container
tags:
- lxc-cache
- lxc-legacy-image-cache-create

View File

@ -15,89 +15,93 @@
- name: Copy files from deployment host to the container cache
copy:
src: "{{ item[1].src }}"
dest: "{{ lxc_container_cache_path }}/{{ item[0].chroot_path }}/{{ item[1].dest }}"
owner: "{{ item[1].owner | default('root') }}"
group: "{{ item[1].group | default('root') }}"
mode: "{{ item[1].mode | default('644') }}"
with_nested:
- lxc_container_caches
- lxc_container_cache_files
src: "{{ item.src }}"
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs{{ item.dest }}"
owner: "{{ item.owner | default('root') }}"
group: "{{ item.group | default('root') }}"
mode: "{{ item.mode | default('644') }}"
with_items: lxc_container_cache_files
tags:
- lxc-cache
- lxc-cache-copy-files
- name: Create apt repos in the cached container
template:
src: sources.list.j2
dest: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}/etc/apt/sources.list"
with_items: lxc_container_caches
tags:
- lxc-cache
- lxc-cache-update
- name: Update container resolvers
template:
src: lxc-resolve-base.j2
dest: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}/run/resolvconf/resolv.conf"
with_items: lxc_container_caches
tags:
- lxc-cache
- lxc-cache-update
- name: Update container resolvconf base
template:
src: lxc-resolve-base.j2
dest: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}/etc/resolvconf/resolv.conf.d/base"
with_items: lxc_container_caches
tags:
- lxc-cache
- lxc-cache-update
- name: Update container resolvconf tail
- name: Cached image preparation script
copy:
content: "# Null Tail"
dest: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}/etc/resolvconf/resolv.conf.d/tail"
with_items: lxc_container_caches
tags:
- lxc-cache
- lxc-cache-update
- name: Update container resolvconf original
copy:
content: "# Null original"
dest: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}/etc/resolvconf/resolv.conf.d/original"
with_items: lxc_container_caches
content: |
#!/usr/bin/env bash
set -x
{{ lxc_cache_map.cache_base_commands }}
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs/usr/local/bin/cache-prep-commands.sh"
mode: "0755"
tags:
- lxc-cache
- lxc-cache-update
# This task runs several commands against the cached image to speed up the
# lxc_container_create playbook.
- name: Prepare cached image
command: "chroot {{ lxc_container_cache_path }}/{{ item[0].chroot_path }} {{ item[1] }}"
with_nested:
- lxc_container_caches
- lxc_cache_commands
when: cache_download|changed
- name: Prepare cached image setup commands
command: "chroot /var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs /usr/local/bin/cache-prep-commands.sh"
tags:
- lxc-cache
- lxc-cache-update
- name: Create repos in the cached container
copy:
content: "{{ item.value }}"
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs{{ item.key }}"
with_dict: lxc_cache_map.repos
tags:
- lxc-cache
- lxc-cache-update
- name: Copy cached image preparation package script into the target
copy:
content: |
#!/usr/bin/env bash
set -x
{{ lxc_cache_install_command }} {{ lxc_cache_map.cache_packages | join(' ') }}
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs/usr/local/bin/cache-package-prep-commands.sh"
mode: "0755"
tags:
- lxc-cache
- lxc-cache-update
- name: Prepare cached image with packages
command: "chroot /var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs /usr/local/bin/cache-package-prep-commands.sh"
tags:
- lxc-cache
- lxc-cache-update
- name: Cached image post-preparation package script
copy:
content: |
#!/usr/bin/env bash
set -x
{{ lxc_cache_map.cache_post_commands }}
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs/usr/local/bin/cache-post-prep-commands.sh"
mode: "0755"
tags:
- lxc-cache
- lxc-cache-update
- name: Post-prepare cached image setup commands
command: "chroot /var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs /usr/local/bin/cache-post-prep-commands.sh"
tags:
- lxc-cache
- lxc-cache-update
- name: Adjust sshd configuration in container
lineinfile:
dest: "{{ lxc_container_cache_path }}/{{ item[0].chroot_path }}/etc/ssh/sshd_config"
regexp: "{{ item[1].regexp }}"
line: "{{ item[1].line }}"
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs/etc/ssh/sshd_config"
regexp: "{{ item.regexp }}"
line: "{{ item.line }}"
state: present
with_nested:
- lxc_container_caches
- lxc_cache_sshd_configuration
with_items: lxc_cache_sshd_configuration
tags:
- lxc-cache
- lxc-cache-update
- name: Obtain the system's ssh public key
- name: Obtain the deploy system's ssh public key
set_fact:
lxc_container_ssh_key: "{{ lookup('file', '/root/.ssh/id_rsa.pub') }}"
when: lxc_container_ssh_key is not defined
@ -107,9 +111,9 @@
- name: Deploy ssh public key into the cached image
lineinfile:
dest: "{{ lxc_container_cache_path }}/{{ item.chroot_path }}/root/.ssh/authorized_keys"
dest: "/var/lib/lxc/cache-{{ lxc_cache_map.distro }}/rootfs/root/.ssh/authorized_keys"
line: "{{ lxc_container_ssh_key }}"
with_items: lxc_container_caches
create: true
tags:
- lxc-cache
- lxc-cache-update

View File

@ -19,6 +19,12 @@
tags:
- install-apt
- include: lxc_install_yum.yml
when:
- ansible_pkg_mgr == 'yum'
tags:
- install-yum
- name: Install pip packages
pip:
name: "{{ item }}"

View File

@ -38,19 +38,33 @@
until: install_packages|success
retries: 5
delay: 2
with_items: lxc_apt_packages
with_items: lxc_packages
tags:
- lxc-apt-packages
# The functionality with changing the container cache has been added into the
# upstream LXC templates with patch [ https://github.com/lxc/lxc/pull/558 ]
# TODO: remove the below patch and pass lxc_container_cache_path to lxc
# templates as appropriate once the lxc update goes mainstream
- name: Patch lxc-ubuntu cache path
replace:
dest: /usr/share/lxc/templates/lxc-ubuntu
regexp: '\$LOCALSTATEDIR/cache/lxc'
replace: "{{ lxc_container_cache_path }}"
backup: yes
- name: Drop irqbalance config
template:
src: "irqbalance.j2"
dest: "/etc/default/irqbalance"
owner: "root"
group: "root"
mode: "0644"
notify:
- Restart irqbalance
tags:
- lxc-cache-path
- lxc-files
- lxc-irqbalance
- name: Drop lxc-openstack app armor profile
template:
src: "lxc-openstack.apparmor.j2"
dest: "/etc/apparmor.d/lxc/lxc-openstack"
owner: "root"
group: "root"
mode: "0644"
notify:
- Load lxc-openstack apparmor profile
- Restart apparmor
tags:
- lxc-files
- lxc-apparmor

213
tasks/lxc_install_yum.yml Normal file
View File

@ -0,0 +1,213 @@
---
# Copyright 2016, Rackspace US, 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.
- name: Install yum packages
yum:
pkg: "{{ item }}"
state: present
register: install_packages
until: install_packages|success
retries: 5
delay: 2
with_items: lxc_packages
tags:
- lxc-packages
- name: Create base directories
file:
path: "{{ item }}"
state: "directory"
owner: "root"
group: "root"
with_items:
- /opt/lxc_embedded
tags:
- lxc-directories
- name: download file with sha256 check
get_url:
url: "{{ lxc_download_url }}"
dest: "/opt/lxc_embedded/{{ lxc_download_url | basename }}"
register: source_download
tags:
- lxc-source
- lxc-source-download
- name: Move lxc cached image into place
unarchive:
src: "/opt/lxc_embedded/{{ lxc_download_url | basename }}"
dest: "/opt/lxc_embedded/"
copy: "no"
when: source_download|changed
tags:
- lxc-source
- lxc-source-unarchive
- name: Create new linked lib location
copy:
content: "/opt/lxc_embedded/x86_64-linux-gnu"
dest: "/etc/ld.so.conf.d/lxc-x86_64.conf"
mode: "0644"
tags:
- lxc-source
- lxc-ldconfig
- name: Create python3 link
file:
src: /usr/bin/python3.4
dest: /usr/bin/python3
state: link
tags:
- lxc-source
- name: Build and install LXC
shell: '{{ item }}'
args:
creates: /opt/lxc_embedded/bin/lxc-ls
chdir: "/opt/lxc_embedded/{{ lxc_download_url | basename | replace('.tar.gz', '') }}"
environment:
PYTHONDEV_CFLAGS: "-I/usr/include/python3.4m"
PYTHONDEV_LIBS: "-lpython3.4m"
with_items:
- ./autogen.sh
- ./configure --prefix=/opt/lxc_embedded
--libdir=/opt/lxc_embedded/x86_64-linux-gnu
--libexecdir=/opt/lxc_embedded/x86_64-linux-gnu
--with-rootfs-path=/opt/lxc_embedded/x86_64-linux-gnu/lxc
--sysconfdir=/etc
--localstatedir=/var
--with-config-path=/var/lib/lxc
--with-distro={{ ansible_distribution | lower }}
--enable-seccomp
--enable-python
--enable-doc
--enable-rpath
--enable-selinux
--enable-capabilities
--enable-configpath-log
--disable-tests
--disable-lua
- make
- make install
tags:
- lxc-source
- lxc-source-compile
- name: Ensure embedded LXC is within the PATH
lineinfile:
dest: "{{ item.dest }}"
line: "{{ item.line }}"
create: "true"
with_items:
- { dest: "/etc/profile.d/lxc-path.sh", line: "pathmunge /opt/lxc_embedded/bin" }
tags:
- lxc-source
- lxc-path
- name: Remove sub system lock if found
file:
path: "{{ item }}"
state: "absent"
owner: "root"
group: "root"
with_items:
- /var/lock/subsys/lxc
tags:
- lxc-directories
- name: Drop post up script
copy:
content: |
#!/usr/bin/env bash
if [ "${DEVICE}" == "{{ lxc_net_bridge }}" ];then
if [ "{{ lxc_net_nat }}" == "True" ];then
/usr/local/bin/lxc-system-manage iptables-create
/usr/local/bin/lxc-system-manage dnsmasq-start || true
fi
fi
dest: "/etc/sysconfig/network-scripts/ifup-post-{{ lxc_net_bridge }}"
owner: "root"
group: "root"
mode: "0755"
tags:
- lxc-post-up
- name: Drop post down script
copy:
content: |
#!/usr/bin/env bash
if [ "${DEVICE}" == "{{ lxc_net_bridge }}" ];then
if [ "{{ lxc_net_nat }}" == "True" ];then
/usr/local/bin/lxc-system-manage dnsmasq-stop
/usr/local/bin/lxc-system-manage iptables-remove
fi
fi
dest: "/etc/sysconfig/network-scripts/ifdown-post-{{ lxc_net_bridge }}"
owner: "root"
group: "root"
mode: "0755"
tags:
- lxc-post-down
- name: Create networking post-up data
lineinfile:
dest: "{{ item.dest }}"
line: "{{ item.line }}"
insertbefore: "^exit\ 0$"
with_items:
- dest: "/etc/sysconfig/network-scripts/ifup-post"
line: ". /etc/sysconfig/network-scripts/ifup-post-{{ lxc_net_bridge }}"
tags:
- lxc-post-up
- name: Create networking post-down data
lineinfile:
dest: "{{ item.dest }}"
line: "{{ item.line }}"
insertbefore: "^exit\ 0$"
with_items:
- dest: "/etc/sysconfig/network-scripts/ifdown-post"
line: ". /etc/sysconfig/network-scripts/ifdown-post-{{ lxc_net_bridge }}"
tags:
- lxc-post-down
- name: Link embedded lxc to python3
shell: >
find /opt/lxc_embedded/lib64/python3.4/site-packages/* -maxdepth 0 | xargs -n1 ln -sf
args:
chdir: /usr/lib64/python3.4
tags:
- lxc-links
- name: Run ldconfig to make sure all libs are linked
command: ldconfig -v
tags:
- lxc-links
# This is needed because Ansible will not read an exported PATH and the default path is too restrictive
- name: Update the sudoers defaults
lineinfile:
dest: /etc/sudoers
state: present
regexp: '{{ item.regexp }}'
line: '{{ item.line }}'
validate: 'visudo -cf %s'
with_items:
- regexp: '^Defaults.*env_reset.*'
line: 'Defaults env_reset'
- regexp: '^Defaults.*secure_path.*'
line: 'Defaults secure_path="/opt/lxc_embedded/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"'
tags:
- lxc-path

View File

@ -13,27 +13,79 @@
# See the License for the specific language governing permissions and
# limitations under the License.
- name: Drop lxc net bridge
template:
src: "{{ item.src }}"
dest: "{{ item.dest }}"
owner: "root"
group: "root"
mode: "0644"
with_items: "{{ lxc_cached_network_interfaces }}"
notify:
- Bring bridge up
tags:
- lxc-files
- lxc-net
- lxc-bridge
- lxc-interfaces
# All Debian installations of LXC use the lxc-net service. This service breaks our network
# model and needs to be disabled
- name: Disable and stop lxc-net
service:
name: lxc-net
enabled: no
state: stopped
when:
- ansible_os_family == "Debian"
tags:
- lxc-net
# All installations of LXC on init based systems (upstart primarily) will need to have the
# the lxc-net service override in place to ensure its not restarted on system boot
- name: Drop lxc-net override file for upstart
template:
src: manual-init.override.j2
dest: /etc/init/lxc-net.override
owner: root
group: root
mode: 0644
when:
- pid1_name == "init"
tags:
- lxc-files
- lxc-net
# All Debian based systems use the interfaces.d directory for extra network configs
# this check ensures the needed source line is in the base config file
- name: Ensure networking includes interfaces.d
lineinfile:
dest: "/etc/network/interfaces"
line: "source /etc/network/interfaces.d/*.cfg"
backup: "yes"
when:
- ansible_os_family == "Debian"
tags:
- lxc-net
- lxc-interfaces
- name: Drop lxc net bridge
- name: Drop lxc net bridge - Debian
template:
src: "lxc-net-bridge.cfg.j2"
dest: "/etc/network/interfaces.d/lxc-net-bridge.cfg"
owner: "root"
group: "root"
mode: "0644"
when:
- ansible_os_family == "Debian"
notify:
- Restart bridge
tags:
- lxc-files
- lxc-net
- lxc-bridge
# Check that the container bridge exists, if not bring it up
- name: Check Container Bridge exists
file:
state: "file"
@ -44,5 +96,7 @@
notify:
- Bring bridge up
tags:
- lxc-net
- lxc-bridge
# Ensure lxc networks are running as they're supposed to
- meta: flush_handlers

View File

@ -32,38 +32,23 @@
mode: "{{ item.mode|default('0644') }}"
with_items:
- { src: lxc-openstack.conf.j2, dest: "/etc/lxc/lxc-openstack.conf" }
- { src: default.conf.j2, dest: "/etc/lxc/default.conf" }
- { src: lxc.default.j2, dest: "/etc/default/lxc-net", mode: "0644" }
- { src: lxc-system-manage.j2, dest: "/usr/local/bin/lxc-system-manage", mode: "0755" }
tags:
- lxc-files
- lxc-config
- name: Drop irqbalance config
template:
src: "irqbalance.j2"
dest: "/etc/default/irqbalance"
- name: Drop lxc veth check script
copy:
src: "lxc-veth-check.sh"
dest: "/usr/local/bin/lxc-veth-check"
owner: "root"
group: "root"
mode: "0644"
notify:
- Restart irqbalance
mode: "0755"
tags:
- lxc-files
- lxc-irqbalance
- name: Drop lxc-openstack app armor profile
template:
src: "lxc-openstack.apparmor.j2"
dest: "/etc/apparmor.d/lxc/lxc-openstack"
owner: "root"
group: "root"
mode: "0644"
notify:
- Load lxc-openstack apparmor profile
- Restart apparmor
tags:
- lxc-files
- lxc-apparmor
- lxc-config
# Ensure apparmor reindex runs before other things that may fail
- meta: flush_handlers

View File

@ -32,14 +32,3 @@
- "{{ lxc_container_cache_path }}"
tags:
- lxc-directories
- name: Drop lxc-net override file
template:
src: manual-init.override.j2
dest: /etc/init/lxc-net.override
owner: root
group: root
mode: 0644
tags:
- lxc-files
- lxc-config

View File

@ -35,10 +35,23 @@
with_first_found:
- "{{ ansible_distribution | lower }}-{{ ansible_distribution_version | lower }}.yml"
- "{{ ansible_distribution | lower }}.yml"
- "{{ ansible_os_family | lower }}-{{ ansible_distribution_version.split('.')[0] }}.yml"
- "{{ ansible_os_family | lower }}.yml"
tags:
- always
- name: Check init system
command: cat /proc/1/comm
register: _pid1_name
tags:
- always
- name: Set the name of pid1
set_fact:
pid1_name: "{{ _pid1_name.stdout }}"
tags:
- always
- include: lxc_pre_install.yml
- include: lxc_install.yml
- include: lxc_post_install.yml
@ -46,7 +59,6 @@
- include: lxc_net.yml
- include: lxc_dnsmasq_cleanup.yml
- include: lxc_cache.yml
- include: lxc_cache_preparation.yml
when: lxc_container_caches is defined
- name: Flush handlers
meta: flush_handlers

View File

@ -0,0 +1,5 @@
lxc.network.type = {{ lxc_container_net_type }}
lxc.network.name = {{ lxc_container_net_name }}
lxc.network.link = {{ lxc_container_net_link }}
lxc.network.flags = up
lxc.network.hwaddr = 00:16:3e:xx:xx:xx

View File

@ -0,0 +1,17 @@
# {{ ansible_managed }}
DEVICE={{ lxc_net_bridge }}
TYPE=Bridge
IPADDR={{ lxc_net_address }}
NETMASK={{ lxc_net_netmask }}
{% if lxc_net_gateway is not none %}
GATEWAY={{ lxc_net_gateway }}
{% endif %}
{% if lxc_net_mtu is defined %}
MTU={{ lxc_net_mtu }}
{% endif %}
ONBOOT=yes
BOOTPROTO=none
NM_CONTROLLED=no
DELAY=0
STP=no

View File

@ -1,3 +0,0 @@
{% for item in lxc_cache_resolvers %}
{{ item }}
{% endfor %}

View File

@ -1,5 +0,0 @@
# {{ ansible_managed }}
deb {{ lxc_container_template_main_apt_repo }} {{ lxc_container_release }} {{ lxc_container_template_apt_components | join(" ") }}
deb {{ lxc_container_template_main_apt_repo }} {{ lxc_container_release }}-updates {{ lxc_container_template_apt_components | join(" ") }}
deb {{ lxc_container_template_main_apt_repo }} {{ lxc_container_release }}-backports {{ lxc_container_template_apt_components | join(" ") }}
deb {{ lxc_container_template_security_apt_repo }} {{ lxc_container_release }}-security {{ lxc_container_template_apt_components | join(" ") }}

View File

@ -1 +1 @@
This is a test file to verify that the container cache file copy worked.
This is a test file to verify that the container cache file copy worked.

View File

@ -1,15 +0,0 @@
auto lxcbr0
iface lxcbr0 inet static
address 10.100.100.1
netmask 255.255.255.0
# dnsmasq start and stop
post-up /usr/local/bin/lxc-system-manage iptables-create
post-up /usr/local/bin/lxc-system-manage dnsmasq-start || true
post-down /usr/local/bin/lxc-system-manage iptables-remove
post-down /usr/local/bin/lxc-system-manage dnsmasq-stop
bridge_fd 0
bridge_maxwait 0
bridge_ports none
bridge_hello 2
bridge_maxage 12
bridge_stp off

View File

@ -17,9 +17,14 @@
hosts: localhost
connection: local
pre_tasks:
- name: Show host facts
debug:
var: hostvars
- name: First ensure apt cache is always refreshed
apt:
update_cache: yes
when:
- ansible_pkg_mgr == 'apt'
- name: Ensure root ssh key
user:
name: "{{ ansible_env.USER | default('root') }}"
@ -46,43 +51,34 @@
- src: files/container-file-copy-test.txt
dest: /tmp/file-copied-from-deployment-host.txt
post_tasks:
- name: Open sysctl file
slurp:
src: /etc/sysctl.conf
register: sysctl_file
- name: Read files
set_fact:
sysctl_content: "{{ sysctl_file.content | b64decode }}"
- name: Check for container tar
stat:
path: /var/cache/lxc_trusty.tgz
register: container_tar_file
- name: Check for container cache dir
stat:
path: /var/cache/lxc/trusty/rootfs-amd64/
register: container_cache_dir
- name: Get sysctl content
shell: |
cat /etc/sysctl.conf
register: sysctl_content
- name: Check for lxc bridge
stat:
path: /sys/class/net/lxcbr0/bridge/bridge_id
register: lxc_bridge_file
- name: Check dnsmasq is running
shell: ps auxfww | grep -w 'dnsmasq -u lxc-dnsmasq'
- name: Get deployed interface file contents, without Ansible managed line
- name: DEBIAN - Get deployed interface file contents, without Ansible managed line
shell: |
cat /etc/network/interfaces.d/lxc-net-bridge.cfg | tail -n +3
register: interface_file
- name: Get expected interface file contents
register: _debian_interface_file
when: ansible_os_family | lower == "debian"
- name: DEBIAN - interface file fact
set_fact:
interface_file: "{{ _debian_interface_file.stdout }}"
when: ansible_os_family | lower == "debian"
- name: RHEL - Get deployed interface file contents, without Ansible managed line
shell: |
cat files/expected-lxc-net-bridge.cfg
register: expected_interface_file
- name: Get the deployed test file from the container cache
slurp:
src: /var/cache/lxc/trusty/rootfs-amd64/tmp/file-copied-from-deployment-host.txt
register: copied_file
- name: Get the expected test file which should have been copied
slurp:
src: files/container-file-copy-test.txt
register: expected_copied_file
cat /etc/sysconfig/network-scripts/ifcfg-lxcbr0 | tail -n +3
register: _rhel_interface_file
when: ansible_os_family | lower == "redhat"
- name: RHEL - interface file fact
set_fact:
interface_file: "{{ _rhel_interface_file.stdout }}"
when: ansible_os_family | lower == "redhat"
- name: Get bridge interface facts
setup:
filter: ansible_lxcbr0
@ -90,10 +86,9 @@
- name: Check role functions
assert:
that:
- "'fs.inotify.max_user_instances' in sysctl_content"
- interface_file | search('.*lxcbr0.*')
- interface_file | search('.*10.100.100.1.*')
- interface_file | search('.*255.255.255.0.*')
- sysctl_content.stdout | search('fs.inotify.max_user_instances.*')
- "lxc_bridge_file.stat.exists"
- "container_cache_dir.stat.isdir"
- "container_tar_file.stat.exists"
- "interface_file.stdout | match(expected_interface_file.stdout)"
- "copied_file.content | match(expected_copied_file.content)"
- "lxcbr0_facts.ansible_facts.ansible_lxcbr0.ipv4.address | match('10.100.100.1')"

70
vars/redhat-7.yml Normal file
View File

@ -0,0 +1,70 @@
---
# Copyright 2016, Rackspace US, 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.
lxc_download_url: "https://linuxcontainers.org/downloads/lxc/lxc-1.0.8.tar.gz"
# Required rpm packages.
lxc_packages:
- '@Development Tools'
- automake
- autoconf
- bridge-utils
- debootstrap
- docbook2X
- dnsmasq
- git
- libseccomp
- libseccomp-devel
- libcap-devel
- libselinux
- libselinux-devel
- python-devel
- python34-libs
- python34-devel
- pkgconfig
- redhat-lsb
- xz
lxc_cache_map:
distro: centos
arch: amd64
release: 7
cache_packages:
- openssh-server
- sudo
repos: {}
cache_base_commands: |
rm /etc/resolv.conf
{% for resolver in lxc_cache_resolvers %}
echo "{{ resolver }}" | tee -a /etc/resolv.conf
{% endfor %}
{{ lxc_cache_install_command }} wget python2
rm -f /usr/bin/python
ln -s /usr/bin/python2.7 /usr/bin/python
/usr/bin/wget https://dl.fedoraproject.org/pub/epel/epel-release-latest-7.noarch.rpm -O /tmp/epel-release-latest-7.noarch.rpm
/usr/bin/rpm -ivh /tmp/epel-release-latest-7.noarch.rpm || true
cache_post_commands: |
yum clean all
lxc_cache_install_command: "yum install -y"
pip_install_options: >
--global-option=build_ext
--global-option="-L/opt/lxc_embedded/x86_64-linux-gnu/"
--global-option="-I/opt/lxc_embedded/include/"
lxc_cached_network_interfaces:
- src: "lxc-net-ifcfg-bridge.cfg.j2"
dest: "/etc/sysconfig/network-scripts/ifcfg-lxcbr0"

View File

@ -18,17 +18,13 @@ cache_timeout: 600
# Container repos
lxc_container_template_main_apt_repo: "https://mirror.rackspace.com/ubuntu"
lxc_container_template_security_apt_repo: "https://mirror.rackspace.com/ubuntu"
lxc_container_template_security_apt_repo: "{{ lxc_container_template_main_apt_repo }}"
lxc_container_template_apt_components:
- main
- universe
# Default image to build from
lxc_container_release: trusty
lxc_container_user_name: ubuntu
# Required apt packages.
lxc_apt_packages:
lxc_packages:
- apparmor
- apparmor-utils
- bridge-utils
@ -45,11 +41,91 @@ lxc_apt_packages:
- lxc-templates
- python-dev
- python3-lxc
- pxz
# Commands to run against cached LXC image
lxc_cache_commands:
- apt-get update
- apt-get -y upgrade
- apt-get -y install python2.7
- rm -f /usr/bin/python
- ln -s /usr/bin/python2.7 /usr/bin/python
lxc_cache_map:
distro: ubuntu
arch: amd64
release: trusty
cache_packages:
- bridge-utils
- bsdmainutils
- build-essential
- cgmanager
- cgmanager-utils
- cgroup-lite
- comerr-dev
- curl
- debconf-utils
- debhelper
- dh-apparmor
- gettext
- gir1.2-glib-2.0
- git
- groff-base
- intltool-debian
- iptables
- iso-codes
- krb5-multidev
- libcgmanager-dev
- libdbus-1-dev
- libdbus-glib-1-2
- libdevmapper-event1.02.1
- libexpat1-dev
- libffi-dev
- libpq-dev
- libpq5
- libpython-dev
- libxml2-dev
- libxslt1-dev
- libxslt1.1
- lvm2
- openssh-server
- python-apt
- python-apt-common
- python-dev
- python-pycurl
- python-software-properties
- python3-apt
- python3-dbus
- python3-gi
- python3-minimal
- python3-pycurl
- python3-software-properties
- software-properties-common
- sqlite3
- ssh
- sshpass
- time
repos:
"/etc/apt/sources.list": |
deb {{ lxc_container_template_main_apt_repo }} trusty {{ lxc_container_template_apt_components | join(' ') }}
deb {{ lxc_container_template_main_apt_repo }} trusty-updates {{ lxc_container_template_apt_components | join(' ') }}
deb {{ lxc_container_template_main_apt_repo }} trusty-backports {{ lxc_container_template_apt_components | join(' ') }}
deb {{ lxc_container_template_security_apt_repo }} trusty-security {{ lxc_container_template_apt_components | join(' ') }}
cache_base_commands: |
rm /run/resolvconf/resolv.conf
# This enforces the resolvers from within the image
{% for resolver in lxc_cache_resolvers %}
echo "{{ resolver }}" | tee -a /run/resolvconf/resolv.conf
{% endfor %}
cp /run/resolvconf/resolv.conf /etc/resolvconf/resolv.conf.d/base
echo "# NONE" > /etc/resolvconf/resolv.conf.d/tail
echo "# NONE" > /etc/resolvconf/resolv.conf.d/original
# This is done because its possible the base repos being installed will use https
# and ansible needs access to python2.7 which the system may not have by default
{{ lxc_cache_install_command }} apt-transport-https python2.7
apt-get -y upgrade
rm -f /usr/bin/python
ln -s /usr/bin/python2.7 /usr/bin/python
mkdir -p /root/.ssh
chmod 700 /root/.ssh
userdel --force --remove ubuntu || true
cache_post_commands: |
apt-get clean
lxc_cache_install_command: "export DEBIAN_FRONTEND=noninteractive && apt-get update && apt-get install -y"
lxc_cached_network_interfaces:
- src: "lxc-net-bridge.cfg.j2"
dest: "/etc/network/interfaces.d/lxc-net-bridge.cfg"

84
vars/ubuntu-16.04.yml Normal file
View File

@ -0,0 +1,84 @@
---
# Copyright 2016, Rackspace US, 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.
## APT Cache Options
cache_timeout: 600
# Container repos
lxc_container_template_main_apt_repo: "https://mirror.rackspace.com/ubuntu"
lxc_container_template_security_apt_repo: "{{ lxc_container_template_main_apt_repo }}"
lxc_container_template_apt_components:
- main
- universe
# Required apt packages.
lxc_packages:
- apparmor
- apparmor-utils
- bridge-utils
- cgmanager
- cgroup-lite
- debootstrap
- dnsmasq
- git
- irqbalance
- language-pack-en
- liblxc1
- lxc
- lxc-dev
- lxc-templates
- python-dev
- python3-lxc
- pxz
lxc_cache_map:
distro: ubuntu
arch: amd64
release: xenial
cache_packages:
- openssh-server
repos:
"/etc/apt/sources.list": |
deb {{ lxc_container_template_main_apt_repo }} xenial {{ lxc_container_template_apt_components | join(' ') }}
deb {{ lxc_container_template_main_apt_repo }} xenial-updates {{ lxc_container_template_apt_components | join(' ') }}
deb {{ lxc_container_template_main_apt_repo }} xenial-backports {{ lxc_container_template_apt_components | join(' ') }}
deb {{ lxc_container_template_security_apt_repo }} xenial-security {{ lxc_container_template_apt_components | join(' ') }}
cache_base_commands: |
rm /run/resolvconf/resolv.conf
# This enforces the resolvers from within the image
{% for resolver in lxc_cache_resolvers %}
echo "{{ resolver }}" | tee -a /run/resolvconf/resolv.conf
{% endfor %}
cp /run/resolvconf/resolv.conf /etc/resolvconf/resolv.conf.d/base
echo "# NONE" > /etc/resolvconf/resolv.conf.d/tail
echo "# NONE" > /etc/resolvconf/resolv.conf.d/original
# This is done because its possible the base repos being installed will use https
# and ansible needs access to python2.7 which the system may not have by default
{{ lxc_cache_install_command }} apt-transport-https python2.7
apt-get -y upgrade
rm -f /usr/bin/python
ln -s /usr/bin/python2.7 /usr/bin/python
mkdir -p /root/.ssh
chmod 700 /root/.ssh
userdel --force --remove ubuntu || true
cache_post_commands: |
apt-get clean
lxc_cache_install_command: "export DEBIAN_FRONTEND=noninteractive && apt-get update && apt-get install -y"
lxc_cached_network_interfaces:
- src: "lxc-net-bridge.cfg.j2"
dest: "/etc/network/interfaces.d/lxc-net-bridge.cfg"