mirror of https://github.com/borgbackup/borg.git
Merge pull request #5462 from schors/master
create: implement --stdin-mode, --stdin-user and --stdin-group, fixes #5333
This commit is contained in:
commit
5f23ff656a
|
@ -1234,14 +1234,19 @@ class FilesystemObjectProcessors:
|
||||||
item.update(self.metadata_collector.stat_attrs(st, path)) # can't use FD here?
|
item.update(self.metadata_collector.stat_attrs(st, path)) # can't use FD here?
|
||||||
return status
|
return status
|
||||||
|
|
||||||
def process_pipe(self, *, path, cache, fd):
|
def process_pipe(self, *, path, cache, fd, mode, user, group):
|
||||||
uid, gid = 0, 0
|
uid = user2uid(user)
|
||||||
|
if uid is None:
|
||||||
|
raise Error("no such user: %s" % user)
|
||||||
|
gid = group2gid(group)
|
||||||
|
if gid is None:
|
||||||
|
raise Error("no such group: %s" % group)
|
||||||
t = int(time.time()) * 1000000000
|
t = int(time.time()) * 1000000000
|
||||||
item = Item(
|
item = Item(
|
||||||
path=path,
|
path=path,
|
||||||
mode=0o100660, # regular file, ug=rw
|
mode=mode & 0o107777 | 0o100000, # forcing regular file mode
|
||||||
uid=uid, user=uid2user(uid),
|
uid=uid, user=user,
|
||||||
gid=gid, group=gid2group(gid),
|
gid=gid, group=group,
|
||||||
mtime=t, atime=t, ctime=t,
|
mtime=t, atime=t, ctime=t,
|
||||||
)
|
)
|
||||||
self.process_file_chunks(item, cache, self.stats, self.show_progress, backup_io_iter(self.chunker.chunkify(fd)))
|
self.process_file_chunks(item, cache, self.stats, self.show_progress, backup_io_iter(self.chunker.chunkify(fd)))
|
||||||
|
|
|
@ -78,6 +78,7 @@ try:
|
||||||
from .patterns import PatternMatcher
|
from .patterns import PatternMatcher
|
||||||
from .item import Item
|
from .item import Item
|
||||||
from .platform import get_flags, get_process_id, SyncFile
|
from .platform import get_flags, get_process_id, SyncFile
|
||||||
|
from .platform import uid2user, gid2group
|
||||||
from .remote import RepositoryServer, RemoteRepository, cache_if_remote
|
from .remote import RepositoryServer, RemoteRepository, cache_if_remote
|
||||||
from .repository import Repository, LIST_SCAN_LIMIT, TAG_PUT, TAG_DELETE, TAG_COMMIT
|
from .repository import Repository, LIST_SCAN_LIMIT, TAG_PUT, TAG_DELETE, TAG_COMMIT
|
||||||
from .selftest import selftest
|
from .selftest import selftest
|
||||||
|
@ -511,6 +512,9 @@ class Archiver:
|
||||||
logger.debug('Processing files ...')
|
logger.debug('Processing files ...')
|
||||||
if args.content_from_command:
|
if args.content_from_command:
|
||||||
path = args.stdin_name
|
path = args.stdin_name
|
||||||
|
mode = args.stdin_mode
|
||||||
|
user = args.stdin_user
|
||||||
|
group = args.stdin_group
|
||||||
if not dry_run:
|
if not dry_run:
|
||||||
try:
|
try:
|
||||||
try:
|
try:
|
||||||
|
@ -518,7 +522,7 @@ class Archiver:
|
||||||
except (FileNotFoundError, PermissionError) as e:
|
except (FileNotFoundError, PermissionError) as e:
|
||||||
self.print_error('Failed to execute command: %s', e)
|
self.print_error('Failed to execute command: %s', e)
|
||||||
return self.exit_code
|
return self.exit_code
|
||||||
status = fso.process_pipe(path=path, cache=cache, fd=proc.stdout)
|
status = fso.process_pipe(path=path, cache=cache, fd=proc.stdout, mode=mode, user=user, group=group)
|
||||||
rc = proc.wait()
|
rc = proc.wait()
|
||||||
if rc != 0:
|
if rc != 0:
|
||||||
self.print_error('Command %r exited with status %d', args.paths[0], rc)
|
self.print_error('Command %r exited with status %d', args.paths[0], rc)
|
||||||
|
@ -533,9 +537,12 @@ class Archiver:
|
||||||
for path in args.paths:
|
for path in args.paths:
|
||||||
if path == '-': # stdin
|
if path == '-': # stdin
|
||||||
path = args.stdin_name
|
path = args.stdin_name
|
||||||
|
mode = args.stdin_mode
|
||||||
|
user = args.stdin_user
|
||||||
|
group = args.stdin_group
|
||||||
if not dry_run:
|
if not dry_run:
|
||||||
try:
|
try:
|
||||||
status = fso.process_pipe(path=path, cache=cache, fd=sys.stdin.buffer)
|
status = fso.process_pipe(path=path, cache=cache, fd=sys.stdin.buffer, mode=mode, user=user, group=group)
|
||||||
except BackupOSError as e:
|
except BackupOSError as e:
|
||||||
status = 'E'
|
status = 'E'
|
||||||
self.print_warning('%s: %s', path, e)
|
self.print_warning('%s: %s', path, e)
|
||||||
|
@ -3222,6 +3229,12 @@ class Archiver:
|
||||||
help='experimental: do not synchronize the cache. Implies not using the files cache.')
|
help='experimental: do not synchronize the cache. Implies not using the files cache.')
|
||||||
subparser.add_argument('--stdin-name', metavar='NAME', dest='stdin_name', default='stdin',
|
subparser.add_argument('--stdin-name', metavar='NAME', dest='stdin_name', default='stdin',
|
||||||
help='use NAME in archive for stdin data (default: %(default)r)')
|
help='use NAME in archive for stdin data (default: %(default)r)')
|
||||||
|
subparser.add_argument('--stdin-user', metavar='USER', dest='stdin_user', default=uid2user(0),
|
||||||
|
help='set user USER in archive for stdin data (default: %(default)r)')
|
||||||
|
subparser.add_argument('--stdin-group', metavar='GROUP', dest='stdin_group', default=gid2group(0),
|
||||||
|
help='set group GROUP in archive for stdin data (default: %(default)r)')
|
||||||
|
subparser.add_argument('--stdin-mode', metavar='M', dest='stdin_mode', type=lambda s: int(s, 8), default=STDIN_MODE_DEFAULT,
|
||||||
|
help='set mode to M in archive for stdin data (default: %(default)04o)')
|
||||||
subparser.add_argument('--content-from-command', action='store_true',
|
subparser.add_argument('--content-from-command', action='store_true',
|
||||||
help='interpret PATH as command and store its stdout. See also section Reading from'
|
help='interpret PATH as command and store its stdout. See also section Reading from'
|
||||||
' stdin below.')
|
' stdin below.')
|
||||||
|
|
|
@ -20,6 +20,10 @@ REQUIRED_ARCHIVE_KEYS = frozenset(['version', 'name', 'items', 'cmdline', 'time'
|
||||||
# default umask, overridden by --umask, defaults to read/write only for owner
|
# default umask, overridden by --umask, defaults to read/write only for owner
|
||||||
UMASK_DEFAULT = 0o077
|
UMASK_DEFAULT = 0o077
|
||||||
|
|
||||||
|
# default file mode to store stdin data, defaults to read/write for owner and group
|
||||||
|
# forcing to 0o100XXX later
|
||||||
|
STDIN_MODE_DEFAULT = 0o660
|
||||||
|
|
||||||
CACHE_TAG_NAME = 'CACHEDIR.TAG'
|
CACHE_TAG_NAME = 'CACHEDIR.TAG'
|
||||||
CACHE_TAG_CONTENTS = b'Signature: 8a477f597d28d172789f06886806bc55'
|
CACHE_TAG_CONTENTS = b'Signature: 8a477f597d28d172789f06886806bc55'
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue