@@ -59,6 +59,7 @@ type InoHandler struct {
59
59
sketchMapper * sourcemapper.InoMapper
60
60
sketchTrackedFilesCount int
61
61
docs map [lsp.DocumentURI ]* lsp.TextDocumentItem
62
+ docHasDiagnostics map [lsp.DocumentURI ]bool
62
63
63
64
config lsp.BoardConfig
64
65
synchronizer Synchronizer
@@ -68,6 +69,7 @@ type InoHandler struct {
68
69
func NewInoHandler (stdio io.ReadWriteCloser , board lsp.Board ) * InoHandler {
69
70
handler := & InoHandler {
70
71
docs : map [lsp.DocumentURI ]* lsp.TextDocumentItem {},
72
+ docHasDiagnostics : map [lsp.DocumentURI ]bool {},
71
73
config : lsp.BoardConfig {
72
74
SelectedBoard : board ,
73
75
},
@@ -1040,23 +1042,6 @@ func (handler *InoHandler) FromClangd(ctx context.Context, connection *jsonrpc2.
1040
1042
// we should transform back N diagnostics of sketch.cpp.ino into
1041
1043
// their .ino counter parts (that may span over multiple files...)
1042
1044
1043
- // Remove diagnostics from all .ino if there are no errors coming from clang
1044
- if len (p .Diagnostics ) == 0 {
1045
- // XXX: Optimize this to publish "empty diagnostics" only to .ino that are
1046
- // currently showing previous diagnostics.
1047
-
1048
- for sourceURI := range handler .docs {
1049
- msg := lsp.PublishDiagnosticsParams {
1050
- URI : sourceURI ,
1051
- Diagnostics : []lsp.Diagnostic {},
1052
- }
1053
- if err := handler .StdioConn .Notify (ctx , "textDocument/publishDiagnostics" , msg ); err != nil {
1054
- return nil , err
1055
- }
1056
- }
1057
- return nil , nil
1058
- }
1059
-
1060
1045
convertedDiagnostics := map [string ][]lsp.Diagnostic {}
1061
1046
for _ , cppDiag := range p .Diagnostics {
1062
1047
inoSource , inoRange := handler .sketchMapper .CppToInoRange (cppDiag .Range )
@@ -1070,11 +1055,13 @@ func (handler *InoHandler) FromClangd(ctx context.Context, connection *jsonrpc2.
1070
1055
}
1071
1056
1072
1057
// Push back to IDE the converted diagnostics
1058
+ docsWithDiagnostics := map [lsp.DocumentURI ]bool {}
1073
1059
for filename , inoDiags := range convertedDiagnostics {
1074
1060
msg := lsp.PublishDiagnosticsParams {
1075
1061
URI : lsp .NewDocumentURI (filename ),
1076
1062
Diagnostics : inoDiags ,
1077
1063
}
1064
+ docsWithDiagnostics [msg .URI ] = true
1078
1065
if enableLogging {
1079
1066
log .Printf ("<-- publishDiagnostics(%s):" , msg .URI )
1080
1067
for _ , diag := range msg .Diagnostics {
@@ -1097,6 +1084,30 @@ func (handler *InoHandler) FromClangd(ctx context.Context, connection *jsonrpc2.
1097
1084
}
1098
1085
}
1099
1086
1087
+ // Remove diagnostics from all .ino where there are no errors coming from clang
1088
+ for sourceURI := range handler .docs {
1089
+ if ! handler .docHasDiagnostics [sourceURI ] {
1090
+ // skip if the document didn't have previously sent diagnostics
1091
+ continue
1092
+ }
1093
+ if docsWithDiagnostics [sourceURI ] {
1094
+ // skip if we already sent updated diagnostics
1095
+ continue
1096
+ }
1097
+ // otherwise clear previous diagnostics
1098
+ msg := lsp.PublishDiagnosticsParams {
1099
+ URI : sourceURI ,
1100
+ Diagnostics : []lsp.Diagnostic {},
1101
+ }
1102
+ if enableLogging {
1103
+ log .Printf ("<-- publishDiagnostics(%s):" , msg .URI )
1104
+ }
1105
+ if err := handler .StdioConn .Notify (ctx , "textDocument/publishDiagnostics" , msg ); err != nil {
1106
+ return nil , err
1107
+ }
1108
+ }
1109
+
1110
+ handler .docHasDiagnostics = docsWithDiagnostics
1100
1111
return nil , err
1101
1112
}
1102
1113
0 commit comments