Skip to content

fix(nu): create completion cache dir with mode 700 and fix home-dir lookup - #731

Merged
jdx merged 1 commit into
mainfrom
fix/nu-completion-cache-dir
Jul 20, 2026
Merged

jdx merged 1 commit into
mainfrom
fix/nu-completion-cache-dir

Conversation

@jdx

@jdx jdx commented Jul 20, 2026

Copy link
Copy Markdown
Owner

Summary

Follow-up to #727, fixing two problems in the nu completion generator's cache-dir setup — both on the same lines that PR touched. Raised (in part) by Bugbot and Greptile on that PR.

1. Cache dir was world-readable (the reported gap)

Nushell's builtin mkdir has no mode flag, so the cache dir was created at the process umask — typically 755, i.e. world-readable — whereas the bash/zsh/fish generators all use mkdir -p -m 700. The symlink-planting attack from #722 stays blocked (an attacker still can't write into ~/.cache), but other local users could read the cached specs.

Fix: create the dir, then ^chmod 0700 it, guarded to non-Windows (where POSIX perms / chmod don't apply):

if not ($spec_dir | path exists) {
    mkdir $spec_dir
    if $nu.os-info.family != "windows" { ^chmod 0700 $spec_dir }
}

The chmod runs only when the dir is first created (behind the path exists check), so it stays off the completion hot path — matching the create-time-only semantics of -m 700 in the other three shells rather than forking chmod on every Tab.

2. $nu.home-path no longer exists → completer errors on every invocation

While fixing the above I found the nu completion is currently broken on any recent nushell: $nu.home-path was renamed to $nu.home-dir in nushell 0.110.0 (Jan 2026). Because default evaluates its argument eagerly, referencing the missing column throws — even when XDG_CACHE_HOME is set and the fallback isn't needed.

Fix: optional access with a fallback that works on both new and old nushell:

let spec_dir = ($env.XDG_CACHE_HOME? | default ($nu.home-dir? | default $nu.home-path? | path join ".cache") | path join "usage")

Testing

Verified end-to-end on nushell 0.114.1:

  • The generated completion script sources cleanly (no parse error).
  • With XDG_CACHE_HOME set and via the ~/.cache fallback, the cache dir is created as drwx------ (700).
  • The spec file is written into the 700 dir (so the dir mode is what enforces confidentiality).
  • Second run: dir already exists → no chmod, no error.

Also: cargo test -p usage-lib --lib (257) passes, cargo clippy clean, cargo fmt --check clean, nu snapshots regenerated. (nushell isn't installed in CI, so its integration tests skip — hence the manual end-to-end check above.)

This PR was generated by Claude Code.


Note

Low Risk
Changes only the generated nu completion script strings and test snapshots; no runtime auth or data-path logic in the library itself.

Overview
Aligns nushell completion cache setup with bash/zsh/fish and fixes breakage on recent Nushell.

Generated completers now resolve the cache path with $nu.home-dir? falling back to $nu.home-path? (optional chaining avoids errors when XDG_CACHE_HOME is set but the old $nu.home-path column is gone). They only mkdir when the usage cache dir is missing, then run ^chmod 0700 on non-Windows so new dirs are not world-readable—matching the other shells’ mkdir -m 700 without chmod on every Tab.

Insta snapshots for the nu generator are updated to match.

Reviewed by Cursor Bugbot for commit f54f4ad. Bugbot is set up for automated code reviews on this repo. Configure here.

…ookup

Two fixes to the nu completion generator's cache-dir setup, both on the
same lines touched by #727.

1. Permissions. Nushell's builtin `mkdir` has no mode flag, so the cache
   dir was created at the process umask (typically 755 / world-readable),
   unlike the bash/zsh/fish generators which use `mkdir -p -m 700`. Cached
   specs were therefore readable by other local users. Create the dir and
   then `^chmod 0700` it (guarded to non-Windows, where chmod doesn't
   apply). The chmod runs only when the dir is first created — behind a
   `path exists` check — so it stays off the completion hot path, matching
   the create-time-only semantics of `-m 700` in the other shells.

2. home-dir lookup. `$nu.home-path` was renamed to `$nu.home-dir` in
   nushell 0.110.0 (Jan 2026). Because `default` evaluates its argument
   eagerly, referencing the missing column made the completer error out on
   every invocation on current nushell — even when XDG_CACHE_HOME was set.
   Use optional access with a fallback: `$nu.home-dir? | default
   $nu.home-path?`, which resolves on both new and old nushell and no
   longer throws.

Verified end-to-end on nushell 0.114.1: the generated completion sources
cleanly, the cache dir is created as drwx------, and the spec file is
written into it. Regenerated the nu snapshots.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
@coderabbitai

coderabbitai Bot commented Jul 20, 2026

Copy link
Copy Markdown

Warning

Review limit reached

@jdx, you've reached your PR review limit, so we couldn't start this review.

Next review available in: 10 minutes

Enable usage-based reviews in Billing to review now. Otherwise, wait until the next included review is available.
You're only billed for reviews past your plan's rate limits ($0.25/file).

How can I continue?

After more reviews become available, a review can be triggered using the @coderabbitai review command as a PR comment. Alternatively, push new commits to this PR.

To avoid repeated limits, reduce automatic review volume by pausing incremental auto-reviews earlier, using label-based review opt-in, excluding WIP or generated PR titles, or requesting reviews manually when the PR is ready. If your team needs uninterrupted high-volume reviews, an organization admin can enable usage-based reviews.

How do review limits work?

CodeRabbit enforces per-developer PR review limits for each organization. Most developers receive the normal plan review availability.

For paid Pro and Pro+ PR reviews, CodeRabbit uses adaptive limits for sustained high-volume activity. When a developer's recent PR review activity reaches the 95th percentile or higher among CodeRabbit users, additional reviews become available more gradually as earlier reviews age out of the rolling window.

Please refer docs for additional details.

Review details
⚙️ Run configuration

Configuration used: Central YAML (base), Organization UI (inherited)

Review profile: CHILL

Plan: Pro Plus

Run ID: 9629072d-bcac-4d67-a181-9bde83e7d6b6

📥 Commits

Reviewing files that changed from the base of the PR and between 1056760 and f54f4ad.

⛔ Files ignored due to path filters (3)
  • lib/src/complete/snapshots/usage__complete__nu__tests__complete_nu-2.snap is excluded by !**/*.snap
  • lib/src/complete/snapshots/usage__complete__nu__tests__complete_nu-3.snap is excluded by !**/*.snap
  • lib/src/complete/snapshots/usage__complete__nu__tests__complete_nu.snap is excluded by !**/*.snap
📒 Files selected for processing (1)
  • lib/src/complete/nu.rs

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@jdx
jdx enabled auto-merge (squash) July 20, 2026 20:27
@jdx
jdx merged commit 1c0e133 into main Jul 20, 2026
5 of 6 checks passed
@jdx
jdx deleted the fix/nu-completion-cache-dir branch July 20, 2026 20:28
@greptile-apps

greptile-apps Bot commented Jul 20, 2026

Copy link
Copy Markdown
Contributor

Greptile Summary

This PR fixes two bugs in the Nushell completion cache-dir setup: the completer was broken on nushell ≥ 0.110 because $nu.home-path was renamed to $nu.home-dir, and the cache directory was created world-readable (mode 755) instead of the 700 used by the bash/zsh/fish generators.

  • Compatibility fix: replaces $nu.home-path with $nu.home-dir? | default $nu.home-path?, using nushell's optional ? access on both sides so neither column access throws when absent — correct on both old and new nushell, and safe even when XDG_CACHE_HOME is set (where the fallback is evaluated eagerly but harmlessly returns null).
  • Permission fix: wraps mkdir in an existence check and applies ^chmod 0700 immediately after creation on non-Windows, matching the create-time-only semantics of -m 700 in the other three shell generators and keeping the chmod off the completion hot path.
  • All three insta snapshots are regenerated to match the new output.

Confidence Score: 5/5

Safe to merge — both fixes are targeted and correct, with no regressions introduced in the generated completion scripts.

The two changes are minimal and address clearly identified, reproducible bugs. The home-dir fallback chain correctly handles both nushell < 0.110 and ≥ 0.110 via optional column access with no throw risk. The chmod is properly gated behind the creation check and the Windows guard. All three snapshot variants are updated consistently, and the PR author confirmed end-to-end testing on nushell 0.114.1.

No files require special attention.

Important Files Changed

Filename Overview
lib/src/complete/nu.rs Core fix: adds ? optional field access for home-dir compatibility across nushell versions, wraps mkdir in an existence check, and adds ^chmod 0700 on non-Windows — all changes are correct and well-scoped.
lib/src/complete/snapshots/usage__complete__nu__tests__complete_nu.snap Snapshot updated to reflect the new spec_dir assignment and conditional mkdir+chmod block; matches the generated output.
lib/src/complete/snapshots/usage__complete__nu__tests__complete_nu-2.snap Snapshot (versioned cache-key variant) updated consistently with the core change.
lib/src/complete/snapshots/usage__complete__nu__tests__complete_nu-3.snap Snapshot (kitchen-sink/inline-spec variant) updated consistently with the core change.

Reviews (1): Last reviewed commit: "fix(nu): create completion cache dir wit..." | Re-trigger Greptile

jdx commented Jul 20, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented Jul 20, 2026

Copy link
Copy Markdown
✅ Action performed

Review finished.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

mise-en-dev added a commit that referenced this pull request Jul 21, 2026
### 🐛 Bug Fixes

- **(cli)** avoid trailing semicolon in macro expression position by
[@jdx](https://github.com/jdx) in
[#729](#729)
- **(completion)** write spec cache to private dir instead of
world-writable tmp by [@jdx](https://github.com/jdx) in
[#727](#727)
- **(lib)** remove needless borrows in format args by
[@jdx](https://github.com/jdx) in
[#726](#726)
- **(markdown)** preserve HTML in fenced code blocks by
[@risu729](https://github.com/risu729) in
[#720](#720)
- **(nu)** create completion cache dir with mode 700 and fix home-dir
lookup by [@jdx](https://github.com/jdx) in
[#731](#731)

### 🔍 Other Changes

- remove dtolnay/rust-toolchain action, use runner default rust by
[@jdx](https://github.com/jdx) in
[#724](#724)
- regenerate aube-lock.yaml on renovate branches by
[@jdx](https://github.com/jdx) in
[#728](#728)
- exclude aube-lock.yaml from prettier by [@jdx](https://github.com/jdx)
in [#732](#732)

### 📦️ Dependency Updates

- lock file maintenance by
[@renovate[bot]](https://github.com/renovate[bot]) in
[#723](#723)
tmeijn pushed a commit to tmeijn/dotfiles that referenced this pull request Jul 22, 2026
This MR contains the following updates:

| Package | Update | Change |
|---|---|---|
| [usage](https://github.com/jdx/usage) | patch | `3.5.5` → `3.5.6` |

MR created with the help of [el-capitano/tools/renovate-bot](https://gitlab.com/el-capitano/tools/renovate-bot).

**Proposed changes to behavior should be submitted there as MRs.**

---

### Release Notes

<details>
<summary>jdx/usage (usage)</summary>

### [`v3.5.6`](https://github.com/jdx/usage/blob/HEAD/CHANGELOG.md#356---2026-07-20)

[Compare Source](jdx/usage@v3.5.5...v3.5.6)

##### 🐛 Bug Fixes

- **(cli)** avoid trailing semicolon in macro expression position by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;729](jdx/usage#729)
- **(completion)** write spec cache to private dir instead of world-writable tmp by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;727](jdx/usage#727)
- **(lib)** remove needless borrows in format args by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;726](jdx/usage#726)
- **(markdown)** preserve HTML in fenced code blocks by [@&#8203;risu729](https://github.com/risu729) in [#&#8203;720](jdx/usage#720)
- **(nu)** create completion cache dir with mode 700 and fix home-dir lookup by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;731](jdx/usage#731)

##### 🔍 Other Changes

- remove dtolnay/rust-toolchain action, use runner default rust by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;724](jdx/usage#724)
- regenerate aube-lock.yaml on renovate branches by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;728](jdx/usage#728)
- exclude aube-lock.yaml from prettier by [@&#8203;jdx](https://github.com/jdx) in [#&#8203;732](jdx/usage#732)

##### 📦️ Dependency Updates

- lock file maintenance by [@&#8203;renovate\[bot\]](https://github.com/renovate\[bot]) in [#&#8203;723](jdx/usage#723)

</details>

---

### Configuration

📅 **Schedule**: (UTC)

- Branch creation
  - At any time (no schedule defined)
- Automerge
  - At any time (no schedule defined)

🚦 **Automerge**: Enabled.

♻ **Rebasing**: Whenever MR is behind base branch, or you tick the rebase/retry checkbox.

🔕 **Ignore**: Close this MR and you won't be reminded about this update again.

---

 - [ ] <!-- rebase-check -->If you want to rebase/retry this MR, check this box

---

This MR has been generated by [Mend Renovate](https://github.com/renovatebot/renovate).
<!--renovate-debug:eyJjcmVhdGVkSW5WZXIiOiI0My4yNzIuNiIsInVwZGF0ZWRJblZlciI6IjQzLjI3Mi42IiwidGFyZ2V0QnJhbmNoIjoibWFpbiIsImxhYmVscyI6WyJSZW5vdmF0ZSBCb3QiLCJhdXRvbWF0aW9uOmJvdC1hdXRob3JlZCIsImRlcGVuZGVuY3ktdHlwZTo6cGF0Y2giXX0=-->
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant