2019-12-07 15:45:43 +01:00
|
|
|
#!/usr/bin/python3
|
|
|
|
# -*- coding: utf-8 -*-
|
|
|
|
|
|
|
|
import argparse
|
|
|
|
import os
|
2019-12-18 10:12:54 +01:00
|
|
|
import subprocess
|
2019-12-07 15:45:43 +01:00
|
|
|
import sys
|
|
|
|
import tempfile
|
|
|
|
|
|
|
|
from lxcmgr import lxcmgr
|
|
|
|
from lxcmgr.paths import LXC_ROOT
|
|
|
|
|
|
|
|
def get_layers(container):
|
|
|
|
with open(os.path.join(LXC_ROOT, container, 'config')) as f:
|
|
|
|
for line in f.read().splitlines():
|
|
|
|
if line.startswith('lxc.hook.pre-start'):
|
|
|
|
return line.split()[-1].split(',')
|
|
|
|
|
|
|
|
def extract(args):
|
|
|
|
with tempfile.TemporaryDirectory() as tmp_rootfs:
|
|
|
|
layers = get_layers(args.container)
|
|
|
|
lxcmgr.mount_rootfs(args.container, layers, tmp_rootfs)
|
|
|
|
source = os.path.join(tmp_rootfs, args.source.lstrip('/'))
|
2019-12-18 10:12:54 +01:00
|
|
|
# Plain cp -pr as shutil.copytree() requires nonexistent target and copy2() doesn't retain owner
|
|
|
|
subprocess.run(['cp', '-pr', source, args.destination])
|
2019-12-07 15:45:43 +01:00
|
|
|
lxcmgr.unmount_rootfs(tmp_rootfs)
|
|
|
|
|
|
|
|
def main(args):
|
|
|
|
if args.action == 'prepare':
|
|
|
|
# Used with LXC hooks on container startup
|
|
|
|
lxcmgr.prepare_container(args.container, args.layers)
|
|
|
|
elif args.action == 'cleanup':
|
|
|
|
# Used with LXC hooks on container stop
|
|
|
|
lxcmgr.cleanup_container(args.container)
|
|
|
|
elif args.action == 'extract':
|
|
|
|
# Used in install.sh scripts to get files or directories from containers rootfs (excluding persistent mounts)
|
|
|
|
extract(args)
|
|
|
|
|
|
|
|
parser = argparse.ArgumentParser(description='Collection of auxiliary LXC tools')
|
|
|
|
subparsers = parser.add_subparsers()
|
|
|
|
|
|
|
|
parser_prepare = subparsers.add_parser('prepare', help='Perform pre-start steps for LXC')
|
|
|
|
parser_prepare.set_defaults(action='prepare')
|
|
|
|
parser_prepare.add_argument('layers', help='OverlayFS LXC rootfs layers')
|
|
|
|
parser_prepare.add_argument('container', help='Container name')
|
|
|
|
parser_prepare.add_argument('lxc', nargs=argparse.REMAINDER)
|
|
|
|
|
|
|
|
parser_cleanup = subparsers.add_parser('cleanup', help='Perform post-stop steps for LXC')
|
|
|
|
parser_cleanup.set_defaults(action='cleanup')
|
|
|
|
parser_cleanup.add_argument('container', help='Container name')
|
|
|
|
parser_cleanup.add_argument('lxc', nargs=argparse.REMAINDER)
|
|
|
|
|
|
|
|
parser_extract = subparsers.add_parser('extract', help='Extracts files or directories from containers rootfs (excluding persistent mounts)')
|
2019-12-07 16:57:24 +01:00
|
|
|
parser_extract.set_defaults(action='extract')
|
2019-12-07 15:45:43 +01:00
|
|
|
parser_extract.add_argument('container', help='Container name')
|
|
|
|
parser_extract.add_argument('source', help='Source file or directory within the container')
|
|
|
|
parser_extract.add_argument('destination', help='Destination file or directory on the host')
|
|
|
|
|
2019-12-09 21:40:07 +01:00
|
|
|
args = parser.parse_args()
|
|
|
|
if hasattr(args, 'action'):
|
|
|
|
main(args)
|
|
|
|
else:
|
|
|
|
parser.print_usage()
|