feat(tvix/eval): context-aware coerce_to_string

I am still undecided whether we need a CoercionKind to control
the coerced context, here's a simple attempt.

Change-Id: Ibe59d09ef26c519a6acfdfe392014446646dd6d8
Reviewed-on: https://cl.tvl.fyi/c/depot/+/10426
Reviewed-by: tazjin <tazjin@tvl.su>
Tested-by: BuildkiteCI
Autosubmit: raitobezarius <tvl@lahfa.xyz>
This commit is contained in:
Ryan Lahfa 2023-12-26 00:38:40 +01:00 committed by clbot
parent 802f374a90
commit 743c362049
2 changed files with 18 additions and 2 deletions

View file

@ -318,15 +318,27 @@ impl Value {
// Track if we are coercing the first value of a list to correctly emit
// separating white spaces.
let mut is_list_head = None;
// FIXME(raitobezarius): as per https://b.tvl.fyi/issues/364
// we might be interested into more powerful context-related coercion kinds.
let mut context: NixContext = NixContext::new();
loop {
let value = if let Some(v) = vals.pop() {
v.force(co, span.clone()).await?
} else {
return Ok(Value::String(result.into()));
return Ok(Value::String(NixString::new_context_from(
context,
result.as_str(),
)));
};
let coerced = match (value, kind) {
// coercions that are always done
(Value::String(s), _) => Ok(s.as_str().to_owned()),
(Value::String(mut s), _) => {
if let Some(ctx) = s.context_mut() {
context = context.join(ctx);
}
Ok(s.as_str().to_owned())
}
// TODO(sterni): Think about proper encoding handling here. This needs
// general consideration anyways, since one current discrepancy between

View file

@ -322,6 +322,10 @@ impl NixString {
Self::new_context_from(context, &s.into_boxed_str())
}
pub(crate) fn context_mut(&mut self) -> Option<&mut NixContext> {
return self.1.as_mut();
}
pub fn iter_plain(&self) -> impl Iterator<Item = &str> {
return self.1.iter().flat_map(|context| context.iter_plain());
}