Allow to pass UID/GID to container exec
This commit is contained in:
parent
da27fa02e0
commit
645735a306
@ -94,9 +94,9 @@ def status(container_name):
|
|||||||
# Prints current running status of the container
|
# Prints current running status of the container
|
||||||
print(Container(container_name).get_state())
|
print(Container(container_name).get_state())
|
||||||
|
|
||||||
def execute(container_name, command):
|
def execute(container_name, command, uid, gid):
|
||||||
# Execute a command in container's namespace
|
# Execute a command in container's namespace
|
||||||
Container(container_name).execute(command)
|
Container(container_name).execute(command, uid, gid)
|
||||||
|
|
||||||
parser = argparse.ArgumentParser(description='SPOC container manager')
|
parser = argparse.ArgumentParser(description='SPOC container manager')
|
||||||
parser.set_defaults(action=None)
|
parser.set_defaults(action=None)
|
||||||
@ -149,6 +149,8 @@ parser_status.add_argument('container')
|
|||||||
|
|
||||||
parser_exec = subparsers.add_parser('exec')
|
parser_exec = subparsers.add_parser('exec')
|
||||||
parser_exec.set_defaults(action=ACTION_EXEC)
|
parser_exec.set_defaults(action=ACTION_EXEC)
|
||||||
|
parser_exec.add_argument('-u', '--uid', help='Sets the command UID')
|
||||||
|
parser_exec.add_argument('-g', '--gid', help='Sets the command GID')
|
||||||
parser_exec.add_argument('container')
|
parser_exec.add_argument('container')
|
||||||
parser_exec.add_argument('command', nargs=argparse.REMAINDER)
|
parser_exec.add_argument('command', nargs=argparse.REMAINDER)
|
||||||
|
|
||||||
@ -167,6 +169,6 @@ elif args.action == ACTION_STOP:
|
|||||||
elif args.action == ACTION_STATUS:
|
elif args.action == ACTION_STATUS:
|
||||||
status(args.container)
|
status(args.container)
|
||||||
elif args.action == ACTION_EXEC:
|
elif args.action == ACTION_EXEC:
|
||||||
execute(args.container, args.command)
|
execute(args.container, args.command, args.uid, args.gid)
|
||||||
else:
|
else:
|
||||||
parser.print_usage()
|
parser.print_usage()
|
||||||
|
@ -173,8 +173,7 @@ class Container:
|
|||||||
subprocess.Popen(['lxc-stop', '-P', CONTAINERS_DIR, self.name])
|
subprocess.Popen(['lxc-stop', '-P', CONTAINERS_DIR, self.name])
|
||||||
self.await_state(STATE_STOPPED)
|
self.await_state(STATE_STOPPED)
|
||||||
|
|
||||||
def execute(self, cmd, **kwargs):
|
def execute(self, cmd, uid=None, gid=None, **kwargs):
|
||||||
# TODO: Allow to pass UID/GID
|
|
||||||
# If the container is starting or stopping, wait until the operation is finished
|
# If the container is starting or stopping, wait until the operation is finished
|
||||||
state = self.get_state()
|
state = self.get_state()
|
||||||
if state == STATE_STARTING:
|
if state == STATE_STARTING:
|
||||||
@ -183,19 +182,27 @@ class Container:
|
|||||||
elif state == STATE_STOPPING:
|
elif state == STATE_STOPPING:
|
||||||
self.await_state(STATE_STOPPED)
|
self.await_state(STATE_STOPPED)
|
||||||
state = self.get_state()
|
state = self.get_state()
|
||||||
|
# Resolve UID/GID, if they have been given
|
||||||
|
uidgid_param = []
|
||||||
|
uid,gid = self.get_uidgid(uid, gid)
|
||||||
|
if uid:
|
||||||
|
uidgid_param.extend(('-u', uid))
|
||||||
|
if gid:
|
||||||
|
uidgid_param.extend(('-g', gid))
|
||||||
# If the container is stopped, use lxc-execute, otherwise use lxc-attach
|
# If the container is stopped, use lxc-execute, otherwise use lxc-attach
|
||||||
if state == STATE_STOPPED:
|
if state == STATE_STOPPED:
|
||||||
return subprocess.run(['lxc-execute', '-P', CONTAINERS_DIR, self.name, '--']+cmd, **kwargs)
|
return subprocess.run(['lxc-execute', '-P', CONTAINERS_DIR]+uidgid_param+[self.name, '--']+cmd, **kwargs)
|
||||||
elif state == STATE_RUNNING:
|
elif state == STATE_RUNNING:
|
||||||
return subprocess.run(['lxc-attach', '-P', CONTAINERS_DIR, '--clear-env', self.name, '--']+cmd, **kwargs)
|
return subprocess.run(['lxc-attach', '-P', CONTAINERS_DIR, '--clear-env']+uidgid_param+[self.name, '--']+cmd, **kwargs)
|
||||||
else:
|
else:
|
||||||
raise InvalidContainerStateError(self.name, state)
|
raise InvalidContainerStateError(self.name, state)
|
||||||
|
|
||||||
def get_uidgid(self, user, group=None):
|
def get_uidgid(self, user=None, group=None):
|
||||||
# Helper function to get UID/GID of an user/group from the container
|
# Helper function to get UID/GID of an user/group from the container
|
||||||
uid_entry = self.execute(['/usr/bin/getent', 'passwd', user], capture_output=True, check=True).stdout.decode().split(':')
|
uid,gid = None,None
|
||||||
|
if user:
|
||||||
|
uid_entry = self.execute(['/usr/bin/getent', 'passwd', user], capture_output=True, check=True).stdout.decode().split(':')
|
||||||
|
uid,gid = uid_entry[2],uid_entry[3]
|
||||||
if group:
|
if group:
|
||||||
gid_entry = self.execute(['/usr/bin/getent', 'group', group], capture_output=True, check=True).stdout.decode().split(':')
|
gid = self.execute(['/usr/bin/getent', 'group', group], capture_output=True, check=True).stdout.decode().split(':')[2]
|
||||||
return (uid_entry[2], gid_entry[2])
|
return (uid,gid)
|
||||||
else:
|
|
||||||
return (uid_entry[2], uid_entry[3])
|
|
||||||
|
Loading…
Reference in New Issue
Block a user