feat: Users can now choose where to load grammars/queries from.

This commit is contained in:
Spencer Brower
2026-07-24 15:59:22 -04:00
parent 961b3f41b0
commit 1992349520
4 changed files with 33 additions and 9 deletions
+2
View File
@@ -6,6 +6,7 @@
- [ ] `render_template` should accept `Template_Context`, not `any` - [ ] `render_template` should accept `Template_Context`, not `any`
- [ ] Load grammars dynamically - [ ] Load grammars dynamically
- [ ] consider adding a limit to the context stack in mustache. - [ ] consider adding a limit to the context stack in mustache.
- [ ] better diagnostics for syntax errors in treesitter.
## Performance ## Performance
@@ -51,6 +52,7 @@
- want rust style diagnostic and better message, maybe "unknown timezone 'America/New_Yorkskie'" - want rust style diagnostic and better message, maybe "unknown timezone 'America/New_Yorkskie'"
## General ## General
- [ ] get rid of the global variables in the `treesitter` package.
- [ ] Integrity hash - [ ] Integrity hash
- Allows users to verify their output didn't change after upgrading to a new version - Allows users to verify their output didn't change after upgrading to a new version
- [ ] Content-hash fingerprinting for CSS and JS cache busting - [ ] Content-hash fingerprinting for CSS and JS cache busting
+5
View File
@@ -7,6 +7,8 @@ import "core:prof/spall"
import "core:sync" import "core:sync"
import "core:time" import "core:time"
import "treesitter"
SPALL :: #config(SPALL, false) SPALL :: #config(SPALL, false)
when SPALL { when SPALL {
@@ -48,6 +50,9 @@ main :: proc() {
context.allocator = site_allocator(&site) context.allocator = site_allocator(&site)
build_vfs(&site) build_vfs(&site)
treesitter.grammar_dir = site.grammars
treesitter.query_dir = site.queries
site_load_content(&site) site_load_content(&site)
render_site(&site) render_site(&site)
log.infof("Built site in %s", time.tick_since(tick)) log.infof("Built site in %s", time.tick_since(tick))
+17
View File
@@ -33,6 +33,8 @@ Site :: struct {
og: Open_Graph, og: Open_Graph,
date: Date_Preferences, date: Date_Preferences,
tz: ^datetime.TZ_Region, tz: ^datetime.TZ_Region,
grammars: string,
queries: string,
} }
Date_Preferences :: struct { Date_Preferences :: struct {
@@ -61,6 +63,8 @@ Config_File :: struct {
modules: json.Value, modules: json.Value,
og: Open_Graph, og: Open_Graph,
date: Date_Preferences, date: Date_Preferences,
grammars: string,
queries: string,
} }
// Configuration loaded from command line arguments. Gets folded in to Site // Configuration loaded from command line arguments. Gets folded in to Site
@@ -188,6 +192,19 @@ site_apply_config :: proc(site: ^Site, config: Config_File, config_dir: string)
site.og = config.og site.og = config.og
site.date = config.date site.date = config.date
site.grammars = expand_path(config.grammars, site_allocator(site))
site.queries = expand_path(config.queries, site_allocator(site))
}
// expand_path replaces a leading ~/ with $HOME/.
expand_path :: proc(path: string, allocator := context.allocator) -> string {
if len(path) >= 2 && path[0] == '~' && path[1] == '/' {
if home := os.get_env_alloc("HOME", allocator); home != "" {
return fmt.aprintf("%s%s", home, path[1:])
}
}
return strings.clone(path, allocator)
} }
site_apply_path_defaults :: proc(site: ^Site, config_dir: string) { site_apply_path_defaults :: proc(site: ^Site, config_dir: string) {
+9 -9
View File
@@ -6,8 +6,8 @@ import "core:log"
import "core:os" import "core:os"
import "core:strings" import "core:strings"
GRAPHS_PATH: string = "/home/spencer/.config/helix/runtime/grammars" grammar_dir: string
QUERIES_PATH: string = "/nix/store/n9da8d007ygbgsx983jr3ar3wb1fsh6q-helix-25.07.1/lib/runtime/queries" query_dir: string
Language :: distinct rawptr Language :: distinct rawptr
Parser :: distinct rawptr Parser :: distinct rawptr
@@ -152,12 +152,12 @@ ensure_parser :: proc(lang: string) -> ^Grammar_Cache {
if builtin, ok := builtin_language(lang); ok { if builtin, ok := builtin_language(lang); ok {
language = builtin language = builtin
} else { } else {
if GRAPHS_PATH == "" { if grammar_dir == "" {
log.warnf("treesitter: no grammars path set, skipping %s", lang) log.warnf("treesitter: no grammar path set, skipping %s", lang)
return nil return nil
} }
so_path := fmt.tprintf("%s/%s.so", GRAPHS_PATH, lang) so_path := fmt.tprintf("%s/%s.so", grammar_dir, lang)
so_c := strings.clone_to_cstring(so_path) so_c := strings.clone_to_cstring(so_path)
defer delete(so_c) defer delete(so_c)
handle := dlopen(so_c, RTLD_LAZY) handle := dlopen(so_c, RTLD_LAZY)
@@ -208,13 +208,13 @@ load_grammar :: proc(lang: string) -> ^Grammar_Cache {
return nil return nil
} }
if QUERIES_PATH == "" { if query_dir == "" {
log.warnf("treesitter: no queries path set, skipping %s", lang) log.warnf("treesitter: no query path set, skipping %s", lang)
gc.query_failed = true gc.query_failed = true
return nil return nil
} }
query_path := fmt.tprintf("%s/%s/highlights.scm", QUERIES_PATH, lang) query_path := fmt.tprintf("%s/%s/highlights.scm", query_dir, lang)
query_src, err := os.read_entire_file_from_path(query_path, context.allocator) query_src, err := os.read_entire_file_from_path(query_path, context.allocator)
if err != nil { if err != nil {
log.warnf("treesitter: cannot load query %s", query_path) log.warnf("treesitter: cannot load query %s", query_path)
@@ -262,7 +262,7 @@ load_grammar :: proc(lang: string) -> ^Grammar_Cache {
_, is_builtin := builtin_language(lang) _, is_builtin := builtin_language(lang)
if !is_builtin { if !is_builtin {
so_path := fmt.tprintf("%s/%s.so", GRAPHS_PATH, lang) so_path := fmt.tprintf("%s/%s.so", grammar_dir, lang)
gram_v := helix_version_from_path(so_path) gram_v := helix_version_from_path(so_path)
query_v := helix_version_from_path(query_path) query_v := helix_version_from_path(query_path)
gram_note := "(version unknown)" gram_note := "(version unknown)"