Skip to content
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

Use XDG dirs per spec #2135

Closed
wants to merge 8 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 3 additions & 0 deletions .cargo/config
Original file line number Diff line number Diff line change
@@ -1,2 +1,5 @@
[alias]
xtask = "run --package xtask --"

[env]
HELIX_CONFIG = { value = "./runtime/config.toml", force = true, relative = true }
15 changes: 13 additions & 2 deletions Cargo.lock

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

9 changes: 4 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -46,14 +46,13 @@ hx --grammar build
This will install the `hx` binary to `$HOME/.cargo/bin` and build tree-sitter grammars.

Helix also needs its runtime files so make sure to copy/symlink the `runtime/` directory into the
config directory (for example `~/.config/helix/runtime` on Linux/macOS, or `%AppData%/helix/runtime` on Windows).
This location can be overridden via the `HELIX_RUNTIME` environment variable.
data directory (default `$XDG_DATA_HOME/helix` on Linux/macOS, or `%AppData%/helix/` on Windows).
This location can be overridden via appropriate entries in helix config file.

Packages already solve this for you by wrapping the `hx` binary with a wrapper
that sets the variable to the install dir.

> NOTE: running via cargo also doesn't require setting explicit `HELIX_RUNTIME` path, it will automatically
> detect the `runtime` directory in the project root.
> NOTE: running via cargo also doesn't require setting explicit `HELIX_CONFIG` path, it is set for you automatically by cargo.

In order to use LSP features like auto-complete, you will need to
[install the appropriate Language Server](https://github.com/helix-editor/helix/wiki/How-to-install-the-default-language-servers)
Expand All @@ -69,7 +68,7 @@ Helix can be installed on MacOS through homebrew via:
brew tap helix-editor/helix
brew install helix
```

# Contributing

Contributing guidelines can be found [here](./docs/CONTRIBUTING.md).
Expand Down
30 changes: 29 additions & 1 deletion book/src/configuration.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@

To override global configuration parameters, create a `config.toml` file located in your config directory:

* Linux and Mac: `~/.config/helix/config.toml`
* Linux and Mac: `$XDG_CONFIG_HOME/helix/config.toml`
* Windows: `%AppData%\helix\config.toml`

> Hint: You can easily open the config file by typing `:config-open` within Helix normal mode.
Expand All @@ -23,6 +23,9 @@ select = "underline"

[editor.file-picker]
hidden = false

[paths]
log-file = "/home/user/logs/helix.log"
```

## Editor
Expand Down Expand Up @@ -136,3 +139,28 @@ Search specific options.
|--|--|---------|
| `smart-case` | Enable smart case regex searching (case insensitive unless pattern contains upper case characters) | `true` |
| `wrap-around`| Whether the search should wrap after depleting the matches | `true` |

### `[paths]` Section

Make Helix use specific files and directories. Generally there's no need
to add/edit this section since Helix will use sensible defaults for given system.

#### Linux

| Key | Description | Default |
|--|--|---------|
| `grammar-dir` | Grammars location | `$XDG_DATA_HOME/helix/grammars` |
| `language-file` | [language.toml](./languages.md) location | `$XDG_CONFIG_HOME/helix/languages.toml` |
| `log-file` | Log file location | `$XDG_STATE_HOME/helix/helix.log` |
| `query-dir` | Queries location | `$XDG_DATA_HOME/helix/queries` |
| `theme-dir` | Themes location | `$XDG_DATA_HOME/helix/themes` |

#### Windows

| Key | Description | Default |
|--|--|---------|
| `grammar-dir` | Grammars location | `%AppData%/helix/grammars` |
| `language-file` | [language.toml](./languages.md) location | `%AppData%/helix/languages.toml` |
| `log-file` | Log file location | `%AppData%/helix/helix.log` |
| `query-dir` | Queries location | `%AppData%/helix/queries` |
| `theme-dir` | Themes location | `%AppData%/helix/themes` |
4 changes: 2 additions & 2 deletions book/src/install.md
Original file line number Diff line number Diff line change
Expand Up @@ -58,8 +58,8 @@ cargo install --path helix-term
This will install the `hx` binary to `$HOME/.cargo/bin`.

Helix also needs it's runtime files so make sure to copy/symlink the `runtime/` directory into the
config directory (for example `~/.config/helix/runtime` on Linux/macOS). This location can be overriden
via the `HELIX_RUNTIME` environment variable.
data directory (for example `$XDG_DATA_HOME/helix` on Linux/macOS). This location can be overriden
via appropriate entries in helix config file.

## Building tree-sitter grammars

Expand Down
30 changes: 30 additions & 0 deletions helix-core/src/syntax.rs
Original file line number Diff line number Diff line change
Expand Up @@ -1962,8 +1962,34 @@ mod test {
use super::*;
use crate::{Rope, Transaction};

fn setup() {
use std::sync::Once;
// mirror struct for helix_term's Config
// original can't be used because it's not built yet
#[derive(Deserialize)]
struct BuildConfig {
paths: helix_loader::Paths,
}

static SETUP: Once = Once::new();
SETUP.call_once(|| {
// config.toml is written relative to workspace root, cd there
assert!(std::env::set_current_dir("..").is_ok());

let config = std::env::var("HELIX_CONFIG").unwrap();
let config = std::fs::read_to_string(config).unwrap();
let paths = toml::from_str::<BuildConfig>(&config).unwrap().paths;
helix_loader::init_paths(paths).unwrap();

// cd back, don't interfere with other tests
assert!(std::env::set_current_dir("./helix-core").is_ok());
});
}

#[test]
fn test_textobject_queries() {
setup();

let query_str = r#"
(line_comment)+ @quantified_nodes
((line_comment)+) @quantified_nodes_grouped
Expand Down Expand Up @@ -2010,6 +2036,8 @@ mod test {

#[test]
fn test_parser() {
setup();

let highlight_names: Vec<String> = [
"attribute",
"constant",
Expand Down Expand Up @@ -2130,6 +2158,8 @@ mod test {

#[test]
fn test_load_runtime_file() {
setup();

// Test to make sure we can load some data from the runtime directory.
let contents = load_runtime_file("rust", "indents.scm").unwrap();
assert!(!contents.is_empty());
Expand Down
27 changes: 27 additions & 0 deletions helix-core/tests/indent.rs
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,39 @@ use helix_core::{
};
use std::path::PathBuf;

fn setup() {
use std::sync::Once;

// mirror struct for helix_term's Config
// original can't be used because it's not built yet
#[derive(serde::Deserialize)]
struct BuildConfig {
paths: helix_loader::Paths,
}
static SETUP: Once = Once::new();

SETUP.call_once(|| {
// config.toml is written relative to workspace root, cd there
std::env::set_current_dir("..").unwrap();

let config = std::env::var("HELIX_CONFIG").unwrap();
let config = std::fs::read_to_string(config).unwrap();
let paths = toml::from_str::<BuildConfig>(&config).unwrap().paths;
helix_loader::init_paths(paths).unwrap();

// cd back, don't interfere with other tests
std::env::set_current_dir("./helix-core").unwrap();
});
}

#[test]
fn test_treesitter_indent_rust() {
setup();
test_treesitter_indent("rust.rs", "source.rust");
}
#[test]
fn test_treesitter_indent_rust_2() {
setup();
test_treesitter_indent("indent.rs", "source.rust");
// TODO Use commands.rs as indentation test.
// Currently this fails because we can't align the parameters of a closure yet
Expand Down
2 changes: 1 addition & 1 deletion helix-loader/Cargo.toml
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,9 @@ homepage = "https://helix-editor.com"

[dependencies]
anyhow = "1"
etcetera = "0.4"
serde = { version = "1.0", features = ["derive"] }
toml = "0.5"
etcetera = "0.3"
tree-sitter = "0.20"
libloading = "0.7"
once_cell = "1.9"
Expand Down
15 changes: 5 additions & 10 deletions helix-loader/src/grammar.rs
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ const REMOTE_NAME: &str = "origin";

pub fn get_language(name: &str) -> Result<Language> {
let name = name.to_ascii_lowercase();
let mut library_path = crate::runtime_dir().join("grammars").join(&name);
let mut library_path = crate::grammar_dir().join(&name);
library_path.set_extension(DYLIB_EXTENSION);

let library = unsafe { Library::new(&library_path) }
Expand Down Expand Up @@ -142,8 +142,7 @@ fn fetch_grammar(grammar: GrammarConfiguration) -> Result<()> {
remote, revision, ..
} = grammar.source
{
let grammar_dir = crate::runtime_dir()
.join("grammars")
let grammar_dir = crate::grammar_dir()
.join("sources")
.join(&grammar.grammar_id);

Expand Down Expand Up @@ -233,8 +232,7 @@ fn build_grammar(grammar: GrammarConfiguration) -> Result<()> {
let grammar_dir = if let GrammarSource::Local { path } = &grammar.source {
PathBuf::from(&path)
} else {
crate::runtime_dir()
.join("grammars")
crate::grammar_dir()
.join("sources")
.join(&grammar.grammar_id)
};
Expand Down Expand Up @@ -280,7 +278,7 @@ fn build_tree_sitter_library(src_path: &Path, grammar: GrammarConfiguration) ->
None
}
};
let parser_lib_path = crate::runtime_dir().join("grammars");
let parser_lib_path = crate::grammar_dir();
let mut library_path = parser_lib_path.join(&grammar.grammar_id);
library_path.set_extension(DYLIB_EXTENSION);

Expand Down Expand Up @@ -385,9 +383,6 @@ fn mtime(path: &Path) -> Result<SystemTime> {
/// Gives the contents of a file from a language's `runtime/queries/<lang>`
/// directory
pub fn load_runtime_file(language: &str, filename: &str) -> Result<String, std::io::Error> {
let path = crate::RUNTIME_DIR
.join("queries")
.join(language)
.join(filename);
let path = crate::query_dir().join(language).join(filename);
std::fs::read_to_string(&path)
}
Loading