Commit graph

5350 commits

Author SHA1 Message Date
Yuya Nishihara
adcb01ef95 index: move RevWalk tests to inner module
The main tests module is getting bigger, and these tests are very specific
to the RevWalk* implementations.
2024-02-19 00:54:43 +09:00
Yuya Nishihara
924a5fc842 index: inline entry size calculation
There aren't many callers now, and using self.commit_id_length might help
compiler remove redundant bounds checking in CommitLookupEntry.
2024-02-19 00:47:46 +09:00
Yuya Nishihara
d5c75da4f5 index: precompute base data offsets
These offsets are getting messier, so let's calculate them in one place. This
will probably help compiler optimization.
2024-02-19 00:47:46 +09:00
Yuya Nishihara
3c7aa75b9b index: switch to persistent change id index
The shortest change id prefix will become a few digits longer, but I think
that's acceptable. Entries included in the "revsets.short-prefixes" set are
unaffected.

The reachable set is calculated eagerly, but this is still faster as we no
longer need to sort the reachable entries by change id. The lazy version will
save another ~100ms in mid-size repos.

"jj log" without working copy snapshot:
```
% hyperfine --sort command --warmup 3 --runs 20 -L bin jj-0,jj-1,jj-2 \
  -s "target/release-with-debug/{bin} -R ~/mirrors/linux debug reindex" \
  "target/release-with-debug/{bin} -R ~/mirrors/linux \
   --ignore-working-copy log -r.. -l100 --config-toml='revsets.short-prefixes=\"\"'"
Benchmark 1: target/release-with-debug/jj-0 -R ~/mirrors/linux --ignore-working-copy log -r.. -l100 --config-toml='revsets.short-prefixes=""'
  Time (mean ± σ):     353.6 ms ±  11.9 ms    [User: 266.7 ms, System: 87.0 ms]
  Range (min … max):   329.0 ms … 365.6 ms    20 runs

Benchmark 2: target/release-with-debug/jj-1 -R ~/mirrors/linux --ignore-working-copy log -r.. -l100 --config-toml='revsets.short-prefixes=""'
  Time (mean ± σ):     271.3 ms ±   9.9 ms    [User: 183.8 ms, System: 87.7 ms]
  Range (min … max):   250.5 ms … 282.7 ms    20 runs

Relative speed comparison
        1.99 ±  0.16  target/release-with-debug/jj-0 -R ~/mirrors/linux --ignore-working-copy log -r.. -l100 --config-toml='revsets.short-prefixes=""'
        1.53 ±  0.12  target/release-with-debug/jj-1 -R ~/mirrors/linux --ignore-working-copy log -r.. -l100 --config-toml='revsets.short-prefixes=""'
```

"jj status" with working copy snapshot (watchman enabled):
```
% hyperfine --sort command --warmup 3 --runs 20 -L bin jj-0,jj-1,jj-2 \
  -s "target/release-with-debug/{bin} -R ~/mirrors/linux debug reindex" \
  "target/release-with-debug/{bin} -R ~/mirrors/linux \
   status --config-toml='revsets.short-prefixes=\"\"'"
Benchmark 1: target/release-with-debug/jj-0 -R ~/mirrors/linux status --config-toml='revsets.short-prefixes=""'
  Time (mean ± σ):     396.6 ms ±  10.1 ms    [User: 300.7 ms, System: 94.0 ms]
  Range (min … max):   373.6 ms … 408.0 ms    20 runs

Benchmark 2: target/release-with-debug/jj-1 -R ~/mirrors/linux status --config-toml='revsets.short-prefixes=""'
  Time (mean ± σ):     318.6 ms ±  12.6 ms    [User: 219.1 ms, System: 94.1 ms]
  Range (min … max):   294.2 ms … 333.0 ms    20 runs

Relative speed comparison
        1.85 ±  0.14  target/release-with-debug/jj-0 -R ~/mirrors/linux status --config-toml='revsets.short-prefixes=""'
        1.48 ±  0.12  target/release-with-debug/jj-1 -R ~/mirrors/linux status --config-toml='revsets.short-prefixes=""'
```
2024-02-18 09:44:57 +09:00
Yuya Nishihara
5f3a31300b index: implement index-level change id lookup methods
These methods are basically the same as the commit_id versions, but
resolve_change_id_prefix() is a bit more involved as we need to gather matches
from multiple segments.
2024-02-18 09:44:57 +09:00
Yuya Nishihara
f73e590837 index: implement segment-level change id lookup methods
In resolve_change_id_prefix(), I've implemented two different ways of
collecting the overflow items. I don't think they impact the performance,
but we can switch to the alternative method as needed.
2024-02-18 09:44:57 +09:00
Yuya Nishihara
8cdf6d752c index: move change ids to sstable, build change-id-to-pos lookup table
This basically means that the change ids are interned. We'll implement binary
search over the sorted change ids table. The table could be sorted differently
for better cache locality, but it is in lexicographical order for simplicity.
With my testing, the cost of the id lookup isn't dominant.

Unlike the parent entries, the size of the per-id overflow items isn't saved.
That's s because the number of the same-change-id commits is either 1 or many.
It doesn't make sense to allocate 8 bytes for each change id. Instead, we'll
pay extra indirection cost to determine the size.
2024-02-18 09:44:57 +09:00
Yuya Nishihara
9974a46327 index: clarify parent entries are global positions
I'm going to add change id overflow table whose elements are of LocalPosition
type. Let's make sure that the serialization code would break if we changed
the underlying data type.
2024-02-18 09:44:57 +09:00
Alexis (Poliorcetics) Bourget
fb10e3f296 completion: Update docs for new style with positional argument 2024-02-17 19:26:30 +01:00
Martin von Zweigbergk
866e862ab0 cli: make new workspace inherit sparse pattern from old workspace 2024-02-17 10:17:38 -08:00
Martin von Zweigbergk
6d7affc4da cli: add test of workspaces with sparse patterns
When adding a new workspace, I would expect that it inherits the
patterns from the workspace I ran the command in. We currently don't
do that. That's quite annoying when your repo has very many files
(like at Google).
2024-02-17 10:17:38 -08:00
Aleksey Kuznetsov
89cf6a00a1 graphlog: refactor graphlog::Edge enum and its usage
`graphlog::Edge` is used somewhat inconsistently. I've replaced `Edge::Present`
with two distinct `Edge::Direct` and `Edge::Indirect` which simplifies the
construction of the enum.
2024-02-17 20:54:20 +05:00
Thomas Castiglione
aaa5d6bc4f working_copy: add Send supertrait
If WorkingCopy: Send, then Workspace is Send, which is useful for long-running
servers. All existing impls are Send already, so this is just a marker.
2024-02-17 15:13:25 +08:00
Yuya Nishihara
5eea88d26a tests: fix concurrent git read/write test to retry on ref lock contention
Apparently, gix has 100ms timeout. Since this test tries to create contended
situation, it's possible that the ref lock can't be acquired. I've added
upper bound to the retry loop at b37293fa68 "tests: add upper bound to
test_concurrent_read_write_commit() loop", so ignoring arbitrary errors
should be okay.

The problem can be reproduced on my Linux machine by inserting 10ms sleep() to
gix and increasing the concurrency.

Fixes #3069
2024-02-17 15:09:27 +09:00
Yuya Nishihara
ce295f8bc2 op_store: remove unneeded repr(u8) from RemoteRefState
It no longer makes sense after e1fd402d39 "Fix the ContentHash implementations
for std::Option, MergedTreeId, and RemoteRefState."
2024-02-17 02:13:44 +09:00
dependabot[bot]
1b3dae346a cargo: bump the cargo-dependencies group with 1 update
Bumps the cargo-dependencies group with 1 update: [clap](https://github.com/clap-rs/clap).


Updates `clap` from 4.5.0 to 4.5.1
- [Release notes](https://github.com/clap-rs/clap/releases)
- [Changelog](https://github.com/clap-rs/clap/blob/master/CHANGELOG.md)
- [Commits](https://github.com/clap-rs/clap/compare/clap_complete-v4.5.0...v4.5.1)

---
updated-dependencies:
- dependency-name: clap
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: cargo-dependencies
...

Signed-off-by: dependabot[bot] <support@github.com>
2024-02-16 10:47:07 -06:00
Yuya Nishihara
718d080e7a index: make reindexing message less scary 2024-02-17 01:45:23 +09:00
Evan Mesterhazy
a80d0183a2 Implement ContentHash for u32 and u64
This is for completeness and to avoid accidents such as someone calling
`ContentHash::hash(1234u32.to_le_bytes())` and expecting it to hash properly as
a u32 instead of a 4 byte slice, which produces a different hash due to hashing
the length of the slice before its contents.
2024-02-16 10:23:39 -05:00
Evan Mesterhazy
e1fd402d39 Fix the ContentHash implementations for std::Option, MergedTreeId, and RemoteRefState
The `ContentHash` documentation specifies that implementations for enums should
hash the ordinal number of the variant contained in the enum as a 32-bit
little-endian number and then hash the contents of the variant, if any.

The current implementations for `std::Option`, `MergedTreeId`, and
`RemoteRefState` are non-conformant since they hash the ordinal number as a u8
with platform specific endianness.


Fixes #3051
2024-02-16 09:27:32 -05:00
Yuya Nishihara
903f18acfd index: extract helper functions for id lookup in mutable table
Similar to the previous commit, these functions will be reused by the change id
lookup methods. The return value isn't cloned because resolve_id_prefix() will
return (key, value) pair, and the current caller doesn't need a cloned value.
2024-02-16 11:12:53 +09:00
Yuya Nishihara
000cb41c7e index: extract helper struct for post processing binary search result
This code will be shared among commit id and change id lookup functions.
2024-02-16 11:12:53 +09:00
Yuya Nishihara
6fa660d9a8 index: extract inner binary search function
The callback returns Ordering instead of &[u8] due to lifetime difficulty.
2024-02-16 11:12:53 +09:00
Yuya Nishihara
5b9f422d1d cli: change workspace@ symbol color to green (the color of HEAD@git)
I think it makes sense because workspace@ is similar to HEAD@git. They are
symbols that aren't branches nor tags.
2024-02-16 11:12:43 +09:00
Evan Mesterhazy
a9278f50b1 Compile insta and similar in opt mode for faster testing
This is recommended by the insta documentation.
See: https://docs.rs/insta/latest/insta/#optional-faster-runs.

Running on an M1 MacBook Pro

Before:
```
________________________________________________________
Executed in   31.10 secs    fish           external
   usr time  118.87 secs  107.00 micros  118.87 secs
   sys time   46.19 secs  847.00 micros   46.19 secs
```

After:
```
________________________________________________________
Executed in   29.73 secs    fish           external
   usr time  119.58 secs    0.13 millis  119.58 secs
   sys time   46.27 secs    1.74 millis   46.27 secs
```

This doesn't seem like a huge change, and there's noise in the measurements,
but I don't think it can hurt and insta recommends it.
2024-02-15 14:07:19 -05:00
Philip Metzger
e9fc8d4e40 Readme: Add a related media section and tidy up the news a bit.
This bundles all Jujutsu related media (the talk, its slides and the three articles we were featured in) 
into a section.

Also update the news section to mention the recent deprecations and the three articles we recently 
were featured in. 

Thanks to everyone who wrote one.
2024-02-15 20:04:37 +01:00
Yuya Nishihara
2e64bf83fd index: pass bytes prefix to binary search function
This helps extract common binary search helper to be used by change id index.
2024-02-14 23:34:47 +09:00
Yuya Nishihara
91a68b950d index: adjust binary search function to conform to std behavior
This removes redundant case from resolve_neighbor_commit_ids(). The returned
position should never be lower than the prefix id.

The implementation is basically a copy of slice::binary_search_by(). We still
use (low + high) / 2 as the size wouldn't exceed 2^31.

https://github.com/rust-lang/rust/blob/1.76.0/library/core/src/slice/mod.rs#L2825
2024-02-14 23:34:47 +09:00
Yuya Nishihara
e2c8a8fabd index: fix change id resolution test to not depend on deterministic order
Since IdIndex sorts the entries by using .sort_unstable_by_key(), the order of
the same-key elements is undefined. Perhaps, it's stable for short arrays, and
the test passes because of that.
2024-02-14 23:22:23 +09:00
Yuya Nishihara
8b1dfa7157 index: compact parent encoding, inline up to two parents
This saves 4 more bytes per entry, and more importantly, most commit parents
can be resolved with no indirection to the overflow table.

IIRC, Git always inlines the first parent, but that wouldn't be useful in jj
since jj diffs merge commit against the auto-merge parent. The first merge
parent is nothing special.

I'll use a similar encoding in change id sstable, where only one position
will be inlined (to optimize for imported commits.)

Benchmark number measuring the cost of change id index building:
```
% hyperfine --sort command --warmup 3 --runs 20 -L bin jj-0,jj-1 \
  -s "target/release-with-debug/{bin} -R ~/mirrors/linux \
      --ignore-working-copy debug reindex" \
  "target/release-with-debug/{bin} -R ~/mirrors/linux \
    --ignore-working-copy log -r@ --config-toml='revsets.short-prefixes=\"\"'"
Benchmark 1: target/release-with-debug/jj-0 -R ~/mirrors/linux --ignore-working-copy log -r@ --config-toml='revsets.short-prefixes=""'
  Time (mean ± σ):     342.9 ms ±  14.5 ms    [User: 202.4 ms, System: 140.6 ms]
  Range (min … max):   326.6 ms … 360.6 ms    20 runs

Benchmark 2: target/release-with-debug/jj-1 -R ~/mirrors/linux --ignore-working-copy log -r@ --config-toml='revsets.short-prefixes=""'
  Time (mean ± σ):     325.0 ms ±  13.6 ms    [User: 196.2 ms, System: 128.8 ms]
  Range (min … max):   311.6 ms … 343.2 ms    20 runs

Relative speed comparison
        1.06 ±  0.06  target/release-with-debug/jj-0 -R ~/mirrors/linux --ignore-working-copy log -r@ --config-toml='revsets.short-prefixes=""'
        1.00          target/release-with-debug/jj-1 -R ~/mirrors/linux --ignore-working-copy log -r@ --config-toml='revsets.short-prefixes=""'
```
2024-02-14 22:33:48 +09:00
Yuya Nishihara
89928ffdd8 index: remove local-global pos round trip from entry_by_id() 2024-02-14 22:33:48 +09:00
Yuya Nishihara
249449ff1a index: store local position in lookup table 2024-02-14 22:33:48 +09:00
Yuya Nishihara
1d11cffcfa index: use local position in segment-local operations
I'm going to change the index format to store local positions in the lookup
table. That's not super important, but I think it makes sense because the
lookup table should never contain inter-segment links.

The mutable segment now stores local positions in its lookup map. The readonly
segment will be updated later.
2024-02-14 22:33:48 +09:00
Yuya Nishihara
3e43108abb index: remove unused flag field from readonly index segment
This is remainder of fdb861b957 "backend: remove unused Commit::is_pruned."
As I'm going to change the index format, let's remove unused fields, too.
2024-02-14 22:33:48 +09:00
Yuya Nishihara
26528091e6 revset: drop now unused is_legacy flag from dag ranges 2024-02-14 10:04:56 +09:00
Yuya Nishihara
815670a4ad revset: add parsing rule and expression node dedicated for kind:"pattern"
This unblocks removal of 'is_legacy: bool' fields.

Note that all legacy dag range expressions can't be accepted by the new grammar.
For example, 'x:y()' is parsed as ('x:y', error) because 'x:y' is a valid string
pattern expression, and '(' isn't an infix operator. The old compat_dag_range_op
is NOT removed as it can still translate 'x():y' or 'x:(y)' to a better error,
and we might make the string pattern syntax stricter #2101.
2024-02-14 10:04:56 +09:00
Yuya Nishihara
c73a092759 cli: drop handling of legacy revset dag range operator
This basically reverts the change c183b94aef "cli: warn when using `:` revset
operator."
2024-02-14 10:04:56 +09:00
Yuya Nishihara
815437598f revset: disable parsing rules of legacy dag range operator
The legacy parsing rules are turned into compatibility errors. The x:y rule
is temporarily enabled when parsing string patterns. It's weird, but we can't
isolate the parsing function because a string pattern may be defined in an
alias.
2024-02-14 10:04:56 +09:00
Yuya Nishihara
2905a70b18 doc, tests: drop use of deprecated revset dag range operator 2024-02-14 10:04:56 +09:00
dependabot[bot]
3500cd84ed github: bump the github-dependencies group with 1 update
Bumps the github-dependencies group with 1 update: [EmbarkStudios/cargo-deny-action](https://github.com/embarkstudios/cargo-deny-action).


Updates `EmbarkStudios/cargo-deny-action` from 1.5.13 to 1.5.15
- [Release notes](https://github.com/embarkstudios/cargo-deny-action/releases)
- [Commits](5def368d93...68cd9c5e3e)

---
updated-dependencies:
- dependency-name: EmbarkStudios/cargo-deny-action
  dependency-type: direct:production
  update-type: version-update:semver-patch
  dependency-group: github-dependencies
...

Signed-off-by: dependabot[bot] <support@github.com>
2024-02-13 17:15:18 +00:00
Martin von Zweigbergk
27017914e2 log: optionally render elided parts of the graph as a synthetic node
This adds a config to render a synthetic node with a "(elided
revisions)" description for elided segments of the graph.

I didn't add any templating support for the elided nodes because I'm
not sure how we would want that to work. In particular, I don't know
what `commit_id` and most other keywords should return for elided
revisions.
2024-02-12 17:33:55 -08:00
Martin von Zweigbergk
6ad49d232e cli: drop support for legacy graph style
I don't think anyone uses the legacy graph style. It's very similar to
the "ascii" style from Sapling's `renderdag` crate.
2024-02-12 17:33:55 -08:00
Martin von Zweigbergk
578c1097d6 cli: fix a few references to "legacy" as default graph style
The "curved" style has been the default for a long time now.
2024-02-12 17:33:55 -08:00
Benjamin Brittain
d3699c2327 Use minus as a builtin pager 2024-02-12 18:55:15 -05:00
Martin von Zweigbergk
af8eb3fd74 next/prev: make --edit implied when already on non-head commit
Users who edit non-head commits usually expect `jj next/prev` to
continue to edit the next/previous commit, so let's make that the
default behavior. This should not confuse users who don't edit
non-head commits since they will simply not be in this state. My main
concern is that doing `jj next; jj prev` will now usually take you
back to the previous commit, but not if you started on the parent of a
head commit.
2024-02-12 10:42:26 -08:00
Martin von Zweigbergk
3b075f1487 next/prev: move current_short variable closer to first use 2024-02-12 10:42:26 -08:00
Ilya Grigoriev
44e1d4a72d docs: fix a bug with offline docs generation
This is a rather annoying bug. It was revealed because CLI reference stopped
working for *offline* docs after the previous commit. Turns out, none of the
plugins we enabled for normal docs were turned on in `mkdocs-offline.yml`.

Thanks to @mondeja for figuring out what was going on.

In the future, we could try a less ugly fix, e.g. turning the `offline` plugin
on or off via an environment variable.

See also:
https://github.com/squidfunk/mkdocs-material/issues/6749
https://github.com/mondeja/mkdocs-include-markdown-plugin/issues/195#issuecomment-1933085478
2024-02-12 10:28:09 -08:00
Ilya Grigoriev
16ec185795 docs, CLI reference: use include-markdown instead of a symlink
The main goal is to avoid having a symlink in our source tree. Currently, there
is no good way to work with the `jj` repo with `jj` on Windows.  Currently `jj`
just crashes with symlinks. This is being worked on, see e.g. #2939, but it will
always depend on whether Developer Mode is enabled in Windows or whether
symlinks are materialized as text files with symlinks. Finally, MkDocs has
trouble following symlinks on Windows, so building docs wouldn't work there.

Another advantage is that, previously, we were lucky that MkDocs treats `insta`
header in `cli-reference@.md.snap` as a Markdown header and follows symlinks at
all. Now, we no longer depend on that.
2024-02-12 10:28:09 -08:00
Ilya Grigoriev
48d839694e poetry: update dependencies in poetry.lock
Marching along with the times...
2024-02-12 10:28:09 -08:00
Ilya Grigoriev
b170988a46 poetry: add the include-markdown MkDocs plugin 2024-02-12 10:28:09 -08:00
Martin von Zweigbergk
7c5cfa7cc7 templater: add a local() method on Timestamps (#2900) 2024-02-12 10:22:24 -08:00