when_if_guard

This commit is contained in:
Folkert 2020-04-04 16:06:21 +02:00
parent 671eb0f32e
commit 98479511f5
4 changed files with 85 additions and 6 deletions

View file

@ -688,7 +688,7 @@ fn canonicalize_when_branch<'a>(
env: &mut Env<'a>, env: &mut Env<'a>,
var_store: &VarStore, var_store: &VarStore,
scope: &mut Scope, scope: &mut Scope,
region: Region, _region: Region,
branch: &'a ast::WhenBranch<'a>, branch: &'a ast::WhenBranch<'a>,
output: &mut Output, output: &mut Output,
) -> (WhenBranch, References) { ) -> (WhenBranch, References) {
@ -721,7 +721,7 @@ fn canonicalize_when_branch<'a>(
None => None, None => None,
Some(loc_expr) => { Some(loc_expr) => {
let (can_guard, guard_branch_output) = let (can_guard, guard_branch_output) =
canonicalize_expr(env, var_store, &mut scope, region, &loc_expr.value); canonicalize_expr(env, var_store, &mut scope, loc_expr.region, &loc_expr.value);
branch_output.union(guard_branch_output); branch_output.union(guard_branch_output);
Some(can_guard) Some(can_guard)

View file

@ -12,6 +12,7 @@ use ven_pretty::{BoxAllocator, DocAllocator, DocBuilder, Render, RenderAnnotated
/// A textual report. /// A textual report.
pub struct Report { pub struct Report {
pub title: String,
pub filename: PathBuf, pub filename: PathBuf,
pub text: ReportText, pub text: ReportText,
} }
@ -121,6 +122,7 @@ pub fn can_problem(filename: PathBuf, problem: Problem) -> Report {
}; };
Report { Report {
title: "SYNTAX PROBLEM".to_string(),
filename, filename,
text: Concat(texts), text: Concat(texts),
} }

View file

@ -74,6 +74,7 @@ fn report_mismatch(
]; ];
Report { Report {
title: "TYPE MISMATCH".to_string(),
filename, filename,
text: Concat(lines), text: Concat(lines),
} }
@ -104,6 +105,7 @@ fn report_bad_type(
]; ];
Report { Report {
title: "TYPE MISMATCH".to_string(),
filename, filename,
text: Concat(lines), text: Concat(lines),
} }
@ -139,7 +141,7 @@ fn to_expr_report(
region, region,
Some(expr_region), Some(expr_region),
problem, problem,
plain_text("Right now its"), plain_text("Right now its "),
Concat(vec![ Concat(vec![
plain_text("but I need every "), plain_text("but I need every "),
keyword_text("if"), keyword_text("if"),
@ -159,6 +161,36 @@ fn to_expr_report(
// they don't know. ("Wait, what's truthiness?") // they don't know. ("Wait, what's truthiness?")
) )
} }
Reason::WhenGuard => {
let problem = Concat(vec![
plain_text("This "),
keyword_text("if"),
plain_text(" guard condition needs to be a "),
ReportText::Type(Content::Alias(Symbol::BOOL_BOOL, vec![], Variable::BOOL)),
plain_text("."),
]);
report_bad_type(
filename,
&category,
found,
expected_type,
region,
Some(expr_region),
problem,
plain_text("Right now its "),
Concat(vec![
plain_text("but I need every "),
keyword_text("if"),
plain_text(" guard condition to evaluate to a "),
ReportText::Type(Content::Alias(Symbol::BOOL_BOOL, vec![], Variable::BOOL)),
plain_text("—either "),
global_tag_text("True"),
plain_text(" or "),
global_tag_text("False"),
plain_text("."),
]),
)
}
Reason::IfBranch { Reason::IfBranch {
index, index,
total_branches, total_branches,
@ -182,7 +214,7 @@ fn to_expr_report(
Concat(vec![ Concat(vec![
plain_text("The "), plain_text("The "),
keyword_text("else"), keyword_text("else"),
plain_text(" branch is"), plain_text(" branch is "),
]), ]),
Concat(vec![ Concat(vec![
plain_text("but the "), plain_text("but the "),
@ -215,7 +247,24 @@ fn to_expr_report(
) )
} }
}, },
_ => todo!(), other => {
// AnonymousFnArg { arg_index: u8 },
// NamedFnArg(String /* function name */, u8 /* arg index */),
// AnonymousFnCall { arity: u8 },
// NamedFnCall(String /* function name */, u8 /* arity */),
// BinOpArg(BinOp, ArgSide),
// BinOpRet(BinOp),
// FloatLiteral,
// IntLiteral,
// NumLiteral,
// InterpolatedStringVar,
// WhenBranch { index: usize },
// WhenGuard,
// ElemInList,
// RecordUpdateValue(Lowercase),
// RecordUpdateKeys(Symbol, SendMap<Lowercase, Type>),
todo!("I don't have a message yet for reason {:?}", other)
}
}, },
} }
} }
@ -304,7 +353,7 @@ fn add_category(this_is: ReportText, category: &Category) -> ReportText {
Num => Concat(vec![this_is, plain_text("a number of type")]), Num => Concat(vec![this_is, plain_text("a number of type")]),
Int => Concat(vec![this_is, plain_text("an integer of type")]), Int => Concat(vec![this_is, plain_text("an integer of type")]),
Float => Concat(vec![this_is, plain_text("a float of type")]), Float => Concat(vec![this_is, plain_text("a float of type")]),
Str => Concat(vec![this_is, plain_text(" a string of type")]), Str => Concat(vec![this_is, plain_text("a string of type")]),
Lambda => Concat(vec![this_is, plain_text("an anonymous function of type")]), Lambda => Concat(vec![this_is, plain_text("an anonymous function of type")]),
@ -378,6 +427,7 @@ fn to_circular_report(
]; ];
Report { Report {
title: "TYPE MISMATCH".to_string(),
filename, filename,
text: Concat(lines), text: Concat(lines),
} }

View file

@ -37,6 +37,7 @@ mod test_reporting {
// use roc_problem::can; // use roc_problem::can;
fn to_simple_report(text: ReportText) -> Report { fn to_simple_report(text: ReportText) -> Report {
Report { Report {
title: "SYNTAX PROBLEM".to_string(),
text: text, text: text,
filename: filename_from_string(r"\code\proj\Main.roc"), filename: filename_from_string(r"\code\proj\Main.roc"),
} }
@ -810,6 +811,32 @@ mod test_reporting {
) )
} }
#[test]
fn when_if_guard() {
report_problem_as(
indoc!(
r#"
when 1 is
2 if 1 -> 0x0
_ -> 0x1
"#
),
indoc!(
r#"
This `if` guard condition needs to be a Bool.
2 2 if 1 -> 0x0
^
Right now its a number of type
Num a
but I need every `if` guard condition to evaluate to a Booleither `True` or `False`.
"#
),
)
}
// #[test] // #[test]
// fn if_3_branch_mismatch() { // fn if_3_branch_mismatch() {
// report_problem_as( // report_problem_as(