diff options
Diffstat (limited to '')
-rw-r--r-- | src/readline_highlighters.cc | 119 |
1 files changed, 71 insertions, 48 deletions
diff --git a/src/readline_highlighters.cc b/src/readline_highlighters.cc index 58c537c..9fe8418 100644 --- a/src/readline_highlighters.cc +++ b/src/readline_highlighters.cc @@ -41,10 +41,6 @@ #include "sql_util.hh" #include "view_curses.hh" -static void readline_sqlite_highlighter_int(attr_line_t& al, - int x, - line_range sub); - static bool is_bracket(const std::string& str, int index, bool is_lit) { @@ -237,12 +233,13 @@ readline_command_highlighter(attr_line_t& al, int x) al, x, line_range{0, (int) al.get_string().length()}); } -static void +void readline_sqlite_highlighter_int(attr_line_t& al, int x, line_range sub) { static const char* brackets[] = { "[]", "()", + "{}", nullptr, }; @@ -260,10 +257,14 @@ readline_sqlite_highlighter_int(attr_line_t& al, int x, line_range sub) sub.lr_start + attr.sa_range.lr_end, }; if (attr.sa_type == &SQL_COMMAND_ATTR - || attr.sa_type == &SQL_KEYWORD_ATTR) + || attr.sa_type == &SQL_KEYWORD_ATTR + || attr.sa_type == &lnav::sql::PRQL_KEYWORD_ATTR + || attr.sa_type == &lnav::sql::PRQL_TRANSFORM_ATTR) { alb.overlay_attr(lr, VC_ROLE.value(role_t::VCR_KEYWORD)); - } else if (attr.sa_type == &SQL_IDENTIFIER_ATTR) { + } else if (attr.sa_type == &SQL_IDENTIFIER_ATTR + || attr.sa_type == &lnav::sql::PRQL_IDENTIFIER_ATTR) + { if (!attr.sa_range.contains(x) && attr.sa_range.lr_end != x) { alb.overlay_attr(lr, VC_ROLE.value(role_t::VCR_IDENTIFIER)); } @@ -271,7 +272,9 @@ readline_sqlite_highlighter_int(attr_line_t& al, int x, line_range sub) alb.overlay_attr( line_range{lr.lr_start, (int) line.find('(', lr.lr_start)}, VC_ROLE.value(role_t::VCR_SYMBOL)); - } else if (attr.sa_type == &SQL_NUMBER_ATTR) { + } else if (attr.sa_type == &SQL_NUMBER_ATTR + || attr.sa_type == &lnav::sql::PRQL_NUMBER_ATTR) + { alb.overlay_attr(lr, VC_ROLE.value(role_t::VCR_NUMBER)); } else if (attr.sa_type == &SQL_STRING_ATTR) { if (lr.length() > 1 && al.al_string[lr.lr_end - 1] == '\'') { @@ -282,9 +285,15 @@ readline_sqlite_highlighter_int(attr_line_t& al, int x, line_range sub) alb.overlay_attr_for_char(lr.lr_start, VC_ROLE.value(role_t::VCR_ERROR)); } - } else if (attr.sa_type == &SQL_OPERATOR_ATTR) { + } else if (attr.sa_type == &lnav::sql::PRQL_STRING_ATTR) { + alb.overlay_attr(lr, VC_ROLE.value(role_t::VCR_STRING)); + } else if (attr.sa_type == &SQL_OPERATOR_ATTR + || attr.sa_type == &lnav::sql::PRQL_OPERATOR_ATTR) + { alb.overlay_attr(lr, VC_ROLE.value(role_t::VCR_SYMBOL)); - } else if (attr.sa_type == &SQL_COMMENT_ATTR) { + } else if (attr.sa_type == &SQL_COMMENT_ATTR + || attr.sa_type == &lnav::sql::PRQL_COMMENT_ATTR) + { alb.overlay_attr(lr, VC_ROLE.value(role_t::VCR_COMMENT)); } } @@ -306,63 +315,77 @@ readline_shlex_highlighter_int(attr_line_t& al, int x, line_range sub) { attr_line_builder alb(al); const auto& str = al.get_string(); - string_fragment cap; - shlex_token_t token; nonstd::optional<int> quote_start; shlex lexer(string_fragment{al.al_string.data(), sub.lr_start, sub.lr_end}); + bool done = false; + + while (!done) { + auto tokenize_res = lexer.tokenize(); + if (tokenize_res.isErr()) { + auto te = tokenize_res.unwrapErr(); + + alb.overlay_attr(line_range(sub.lr_start + te.te_source.sf_begin, + sub.lr_start + te.te_source.sf_end), + VC_STYLE.value(text_attrs{A_REVERSE})); + alb.overlay_attr(line_range(sub.lr_start + te.te_source.sf_begin, + sub.lr_start + te.te_source.sf_end), + VC_ROLE.value(role_t::VCR_ERROR)); + return; + } - while (lexer.tokenize(cap, token)) { - switch (token) { - case shlex_token_t::ST_ERROR: - alb.overlay_attr(line_range(sub.lr_start + cap.sf_begin, - sub.lr_start + cap.sf_end), - VC_STYLE.value(text_attrs{A_REVERSE})); - alb.overlay_attr(line_range(sub.lr_start + cap.sf_begin, - sub.lr_start + cap.sf_end), - VC_ROLE.value(role_t::VCR_ERROR)); + auto token = tokenize_res.unwrap(); + switch (token.tr_token) { + case shlex_token_t::eof: + done = true; break; - case shlex_token_t::ST_TILDE: - case shlex_token_t::ST_ESCAPE: - alb.overlay_attr(line_range(sub.lr_start + cap.sf_begin, - sub.lr_start + cap.sf_end), - VC_ROLE.value(role_t::VCR_SYMBOL)); + case shlex_token_t::tilde: + case shlex_token_t::escape: + alb.overlay_attr( + line_range(sub.lr_start + token.tr_frag.sf_begin, + sub.lr_start + token.tr_frag.sf_end), + VC_ROLE.value(role_t::VCR_SYMBOL)); break; - case shlex_token_t::ST_DOUBLE_QUOTE_START: - case shlex_token_t::ST_SINGLE_QUOTE_START: - quote_start = sub.lr_start + cap.sf_begin; + case shlex_token_t::double_quote_start: + case shlex_token_t::single_quote_start: + quote_start = sub.lr_start + token.tr_frag.sf_begin; break; - case shlex_token_t::ST_DOUBLE_QUOTE_END: - case shlex_token_t::ST_SINGLE_QUOTE_END: + case shlex_token_t::double_quote_end: + case shlex_token_t::single_quote_end: alb.overlay_attr( - line_range(quote_start.value(), sub.lr_start + cap.sf_end), + line_range(quote_start.value(), + sub.lr_start + token.tr_frag.sf_end), VC_ROLE.value(role_t::VCR_STRING)); quote_start = nonstd::nullopt; break; - case shlex_token_t::ST_VARIABLE_REF: - case shlex_token_t::ST_QUOTED_VARIABLE_REF: { - int extra = token == shlex_token_t::ST_VARIABLE_REF ? 0 : 1; - auto ident = str.substr(sub.lr_start + cap.sf_begin + 1 + extra, - cap.length() - 1 - extra * 2); + case shlex_token_t::variable_ref: + case shlex_token_t::quoted_variable_ref: { + int extra = token.tr_token == shlex_token_t::variable_ref ? 0 + : 1; + auto ident = str.substr( + sub.lr_start + token.tr_frag.sf_begin + 1 + extra, + token.tr_frag.length() - 1 - extra * 2); alb.overlay_attr( - line_range(sub.lr_start + cap.sf_begin, - sub.lr_start + cap.sf_begin + 1 + extra), + line_range( + sub.lr_start + token.tr_frag.sf_begin, + sub.lr_start + token.tr_frag.sf_begin + 1 + extra), VC_ROLE.value(role_t::VCR_SYMBOL)); alb.overlay_attr( - line_range(sub.lr_start + cap.sf_begin + 1 + extra, - sub.lr_start + cap.sf_end - extra), - VC_ROLE.value( - x == sub.lr_start + cap.sf_end - || (cap.sf_begin <= x && x < cap.sf_end) - ? role_t::VCR_SYMBOL - : role_t::VCR_IDENTIFIER)); + line_range( + sub.lr_start + token.tr_frag.sf_begin + 1 + extra, + sub.lr_start + token.tr_frag.sf_end - extra), + VC_ROLE.value(x == sub.lr_start + token.tr_frag.sf_end + || (token.tr_frag.sf_begin <= x + && x < token.tr_frag.sf_end) + ? role_t::VCR_SYMBOL + : role_t::VCR_IDENTIFIER)); if (extra) { alb.overlay_attr_for_char( - sub.lr_start + cap.sf_end - 1, + sub.lr_start + token.tr_frag.sf_end - 1, VC_ROLE.value(role_t::VCR_SYMBOL)); } break; } - case shlex_token_t::ST_WHITESPACE: + case shlex_token_t::whitespace: break; } } |