This is due to the abstract syntax tree getting out of sync with the text of the document. Normally, you'd modify the source file by manipulating the syntax tree, which in turn updates the text of the document. When modifying the text directly, you need to make sure the syntax tree is notified of the change, so it knows to update.
You can do this by wrapping the update in a transaction:
using(solution.CreateTransactionCookie(DefaultAction.Commit, "Update text"))
{
document.InsertText(...);
}
You get to specify the default action that will happen when the transaction cookie's Dispose
method is called - commit or rollback, and you can call methods directly on the transaction cookie, too. The text passed to the cookie is plain text and is only used for diagnostics purposes, so you can see the transaction that is currently active.
UPDATE:
After looking at the code, the issue here is that you can't modify the text of the document while there's a PSI transaction active. The PSI transaction indicates that you're going to modify the abstract syntax tree of the document, so you can't then modify the text of the document as well - you could easily get into a situation with two conflicting changes and no way to reconcile them.
The PSI transaction is being created by the BulbActionBase
base class of the context action, before calling the ExecutePsiTransaction
method. You can't modify the text directly in this method.
You have a couple of choices here. You could create a comment node using CSharpElementFactory.GetInstance(...).CreateComment(text)
and then add it to the PSI tree using the methods in ModificationUtil
, or you can leave ExecutePsiTransaction
as an empty method (return null
) and implement ExecuteAfterPsiTransaction
and call Document.InsertText
there (this is what the XAML InsertTextQuickFix
class does). Because this method is called while in a transaction, but not while in a PSI transaction, it should update the text, and cause the PSI to be put back in sync.
Incidentally, ReSharper throws an exception when trying to modify the document while the PSI transaction is active, with an appropriate message. If you run Visual Studio with the command line devenv.exe /ReSharper.Internal
, this exception should be shown as a tooltip like window in the status bar. Even better, if you're building a plugin, you can install a "checked" build, which includes more checks and reports exceptions by default.