-
Notifications
You must be signed in to change notification settings - Fork 98
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Package management CLI, part 1 #2146
Conversation
|
Branch | npm-without-index |
Testbed | ubuntu-latest |
Click to view all benchmark results
Benchmark | Latency | microseconds (µs) |
---|---|---|
fibonacci 10 | 📈 view plot 🚷 view threshold | 396.97 |
foldl arrays 50 | 📈 view plot 🚷 view threshold | 1,560.70 |
foldl arrays 500 | 📈 view plot 🚷 view threshold | 5,897.50 |
foldr strings 50 | 📈 view plot 🚷 view threshold | 5,893.60 |
foldr strings 500 | 📈 view plot 🚷 view threshold | 51,366.00 |
generate normal 250 | 📈 view plot 🚷 view threshold | 45,770.00 |
generate normal 50 | 📈 view plot 🚷 view threshold | 1,907.50 |
generate normal unchecked 1000 | 📈 view plot 🚷 view threshold | 2,778.40 |
generate normal unchecked 200 | 📈 view plot 🚷 view threshold | 665.95 |
pidigits 100 | 📈 view plot 🚷 view threshold | 2,780.90 |
pipe normal 20 | 📈 view plot 🚷 view threshold | 1,285.40 |
pipe normal 200 | 📈 view plot 🚷 view threshold | 8,566.40 |
product 30 | 📈 view plot 🚷 view threshold | 751.43 |
scalar 10 | 📈 view plot 🚷 view threshold | 1,318.00 |
sum 30 | 📈 view plot 🚷 view threshold | 750.19 |
ca59874
to
19b1cb1
Compare
I haven't added a progress bar to the git downloads, but I think this is ready for a first look. This does auto-updating of the lock-file, like cargo but unlike npm. I haven't yet implemented re-using the standard library across evaluation of multiple manifests, but I think it shouldn't be too hard (certainly easier than the general case of #2140 where you want to re-use work across nickel invocations). |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Just a partial review for now. Note to self: next item on the stack is package/src/lib.rs
.
cli/src/package.rs
Outdated
Lock { | ||
/// The path at which to write the lock file. | ||
/// | ||
/// Defaults to the filename `package.ncl.lock` in the same directory |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's a detail, but I think usually package managers don't keep the .ncl
equivalent in the lock file: flake.nix
-> flake.lock
, Cargo.toml
-> Cargo.lock
, Pipefile
-> Pipefile.lock
, foo_bar.gemspec
-> Gemfile.lock
, etc.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Right, but I was worried about colliding with npm's (the other npm 😉) package.lock
. Maybe it's better to avoid a collision by having a more nickel-specific name than "package", though...
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I see. Yes, maybe having a more specific name than "package" could be helpful in general, if only there are projects with both an NPM manifest an a Nickel manifest (or even imagine that you handle everything with Nickel, so you would like to write your "package.json" as a "package.ncl" instead and generate it).
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Ok, I realized while fiddling with the website that actually npm uses "package-lock.json", not "package.lock". So there would be no conflict to go with "package.lock", but maybe a more distinctive name is better anyway. What do you think about Nickel.ncl
/Nickel.lock
? Or Nickelfile.ncl
/Nickelfile.lock
?
package/Cargo.toml
Outdated
[package] | ||
name = "nickel-lang-package" | ||
description = "The Nickel Package Manager (npm)" | ||
version = "0.1.0" |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It's not very important for this PR, but I wonder if we shouldn't make it target either nickel-lang-core
or the Nickel version (nickel-lang-cli
) (probably the latter, since it does provide new CLI commands), to avoid the proliferation of uncorrelated versions. On the other hand, this removes the possibility of updating those crates independently.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it makes some sense to have the version in sync with nickel-lang-cli
. It does require a little bit of manual intervention to keep them in sync: I can put version.workspace = true
in package/Cargo.toml
, but I need to repeat the "1.9.0" in the workspace's dependencies list.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The release scripts is capable of handling that (we already do it for other crates like NLS). Though we should update the script as part of this PR, to make sure everything is consistent.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Right, but none of the other non-"independent" crates are a dependency of other crates in the workspace. Naively adding package
to the list of crates gives
-- Updating cross-dependencies...
-- Patching cross-dependency lsp-harness in ./Cargo.toml to version 0.1.0
-- Patching cross-dependency nickel-lang-core in ./Cargo.toml to version 0.11.0
-- Patching cross-dependency nickel-lang-package in ./Cargo.toml to version {
"workspace": true
}
sed: -e expression #1, char 87: unterminated `s' command
++ Unexpected exit. Cleaning up...
(Also, I guess we should add git
and vector
)
8fdcef9
to
32a68a0
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I can't pretend I followed all the details, but it looks good after a pass. The extensive tests are also great and reassuring. I just wonder if all the tests using git
commands explicitly wouldn't break tests on Windows ?
if self.id == 0 { | ||
write!(f, "{}", self.name) | ||
} else { | ||
write!(f, "{} {}", self.name, self.id) |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Naive question: is it possible that a package name has a space in the name?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can't use such a package because the import syntax for packages requires the package name to be an identifier ("identifier" in the sense of the nickel lexer). But it's a good point, nickel_lang_package
should check this.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've added this check to std.package.Manifest
|
||
// The rust stdlib doesn't have anything for recursively copying a directory. There are | ||
// some crates for that, but it's easier just to shell out. | ||
run(Command::new("cp") |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Wouldn't that break the CI on Windows?
Enables package management for git and path packages, when the package-experimental feature is enabled. Co-authored-by: Yann Hamdaoui <[email protected]>
3196a84
to
d4f86e2
Compare
Ok, I think the main outstanding thing is to settle on a name for the manifest and lock files. I'm pretty sure the windows CI is working ok with |
in | ||
let | ||
semver_req_re = "(%{partial_semver_re})|(%{semver_equals_req_re})", | ||
IdentKeys = |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Should we expose IdentKeys
as well? While it feels like a small self-explanatory contract, exposing it makes it discoverable, re-usable, and queri-able (if we add documentation). Though it also makes it part of the backward-compatibility. So I don't have a strong opinion either way.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I've been playing with json schema lately, and it seems pretty common to have a dict with a regex for the key names. What if we exposed, say, std.record.KeysMatch
which could get used like
{
foo = 1
} | std.record.KeysMatch "^[a-z]+*"
(basically, I'm worried that IdentKeys
is a bit too specific to be worth making public)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, I even think CUE provide built-in syntax for that. Nitpick: should we use FieldMatches
instead to follow Nickel's jargon? Although the issue with field is that it designates both the content and the name. Could use FieldNameMatches
, but it's longer. That being said, we have std.record.fields
which return field names, so FieldMatches
might be reasonable.
Fair for IdentKeys
, we can keep it local for now.
I see, this makes our life simpler (it was just a random thought - I haven't used Windows in ages so I wondered if the CLI argument syntax was different, I remember using As per the bikeshedding for the file name:
Maybe something with both |
|
I initially didn't like the inconsistency of upper casing this specific file but I think their rationale makes sense. Let's start with |
This is the first part of the package manager CLI, hidden behind a "experimental-package" feature flag. It initially supports only git and path dependencies.