Stream support (#812)

* Moves off of draining between filters. Instead, the sink will pull on the stream, and will drain element-wise. This moves the whole stream to being lazy.
* Adds ctrl-c support and connects it into some of the key points where we pull on the stream. If a ctrl-c is detect, we immediately halt pulling on the stream and return to the prompt.
* Moves away from having a SourceMap where anchor locations are stored. Now AnchorLocation is kept directly in the Tag.
* To make this possible, split tag and span. Span is largely used in the parser and is copyable. Tag is now no longer copyable.
This commit is contained in:
Jonathan Turner
2019-10-13 17:12:43 +13:00
committed by GitHub
parent 8ca678440a
commit 193b00764b
110 changed files with 1988 additions and 1892 deletions

View File

@ -48,19 +48,23 @@ pub(crate) fn evaluate_baseline_expr(
scope: &Scope,
source: &Text,
) -> Result<Tagged<Value>, ShellError> {
let tag = Tag {
span: expr.span,
anchor: None,
};
match &expr.item {
RawExpression::Literal(literal) => Ok(evaluate_literal(expr.copy_tag(literal), source)),
RawExpression::Literal(literal) => Ok(evaluate_literal(literal.tagged(tag), source)),
RawExpression::ExternalWord => Err(ShellError::argument_error(
"Invalid external word",
ArgumentError::InvalidExternalWord,
expr.tag(),
tag,
)),
RawExpression::FilePath(path) => Ok(Value::path(path.clone()).tagged(expr.tag())),
RawExpression::FilePath(path) => Ok(Value::path(path.clone()).tagged(tag)),
RawExpression::Synthetic(hir::Synthetic::String(s)) => {
Ok(Value::string(s).tagged_unknown())
}
RawExpression::Variable(var) => evaluate_reference(var, scope, source, expr.tag()),
RawExpression::Command(_) => evaluate_command(expr.tag(), scope, source),
RawExpression::Variable(var) => evaluate_reference(var, scope, source, tag),
RawExpression::Command(_) => evaluate_command(tag, scope, source),
RawExpression::ExternalCommand(external) => evaluate_external(external, scope, source),
RawExpression::Binary(binary) => {
let left = evaluate_baseline_expr(binary.left(), registry, scope, source)?;
@ -69,10 +73,16 @@ pub(crate) fn evaluate_baseline_expr(
trace!("left={:?} right={:?}", left.item, right.item);
match left.compare(binary.op(), &*right) {
Ok(result) => Ok(Value::boolean(result).tagged(expr.tag())),
Ok(result) => Ok(Value::boolean(result).tagged(tag)),
Err((left_type, right_type)) => Err(ShellError::coerce_error(
binary.left().copy_tag(left_type),
binary.right().copy_tag(right_type),
left_type.tagged(Tag {
span: binary.left().span,
anchor: None,
}),
right_type.tagged(Tag {
span: binary.right().span,
anchor: None,
}),
)),
}
}
@ -84,13 +94,10 @@ pub(crate) fn evaluate_baseline_expr(
exprs.push(expr);
}
Ok(Value::Table(exprs).tagged(expr.tag()))
Ok(Value::Table(exprs).tagged(tag))
}
RawExpression::Block(block) => {
Ok(
Value::Block(Block::new(block.clone(), source.clone(), expr.tag()))
.tagged(expr.tag()),
)
Ok(Value::Block(Block::new(block.clone(), source.clone(), tag.clone())).tagged(&tag))
}
RawExpression::Path(path) => {
let value = evaluate_baseline_expr(path.head(), registry, scope, source)?;
@ -113,16 +120,16 @@ pub(crate) fn evaluate_baseline_expr(
return Err(ShellError::labeled_error(
"Unknown column",
format!("did you mean '{}'?", possible_matches[0].1),
expr.tag(),
&tag,
));
}
Some(next) => {
item = next.clone().item.tagged(expr.tag());
item = next.clone().item.tagged(&tag);
}
};
}
Ok(item.item().clone().tagged(expr.tag()))
Ok(item.item().clone().tagged(tag))
}
RawExpression::Boolean(_boolean) => unimplemented!(),
}