makeself icon indicating copy to clipboard operation
makeself copied to clipboard

makeself removes directory name when specifying directory without sub-directories

Open PeterWhittaker opened this issue 2 years ago • 5 comments

Given a directory bin containing two files, test1 and test2, I would expect different behaviour when running the two commands

makeself --current ./bin ~/test.sh test_label cd bin; makeself --current . ~/test.sh test_label

but the results are exactly the same:

Adding files to archive named "test.sh"...
./test1
./test2

The second command does what I would expect: it creates an archive containing the contents of bin, but without any path information. This is consistent with cd bin; tar cf ../test.tar ., for example. Perfect!

But I would expect the first command to be consistent with tar cf test.tar ./bin, that is, I would expect it to preserve the relative path information. In other words, I would expect

Adding files to archive named "test.sh"...
./bin/test1
./bin/test2

After all, if I go to bin's parent directory, and execute makeself --current . test.sh somelabel, I get

Adding files to archive named "test.sh"...
./bin/test1
./bin/test2

which, again, is consistent with cd ..; tar cf test.tar . (assuming one started in bin).

FWIW, I discovered this while attempting to incrementally build a self-extractor of only parts of my current working directory. E.g., I have a directory containing .git, bin, etc, var, lib, wlp, examples, README, Makefile, testing, etc., and I only want to include bin, etc, lib, and var in my archive.

In other words, I wanted to do

makeself --current ./bin test.sh somelabel
makeself --append ./lib test.sh somelabel
makeself --append ./etc test.sh somelabel
makeself --append ./var test.sh somelabel

but everything ends up being flattened, which is not what I expected.

The only supported way to do this is to use --tar-extra --exclude=wlp --exclude examples --exclude Makefile..., which is a bit clunky, since I may have far more directories that aren't bin, etc, lib, or var. (I've tried getting a man 7 glob pattern that works but have had no luck.)

PeterWhittaker avatar Aug 29 '23 15:08 PeterWhittaker

If I understand correctly, makeself doesn't support multiple source directories.

On Tue, Aug 29, 2023, 11:01 Peter Whittaker @.***> wrote:

Given a directory bin containing two files, test1 and test2, I would expect different behaviour when running the two commands

makeself --current ./bin ~/test.sh test_label cd bin; makeself --current . ~/test.sh test_label

but the results are exactly the same:

Adding files to archive named "test.sh"... ./test1 ./test2

The second command does what I would expect: it creates an archive containing the contents of bin, but without any path information. This is consistent with cd bin; tar cf ../test.tar ., for example. Perfect!

But I would expect the first command to be consistent with tar cf test.tar ./bin, that is, I would expect it to preserve the relative path information. In other words, I would expect

Adding files to archive named "test.sh"... ./bin/test1 ./bin/test2

After all, if I go to bin's parent directory, and execute makeself --current . test.sh somelabel, I get

Adding files to archive named "test.sh"... ./bin/test1 ./bin/test2

which, again, is consistent with cd ..; tar cf test.tar . (assuming one started in bin).

FWIW, I discovered this while attempting to incrementally build a self-extractor of only parts of my current working directory. E.g., I have a directory containing .git, bin, etc, var, lib, wlp, examples, README, Makefile, testing, etc., and I only want to include bin, etc, lib, and var in my archive.

In other words, I wanted to do

makeself --current ./bin test.sh somelabel makeself --append ./lib test.sh somelabel makeself --append ./etc test.sh somelabel makeself --append ./var test.sh somelabel

but everything ends up being flattened, which is not what I expected.

The only supported way to do this is to use --tar-extra --exclude=wlp --exclude examples --exclude Makefile..., which is a bit clunky, since I may have far more directories that aren't bin, etc, lib, or var. (I've tried getting a man 7 glob pattern that works but have had no luck.)

— Reply to this email directly, view it on GitHub https://github.com/megastep/makeself/issues/314, or unsubscribe https://github.com/notifications/unsubscribe-auth/AKY6BKLPY4RNZJ6Q3FJYA2LXXX743ANCNFSM6AAAAAA4DDGIPA . You are receiving this because you are subscribed to this thread.Message ID: @.***>

realtime-neil avatar Aug 29 '23 22:08 realtime-neil

Yeah, that's the way it has been for a long time and changing this behavior would probably break the way people use the tool already.

That said I'd be open to enabling a new kind of behavior over time to make this easier.

megastep avatar Aug 29 '23 22:08 megastep

Agreed. When and if the "calling convention" for creation/appendation is changed to support multiple tar arguments, this would become feasible.

On Tue, Aug 29, 2023, 18:19 Stéphane Peter @.***> wrote:

Yeah, that's the way it has been for a long time and changing this behavior would probably break the way people use the tool already.

That said I'd be open to enabling a new kind of behavior over time to make this easier.

— Reply to this email directly, view it on GitHub https://github.com/megastep/makeself/issues/314#issuecomment-1698219733, or unsubscribe https://github.com/notifications/unsubscribe-auth/AKY6BKKVOVFPSUL2RUGUZVLXXZTGPANCNFSM6AAAAAA4DDGIPA . You are receiving this because you commented.Message ID: @.***>

realtime-neil avatar Aug 29 '23 23:08 realtime-neil

What if we introduced two different calling conventions, which would be easily detectable via command line argument processing?

  1. The current positional scheme, in which self-extractor name and label must always be present, and
  2. A flagged scheme, in which all arguments are specified via flag?

For sake of argument, assume that -s ... denotes the name of the self-extractor and and -l ... denotes the label. Then, under the new convention, -s ... -l ... would be required, unless --append was supplied, in which case only -s ... was supplied.

So far, so good.

Then we add a flag, e.g., --root or --base, which, regardless of the path elements to include in the archive represents the top level directory of the archive, from which all included files are interpreted.

Under this scheme, --root/--base would be required inly under creation, not under --append -s ..., which would respect this initial setting (and initial -l label as well, e.g.).

This wouldn't be a breaking change, since users could continue to use the original calling convention.

PeterWhittaker avatar Sep 03 '23 23:09 PeterWhittaker

What if we introduced two different calling conventions, which would be easily detectable via command line argument processing?

Okay, I see where you're going with this. If I understand correctly, then I have some criticisms I would like to share.

  1. The current positional scheme, in which self-extractor name and label must always be present, and
  2. A flagged scheme, in which all arguments are specified via flag?

Yes, this trick is familiar to me. My general criticism is that it complicates the parsing logic for the option flags, option arguments, and positional arguments. Because users make mistakes, you can expect makeself to be invoked with every possible combinatorial expansion of opts and args. This usually forces you to do at least one of the following:

  • Absorb (and save) the entire argv before attempting to parse it.

  • Parse each option iteratively while aggressively vetting each to defend against mutually conflicting options.

For sake of argument, assume that -s ... denotes the name of the self-extractor and and -l ... denotes the label. Then, under the new convention, -s ... -l ... would be required, unless --append was supplied, in which case only -s ... was supplied.

Consider the case where the caller invokes

makeself.sh -s foobar -l 'Foo Bar' mything mything.run 'My Thing' ./start.sh

The caller's invocation seems incorrect until you consider the possibility that any of the non-option positional arguments could be an intentional reference to a directory in $PWD. You can't know they don't exist until tar fails to add them.

Then we add a flag, e.g., --root or --base, which, regardless of the path elements to include in the archive represents the top level directory of the archive, from which all included files are interpreted.

Under this scheme, --root/--base would be required inly under creation, not under --append -s ..., which would respect this initial setting (and initial -l label as well, e.g.).

I like this even less. If makeself must grow an option denoting a "starting directory", then imho it should be -C and behave identically to that of tar. In fact, I'm going to go on record and say: the closer we can push the makeself calling convention to that of tar, the better.

This wouldn't be a breaking change, since users could continue to use the original calling convention.

You're correct in that the change you propose wouldn't break the interface embodied by the calling convention. It would, however, require:

  • at least 3 additional options; i.e., one for each of the current non-archive_dir positional arguments

  • argv accumulation before parsing and/or aggressive vetting during argv iteration

The problem here is really that, in its current form, makeself takes a singular input directory and an arbitrary quantity of script_args. To turn this convention on its head is non-trivial.

realtime-neil avatar Sep 05 '23 14:09 realtime-neil