nix-prefetch-url: Add --executable flag

pkgs.fetchurl supports an executable argument, which is especially nice
when downloading a large executable. This patch adds the same option to
nix-prefetch-url.

I have tested this to work on the simple case of prefetching a little
executable:

1. nix-prefetch-url --executable https://my/little/script
2. Paste the hash into a pkgs.fetchurl-based package, script-pkg.nix
3. Delete the output from the store to avoid any misidentified artifacts
4. Realise the package script-pkg.nix
5. Run the executable

I repeated the above while using --name, as well.

I suspect --executable would have no meaningful effect if combined with
--unpack, but I have not tried it.
This commit is contained in:
Bryan Richter 2020-09-18 18:36:17 +03:00
parent 958bf57123
commit 5fe375a8f1
No known key found for this signature in database
GPG key ID: 3EDE726D934B289C
2 changed files with 12 additions and 2 deletions

View file

@ -51,6 +51,9 @@ Nix store is also printed.
result to the Nix store. The resulting hash can be used with result to the Nix store. The resulting hash can be used with
functions such as Nixpkgss `fetchzip` or `fetchFromGitHub`. functions such as Nixpkgss `fetchzip` or `fetchFromGitHub`.
- `--executable`
Set the executable bit on the downloaded file.
- `--name` *name* - `--name` *name*
Override the name of the file in the Nix store. By default, this is Override the name of the file in the Nix store. By default, this is
`hash-basename`, where *basename* is the last component of *url*. `hash-basename`, where *basename* is the last component of *url*.

View file

@ -57,6 +57,7 @@ static int _main(int argc, char * * argv)
bool fromExpr = false; bool fromExpr = false;
string attrPath; string attrPath;
bool unpack = false; bool unpack = false;
bool executable = false;
string name; string name;
struct MyArgs : LegacyArgs, MixEvalArgs struct MyArgs : LegacyArgs, MixEvalArgs
@ -81,6 +82,8 @@ static int _main(int argc, char * * argv)
} }
else if (*arg == "--unpack") else if (*arg == "--unpack")
unpack = true; unpack = true;
else if (*arg == "--executable")
executable = true;
else if (*arg == "--name") else if (*arg == "--name")
name = getArg(*arg, arg, end); name = getArg(*arg, arg, end);
else if (*arg != "" && arg->at(0) == '-') else if (*arg != "" && arg->at(0) == '-')
@ -175,7 +178,11 @@ static int _main(int argc, char * * argv)
/* Download the file. */ /* Download the file. */
{ {
AutoCloseFD fd = open(tmpFile.c_str(), O_WRONLY | O_CREAT | O_EXCL, 0600); auto mode = 0600;
if (executable)
mode = 0700;
AutoCloseFD fd = open(tmpFile.c_str(), O_WRONLY | O_CREAT | O_EXCL, mode);
if (!fd) throw SysError("creating temporary file '%s'", tmpFile); if (!fd) throw SysError("creating temporary file '%s'", tmpFile);
FdSink sink(fd.get()); FdSink sink(fd.get());
@ -201,7 +208,7 @@ static int _main(int argc, char * * argv)
tmpFile = unpacked; tmpFile = unpacked;
} }
const auto method = unpack ? FileIngestionMethod::Recursive : FileIngestionMethod::Flat; const auto method = unpack || executable ? FileIngestionMethod::Recursive : FileIngestionMethod::Flat;
auto info = store->addToStoreSlow(name, tmpFile, method, ht, expectedHash); auto info = store->addToStoreSlow(name, tmpFile, method, ht, expectedHash);
storePath = info.path; storePath = info.path;