diff options
Diffstat (limited to 'cli/tools/repl/editor.rs')
-rw-r--r-- | cli/tools/repl/editor.rs | 108 |
1 files changed, 59 insertions, 49 deletions
diff --git a/cli/tools/repl/editor.rs b/cli/tools/repl/editor.rs index e12b9314b..79467a996 100644 --- a/cli/tools/repl/editor.rs +++ b/cli/tools/repl/editor.rs @@ -249,69 +249,79 @@ fn validate(input: &str) -> ValidationResult { let mut in_template = false; let mut div_token_count_on_current_line = 0; let mut last_line_index = 0; - - for item in deno_ast::lex(input, deno_ast::MediaType::TypeScript) { - let current_line_index = line_info.line_index(item.range.start); + let mut queued_validation_error = None; + let tokens = deno_ast::lex(input, deno_ast::MediaType::TypeScript) + .into_iter() + .filter_map(|item| match item.inner { + deno_ast::TokenOrComment::Token(token) => Some((token, item.range)), + deno_ast::TokenOrComment::Comment { .. } => None, + }); + + for (token, range) in tokens { + let current_line_index = line_info.line_index(range.start); if current_line_index != last_line_index { div_token_count_on_current_line = 0; last_line_index = current_line_index; + + if let Some(error) = queued_validation_error { + return error; + } } - if let deno_ast::TokenOrComment::Token(token) = item.inner { - match token { - Token::BinOp(BinOpToken::Div) - | Token::AssignOp(AssignOp::DivAssign) => { - // it's too complicated to write code to detect regular expression literals - // which are no longer tokenized, so if a `/` or `/=` happens twice on the same - // line, then we bail - div_token_count_on_current_line += 1; - if div_token_count_on_current_line >= 2 { - return ValidationResult::Valid(None); - } + match token { + Token::BinOp(BinOpToken::Div) | Token::AssignOp(AssignOp::DivAssign) => { + // it's too complicated to write code to detect regular expression literals + // which are no longer tokenized, so if a `/` or `/=` happens twice on the same + // line, then we bail + div_token_count_on_current_line += 1; + if div_token_count_on_current_line >= 2 { + return ValidationResult::Valid(None); } - Token::BackQuote => in_template = !in_template, - Token::LParen - | Token::LBracket - | Token::LBrace - | Token::DollarLBrace => stack.push(token), - Token::RParen | Token::RBracket | Token::RBrace => { - match (stack.pop(), token) { - (Some(Token::LParen), Token::RParen) - | (Some(Token::LBracket), Token::RBracket) - | (Some(Token::LBrace), Token::RBrace) - | (Some(Token::DollarLBrace), Token::RBrace) => {} - (Some(left), _) => { - return ValidationResult::Invalid(Some(format!( - "Mismatched pairs: {left:?} is not properly closed" - ))) - } - (None, _) => { - // While technically invalid when unpaired, it should be V8's task to output error instead. - // Thus marked as valid with no info. - return ValidationResult::Valid(None); - } + } + Token::BackQuote => in_template = !in_template, + Token::LParen | Token::LBracket | Token::LBrace | Token::DollarLBrace => { + stack.push(token) + } + Token::RParen | Token::RBracket | Token::RBrace => { + match (stack.pop(), token) { + (Some(Token::LParen), Token::RParen) + | (Some(Token::LBracket), Token::RBracket) + | (Some(Token::LBrace), Token::RBrace) + | (Some(Token::DollarLBrace), Token::RBrace) => {} + (Some(left), _) => { + // queue up a validation error to surface once we've finished examininig the current line + queued_validation_error = Some(ValidationResult::Invalid(Some( + format!("Mismatched pairs: {left:?} is not properly closed"), + ))); + } + (None, _) => { + // While technically invalid when unpaired, it should be V8's task to output error instead. + // Thus marked as valid with no info. + return ValidationResult::Valid(None); } } - Token::Error(error) => { - match error.kind() { - // If there is unterminated template, it continues to read input. - SyntaxError::UnterminatedTpl => {} - _ => { - // If it failed parsing, it should be V8's task to output error instead. - // Thus marked as valid with no info. - return ValidationResult::Valid(None); - } + } + Token::Error(error) => { + match error.kind() { + // If there is unterminated template, it continues to read input. + SyntaxError::UnterminatedTpl => {} + _ => { + // If it failed parsing, it should be V8's task to output error instead. + // Thus marked as valid with no info. + return ValidationResult::Valid(None); } } - _ => {} } + _ => {} } } - if !stack.is_empty() || in_template { - return ValidationResult::Incomplete; + if let Some(error) = queued_validation_error { + error + } else if !stack.is_empty() || in_template { + ValidationResult::Incomplete + } else { + ValidationResult::Valid(None) } - - ValidationResult::Valid(None) } impl Highlighter for EditorHelper { |