aboutsummaryrefslogtreecommitdiff
path: root/src/nix-prefetch-url/nix-prefetch-url.cc
diff options
context:
space:
mode:
authorEelco Dolstra <edolstra@gmail.com>2021-01-07 21:51:46 +0100
committerEelco Dolstra <edolstra@gmail.com>2021-01-07 21:51:46 +0100
commit08133503494d023b646b3107acf159a5274466ec (patch)
tree6a2a766bd568ae75b68b1394ec1f3efa5d758022 /src/nix-prefetch-url/nix-prefetch-url.cc
parent0df69d96e02ce4c9e17bd33333c5d78313341dd3 (diff)
Add 'nix store prefetch-{file,tarball}'
These replace nix-prefetch-url and nix-prefetch-url --unpack, respectively.
Diffstat (limited to 'src/nix-prefetch-url/nix-prefetch-url.cc')
-rw-r--r--src/nix-prefetch-url/nix-prefetch-url.cc232
1 files changed, 0 insertions, 232 deletions
diff --git a/src/nix-prefetch-url/nix-prefetch-url.cc b/src/nix-prefetch-url/nix-prefetch-url.cc
deleted file mode 100644
index 3bdee55a7..000000000
--- a/src/nix-prefetch-url/nix-prefetch-url.cc
+++ /dev/null
@@ -1,232 +0,0 @@
-#include "hash.hh"
-#include "shared.hh"
-#include "filetransfer.hh"
-#include "store-api.hh"
-#include "eval.hh"
-#include "eval-inline.hh"
-#include "common-eval-args.hh"
-#include "attr-path.hh"
-#include "finally.hh"
-#include "../nix/legacy.hh"
-#include "progress-bar.hh"
-#include "tarfile.hh"
-
-#include <iostream>
-
-#include <sys/types.h>
-#include <sys/stat.h>
-#include <fcntl.h>
-
-using namespace nix;
-
-
-/* If ‘uri’ starts with ‘mirror://’, then resolve it using the list of
- mirrors defined in Nixpkgs. */
-string resolveMirrorUri(EvalState & state, string uri)
-{
- if (string(uri, 0, 9) != "mirror://") return uri;
-
- string s(uri, 9);
- auto p = s.find('/');
- if (p == string::npos) throw Error("invalid mirror URI");
- string mirrorName(s, 0, p);
-
- Value vMirrors;
- state.eval(state.parseExprFromString("import <nixpkgs/pkgs/build-support/fetchurl/mirrors.nix>", "."), vMirrors);
- state.forceAttrs(vMirrors);
-
- auto mirrorList = vMirrors.attrs->find(state.symbols.create(mirrorName));
- if (mirrorList == vMirrors.attrs->end())
- throw Error("unknown mirror name '%1%'", mirrorName);
- state.forceList(*mirrorList->value);
-
- if (mirrorList->value->listSize() < 1)
- throw Error("mirror URI '%1%' did not expand to anything", uri);
-
- string mirror = state.forceString(*mirrorList->value->listElems()[0]);
- return mirror + (hasSuffix(mirror, "/") ? "" : "/") + string(s, p + 1);
-}
-
-
-static int main_nix_prefetch_url(int argc, char * * argv)
-{
- {
- HashType ht = htSHA256;
- std::vector<string> args;
- bool printPath = getEnv("PRINT_PATH") == "1";
- bool fromExpr = false;
- string attrPath;
- bool unpack = false;
- bool executable = false;
- string name;
-
- struct MyArgs : LegacyArgs, MixEvalArgs
- {
- using LegacyArgs::LegacyArgs;
- };
-
- MyArgs myArgs(std::string(baseNameOf(argv[0])), [&](Strings::iterator & arg, const Strings::iterator & end) {
- if (*arg == "--help")
- showManPage("nix-prefetch-url");
- else if (*arg == "--version")
- printVersion("nix-prefetch-url");
- else if (*arg == "--type") {
- string s = getArg(*arg, arg, end);
- ht = parseHashType(s);
- }
- else if (*arg == "--print-path")
- printPath = true;
- else if (*arg == "--attr" || *arg == "-A") {
- fromExpr = true;
- attrPath = getArg(*arg, arg, end);
- }
- else if (*arg == "--unpack")
- unpack = true;
- else if (*arg == "--executable")
- executable = true;
- else if (*arg == "--name")
- name = getArg(*arg, arg, end);
- else if (*arg != "" && arg->at(0) == '-')
- return false;
- else
- args.push_back(*arg);
- return true;
- });
-
- myArgs.parseCmdline(argvToStrings(argc, argv));
-
- initPlugins();
-
- if (args.size() > 2)
- throw UsageError("too many arguments");
-
- Finally f([]() { stopProgressBar(); });
-
- if (isatty(STDERR_FILENO))
- startProgressBar();
-
- auto store = openStore();
- auto state = std::make_unique<EvalState>(myArgs.searchPath, store);
-
- Bindings & autoArgs = *myArgs.getAutoArgs(*state);
-
- /* If -A is given, get the URI from the specified Nix
- expression. */
- string uri;
- if (!fromExpr) {
- if (args.empty())
- throw UsageError("you must specify a URI");
- uri = args[0];
- } else {
- Path path = resolveExprPath(lookupFileArg(*state, args.empty() ? "." : args[0]));
- Value vRoot;
- state->evalFile(path, vRoot);
- Value & v(*findAlongAttrPath(*state, attrPath, autoArgs, vRoot).first);
- state->forceAttrs(v);
-
- /* Extract the URI. */
- auto attr = v.attrs->find(state->symbols.create("urls"));
- if (attr == v.attrs->end())
- throw Error("attribute set does not contain a 'urls' attribute");
- state->forceList(*attr->value);
- if (attr->value->listSize() < 1)
- throw Error("'urls' list is empty");
- uri = state->forceString(*attr->value->listElems()[0]);
-
- /* Extract the hash mode. */
- attr = v.attrs->find(state->symbols.create("outputHashMode"));
- if (attr == v.attrs->end())
- printInfo("warning: this does not look like a fetchurl call");
- else
- unpack = state->forceString(*attr->value) == "recursive";
-
- /* Extract the name. */
- if (name.empty()) {
- attr = v.attrs->find(state->symbols.create("name"));
- if (attr != v.attrs->end())
- name = state->forceString(*attr->value);
- }
- }
-
- /* Figure out a name in the Nix store. */
- if (name.empty())
- name = baseNameOf(uri);
- if (name.empty())
- throw Error("cannot figure out file name for '%1%'", uri);
-
- /* If an expected hash is given, the file may already exist in
- the store. */
- std::optional<Hash> expectedHash;
- Hash hash(ht);
- std::optional<StorePath> storePath;
- if (args.size() == 2) {
- expectedHash = Hash::parseAny(args[1], ht);
- const auto recursive = unpack ? FileIngestionMethod::Recursive : FileIngestionMethod::Flat;
- storePath = store->makeFixedOutputPath(recursive, *expectedHash, name);
- if (store->isValidPath(*storePath))
- hash = *expectedHash;
- else
- storePath.reset();
- }
-
- if (!storePath) {
-
- auto actualUri = resolveMirrorUri(*state, uri);
-
- AutoDelete tmpDir(createTempDir(), true);
- Path tmpFile = (Path) tmpDir + "/tmp";
-
- /* Download the file. */
- {
- 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);
-
- FdSink sink(fd.get());
-
- FileTransferRequest req(actualUri);
- req.decompress = false;
- getFileTransfer()->download(std::move(req), sink);
- }
-
- /* Optionally unpack the file. */
- if (unpack) {
- printInfo("unpacking...");
- Path unpacked = (Path) tmpDir + "/unpacked";
- createDirs(unpacked);
- unpackTarfile(tmpFile, unpacked);
-
- /* If the archive unpacks to a single file/directory, then use
- that as the top-level. */
- auto entries = readDirectory(unpacked);
- if (entries.size() == 1)
- tmpFile = unpacked + "/" + entries[0].name;
- else
- tmpFile = unpacked;
- }
-
- const auto method = unpack || executable ? FileIngestionMethod::Recursive : FileIngestionMethod::Flat;
-
- auto info = store->addToStoreSlow(name, tmpFile, method, ht, expectedHash);
- storePath = info.path;
- assert(info.ca);
- hash = getContentAddressHash(*info.ca);
- }
-
- stopProgressBar();
-
- if (!printPath)
- printInfo("path is '%s'", store->printStorePath(*storePath));
-
- std::cout << printHash16or32(hash) << std::endl;
- if (printPath)
- std::cout << store->printStorePath(*storePath) << std::endl;
-
- return 0;
- }
-}
-
-static RegisterLegacyCommand r_nix_prefetch_url("nix-prefetch-url", main_nix_prefetch_url);