Skip to content

Commit

Permalink
nixd/Syntax: add legacy let warning
Browse files Browse the repository at this point in the history
  • Loading branch information
inclyc committed Sep 18, 2023
1 parent 032f564 commit d108ee5
Show file tree
Hide file tree
Showing 3 changed files with 70 additions and 6 deletions.
6 changes: 6 additions & 0 deletions nixd/lib/Syntax/Parser/Parser.y
Original file line number Diff line number Diff line change
Expand Up @@ -268,6 +268,12 @@ expr_simple
auto N = decorateNode(new LegacyLet, *yylocp, *Data);
N->AttrBinds = $3;
$$ = N;

Diagnostic Diag;
Diag.Msg = "using deprecated `let' syntactic sugar `let {..., body = ...}' -> (rec {..., body = ...}).body'";
Diag.Kind = Diagnostic::Warning;
Diag.Range = N->Range;
Data->Diags.emplace_back(std::move(Diag));
}
| REC '{' binds '}' {
auto N = decorateNode(new AttrSet, *yylocp, *Data);
Expand Down
65 changes: 59 additions & 6 deletions nixd/tools/nixd-lint/nixd-lint.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -23,6 +23,54 @@ opt<std::string> Filename(Positional, desc("<input file>"), init("-"),

const OptionCategory *Cat[] = {&Misc};

static void printCodeLines(std::ostream &Out, const std::string &Prefix,
const nix::AbstractPos &BeginPos,
const nix::AbstractPos &EndPos,
const nix::LinesOfCode &LOC) {
using namespace nix;
// previous line of code.
if (LOC.prevLineOfCode.has_value()) {
Out << std::endl
<< fmt("%1% %|2$5d|| %3%", Prefix, (BeginPos.line - 1),
*LOC.prevLineOfCode);
}

if (LOC.errLineOfCode.has_value()) {
// line of code containing the error.
Out << std::endl
<< fmt("%1% %|2$5d|| %3%", Prefix, (BeginPos.line), *LOC.errLineOfCode);
// error arrows for the column range.
if (BeginPos.column > 0) {
auto Start = BeginPos.column;
std::string Spaces;
for (auto I = 0; I < Start; ++I) {
Spaces.append(" ");
}

std::string arrows("^");

Out << std::endl
<< fmt("%1% |%2%" ANSI_RED "%3%" ANSI_NORMAL, Prefix, Spaces,
arrows);

if (BeginPos.line == EndPos.line) {
Out << ANSI_RED;
for (auto I = BeginPos.column + 1; I < EndPos.column; I++) {
Out << (I == EndPos.column - 1 ? "^" : "~");
}
Out << ANSI_NORMAL;
}
}
}

// next line of code.
if (LOC.nextLineOfCode.has_value()) {
Out << std::endl
<< fmt("%1% %|2$5d|| %3%", Prefix, (BeginPos.line + 1),
*LOC.nextLineOfCode);
}
}

int main(int argc, char *argv[]) {
HideUnrelatedOptions(Cat);
ParseCommandLineOptions(argc, argv, "nixd linter", nullptr,
Expand All @@ -49,20 +97,25 @@ int main(int argc, char *argv[]) {
nixd::syntax::parse(Buffer, &Data);

for (const auto &Diag : Data.Diags) {
std::shared_ptr<nix::AbstractPos> Pos = (*PTable)[Diag.Range.Begin];
std::shared_ptr<nix::AbstractPos> BeginAPos = (*PTable)[Diag.Range.Begin];
std::shared_ptr<nix::AbstractPos> EndAPos = (*PTable)[Diag.Range.End];
switch (Diag.Kind) {
case nixd::syntax::Diagnostic::Warning:
std::cout << ANSI_WARNING "warning:" ANSI_NORMAL;
std::cout << ANSI_WARNING "warning: " ANSI_NORMAL;
break;
case nixd::syntax::Diagnostic::Error:
std::cout << ANSI_RED "error: " ANSI_NORMAL;
break;
}
std::cout << Diag.Msg << "\n";
if (Pos) {
if (BeginAPos) {
std::cout << "\n"
<< ANSI_BLUE << "at " ANSI_WARNING
<< (*PTable)[Diag.Range.Begin] << ANSI_NORMAL << ":";
if (auto Lines = Pos->getCodeLines()) {
nix::printCodeLines(std::cout, "", *Pos, *Lines);
if (auto Lines = BeginAPos->getCodeLines()) {
std::cout << "\n";
printCodeLines(std::cout, "", *BeginAPos, *EndAPos, *Lines);
std::cout << "\n";
}
}

Expand All @@ -75,7 +128,7 @@ int main(int argc, char *argv[]) {
<< ":";
if (auto Lines =
std::shared_ptr<nix::AbstractPos>(NotePos)->getCodeLines()) {
nix::printCodeLines(std::cout, "", *Pos, *Lines);
nix::printCodeLines(std::cout, "", *BeginAPos, *Lines);
}
}
}
Expand Down
5 changes: 5 additions & 0 deletions nixd/tools/nixd-lint/test/legacy-let.nix
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
# RUN: nixd-lint %s | FileCheck %s

let { a = 1; } # CHECK: using deprecated `let'

; # CHECK: syntax error, unexpected ';', expecting end of file

0 comments on commit d108ee5

Please sign in to comment.