commit 73880ef86f21fd9a8da10cf967c87254d1c3857d
parent 9578d72144f4c9a98a175c949e739fffc3bec1a9
Author: Lou Woell <lou.woell@posteo.de>
Date:   Fri, 19 Sep 2025 04:06:02 +0200

[resolve] restructure resolve_local, add tests

Diffstat:
Mcmd/harehelper/+test/resolve_test.ha | 34++++++++++++++++++++++++++++++++--
Mcmd/harehelper/resolve.ha | 37++++++++++++++++++++-----------------
2 files changed, 52 insertions(+), 19 deletions(-)

diff --git a/cmd/harehelper/+test/resolve_test.ha b/cmd/harehelper/+test/resolve_test.ha @@ -1,23 +1,27 @@ use dirs; +use fmt; use hare::ast; use hare::module::*; use hare::parse; +use hare::unparse; use m = math; use memio::{concat, dynamic}; use os; +use strings; use test; fn resolve_test_fn (in: str, out: str) void = { const ctx = context { - harepath = os::tryenv("HAREPATH", HAREPATH), + harepath = strings::join(":", harepath(), ".")!, harecache = match (os::getenv("HARECACHE")) { case let s: str => yield s; case void => yield dirs::cache("hare"); }, - tags = ["linux"], + tags = ["linux", "test"], }; + defer free(ctx.harepath); const id = parse::identstr(in)!; const exp = parse::identstr(out)!; @@ -27,6 +31,11 @@ fn resolve_test_fn (in: str, out: str) void = { match(res) { case void => abort(); case let i: ast::ident => + fmt::error("got: ")!; + unparse::ident(os::stderr, i)!; + fmt::error(", expected: ")!; + unparse::ident(os::stderr, exp)!; + fmt::error("\n")!; assert(ast::ident_eq(i, exp)); }; }; @@ -79,3 +88,24 @@ fn resolve_test_fn (in: str, out: str) void = { @test fn resolve_alias_module () void = { resolve_test_fn("m", "math"); }; + +@test fn resolve_local () void = { + resolve_test_fn( + "resolve_test_fn", + "cmd::harehelper::resolve_test_fn" + ); +}; + +@test fn resolve_local_tagged () void = { + resolve_test_fn( + "resolve_test_fn", + "cmd::harehelper::resolve_test_fn" + ); +}; + +@test fn resolve_local () void = { + resolve_test_fn( + "resolve", + "cmd::harehelper::resolve" + ); +}; diff --git a/cmd/harehelper/resolve.ha b/cmd/harehelper/resolve.ha @@ -50,18 +50,12 @@ fn resolve(cmd: getopt::command, ctx: *module::context) void = { printident(id_exp, trailing); ast::ident_free(id_exp); case => - match (resolve_local(ctx, id, file)) { - case let id: ast::ident => - printident(id, trailing); - free(id); - case => - printident(id, trailing); - }; + printident(id, trailing); }; }; -// Prepend id with path to file (relative to HAREPATH). Components of return -// value are borrowed from input. Slice itself must be freed. +// Prepend id with path to file (relative to HAREPATH). Return value must be +// freed by caller. fn resolve_local ( ctx: *module::context, id: ast::ident, @@ -71,18 +65,27 @@ fn resolve_local ( let hp = strings::split(ctx.harepath, ":")!; defer free(hp); - let new_id: ast::ident = []; for (let p .. hp) { if (strings::hasprefix(file, p)) { - let new_path = strings::trimprefix(file, p); - new_path = strings::trimprefix(new_path, "/"); - new_path = path::dirname(new_path); - new_id = strings::split(new_path, "/")!; + let new_id: ast::ident = []; + + file = strings::trimprefix(file, p); + file = strings::trimprefix(file, "/"); + file = path::dirname(file); + + new_id = strings::split(file, "/")!; + defer free(new_id); + + let result: ast::ident = []; + for (let s .. new_id) { + if (!strings::hasprefix(s, '+')) + append(result, strings::dup(s)!)!; + }; for (let s .. id) { - append(new_id, s)!; + append(result, strings::dup(s)!)!; }; - return new_id; + return result; }; }; @@ -166,5 +169,5 @@ fn resolve_uid ( }; }; - return void; + return resolve_local(ctx, id, path); };