Drop Root Privileges in a Shell Script with setpriv
Run a command as an unprivileged user from a root script with setpriv --reuid --regid --clear-groups, optionally with --no-new-privs. It needs util-linux.
A root script starts a service or a tool that does not need root, and it should run with as little power as possible.
id -u
setpriv --reuid=1000 --regid=1000 id
setpriv --reuid=1000 --regid=1000 --clear-groups id
setpriv --reuid=1000 --regid=1000 --clear-groups --no-new-privs sh -c 'grep -E "^(Uid|NoNewPrivs|CapEff)" /proc/self/status'
setpriv --reuid=1000 --regid=1000 --clear-groups sh -c 'echo x > /root/file' 2>&10
setpriv: --[re]gid requires --keep-groups, --clear-groups, --init-groups, or --groups
uid=1000 gid=1000 groups=1000
Uid: 1000 1000 1000 1000
CapEff: 0000000000000000
NoNewPrivs: 1
sh: 1: cannot create /root/file: Permission deniedsetpriv --reuid=1000 --regid=1000 --clear-groups switches the user and group IDs and removes the supplementary groups of root, then runs the command, which reported uid=1000 gid=1000 groups=1000. The tool refuses to set a group ID without saying what to do about groups, which is why the second call printed an error. With --no-new-privs the process cannot gain privileges through setuid programs, NoNewPrivs was 1 and the effective capability set was empty, and writing to /root failed. See setpriv.
The target ID must exist in the sense that you give it as a number, but file ownership and the home directory are not changed, so set HOME yourself if the program needs it. setpriv is part of util-linux and absent from macOS and busybox builds without that applet; su -s or runuser are alternatives.