Inspection not re-run after applying QuickFix

Answered

I have a simple Inspection that provides a QuickFix. The fix changes the PsiElement successfully and it basically does only this

MathematicaPsiElementFactory factory = new MathematicaPsiElementFactory(project);
final Expression epxr = factory.createExpressionFromText("1;");
final PsiElement semicolon = epxr.getLastChild();
elm.addAfter(semicolon, elm.getLastChild());

However, after the quickfix is applied, the editor still shows the error. I tried commiting the document but it doesn't help. Note that when I write a string into the document instead of changing the PsiElement the inspection is re-run.

What am I doing wrong?

Btw, I checked several implementations of QuickFix in the Idea source and they all do it like I do.

5 comments
Comment actions Permalink

Hi Patrick,

I assume that your inspection was not called once more on the initial element or it doesn't provide any errors after a fix.

do you ask for a writeAction? Where is the highlighting error, is it on the elm or somewhere else? If you update "foreign" element in the quickfix, editor optimization could not include initial element in the rehighlighting range as it was not changed.

Anna

0
Comment actions Permalink

Hey Anna,

thanks as always for your time.

I believe the re-run of the inspection is just not triggered, because as soon as I start editing the file, all error annotations disappear. I do not ask explicitly for a writeAction because I thought a QuickFix is wrapped automatically in one and when I insert directly a string into the Document it works as well without one. Although what I do is calling

FileModificationService.getInstance().prepareFileForWrite(elm.getContainingFile())

The whole implementation is only about 10 lines long. If you like to take a look, here is the implementation that works on PsiElements and here is the same implementation that inserts strings into the document.

Btw, if you are asking why I'm going through this trouble when the doc-method works: The problem is that when I call FixAll, then obviously the text-ranges inside the document change when one issue is fixed. Therefore, the other QuickFixes happen in the wrong place. I felt that fixing this on PsiElements is a better way.

0
Comment actions Permalink

Working on PsiElements is better, absolutely agree. I've asked about write action because we introduced the ability to avoid write action when not needed. Your code (on Psi) is ok, I would remove working with document completely and call CodeStyleManager.reformat(elm.getParent()).

To the problem itself: I would rather try to put the error on elm.getParent and highlight elm.getTextRange() only. This way, elm.addAfter would be inside element with the highlighting and should be rehighlighted on change.

Hope this help, 

Anna

0
Comment actions Permalink

Anna,

thanks for the remarks. I thought I loose my mind until I saw the mistake on my side. I'll explain as further reference for future visitor in a moment but I have two questions:

  1. Is it possible that I can fix all annotations from one inspection in one run? Basically, I want to have all annotated elements, so that I can go through them and fixing everything in one run when the user selects "fix all issues".
  2. How would I call a reparse of the whole file?

Explanation: Anna was right, it should work and indeed my annotator *was* called after the fix. The problem is that inserting a child at a node did not create a valid tree. The real problem was that in Mathematica this

1+1
x^2
3*y

is just a sequence of expressions where the root node is the PsiFile. More importantly, this here

1+1;
x^2;
3*y;

is a "compound expression". It's several subexpressions separated by a semicolon. The first child of the PsiFile is, therefore, a CompoundExpression node containing as children all the subexpressions and of course the separating semicolons.

When I do a quickfix and just insert the semicolon-PsiElements at the end, this isn't enough. I would have to build up the correct tree-form with a wrapping CompoundExpression PsiElement around all subexpressions. This was the reason that my annotator still showed the error.

The moment I touch the file and make some changes, the file is reparsed and the correct structures was built. Therefore, all annotations vanished.

So for future visitors, remember that you have to build the correct structure regarding your language when you make changes on PsiElements. I did know this, but it seems I was just too blind and I suspected a different issue.

0
Comment actions Permalink

Patrick,

"Fix all" should work automatically if you add your fix in on-the-fly and in batch mode. I don't think that it's a good idea to reparse the whole file, if you create valid psi after applying the quickfix you should not have problems. In java, most dirty work is done inside the addChild/removeChild, etc methods, so you don't have to bother to add commas to the expression list, etc. Could you do the same for you? 

Anna

0

Please sign in to leave a comment.