Logo
PRB: Window.Close doesn't save changes if requested for .sql files in non-database projects

Author: Carlos J. Quintero (Microsoft MVP) Applies to: Microsoft Visual Studio 2013
Date: September 2014    
       
Introduction

When you call EnvDTE.Window.Close(vsSaveChanges.vsSaveChangesYes) on a .sql file that belongs to a non-database project (such as a C# project), the window is closed but the file on disk is not updated with the changes.

More Information

Steps to reproduce the problem:

  • Create a Visual Studio 2013 add-in with the following code. The add-in, when loaded, opens an invisible window for each .cs or .sql file of the first project of the solution, gets the text document of the window, inserts a new line and closes the window saving the changes.
Language: C#   Copy Code Copy Code (IE only)
using System;
using Extensibility;
using EnvDTE;
using EnvDTE80;

namespace MyAddin1
{
   public class Connect : IDTExtensibility2
   {
      private DTE2 _applicationObject;
      private AddIn _addInInstance;

      public void OnConnection(object application, ext_ConnectMode connectMode, object addInInst, ref Array custom)
      {
         _applicationObject = (DTE2)application;
         _addInInstance = (AddIn)addInInst;

         switch (connectMode)
         {
            case ext_ConnectMode.ext_cm_AfterStartup:

               InitializeAddIn();
               break;

            case ext_ConnectMode.ext_cm_Startup:

               // Do nothing. OnStartupComplete will be called
               break;
         }
      }

      public void OnStartupComplete(ref Array custom)
      {
         InitializeAddIn();
      }

      private void InitializeAddIn()
      {
         Project project;
         Window window;
         Document document;
         TextDocument textDocument;
         EditPoint editPoint;

         try
         {
            project = _applicationObject.Solution.Projects.Item(1);

            foreach (ProjectItem projectItem in project.ProjectItems)
            {
               if (projectItem.Name.EndsWith(".cs") || projectItem.Name.EndsWith(".sql"))
               {
                  window = projectItem.Open(EnvDTE.Constants.vsViewKindPrimary);
                  
                  document = window.Document;
                  
                  textDocument = (TextDocument)document.Object("");
                  
                  editPoint = textDocument.StartPoint.CreateEditPoint();
                  
                  editPoint.Insert("This is new text\n");
                  
                  window.Close(vsSaveChanges.vsSaveChangesYes);

                  System.Windows.Forms.MessageBox.Show("Modified " + projectItem.Name);
               }
            }
         }
         catch (Exception ex)
         {
            System.Windows.Forms.MessageBox.Show(ex.ToString());
         }
      }
      public void OnDisconnection(ext_DisconnectMode disconnectMode, ref Array custom)
      {
      }

      public void OnAddInsUpdate(ref Array custom)
      {
      }

      public void OnBeginShutdown(ref Array custom)
      {
      }
   }
}
  • Run the add-in project but do not load the add-in yet.
  • Create a C# Console project.
  • Add a Text file but with the .sql extension rather than with the .txt extension.
  • Close all windows.
  • Load the add-in.
  • You get a "Modified" message box for the Program.cs file and the .sql file. If you open the Program.cs file, you see the persisted change. However, if you open the .sql file no change has been persisted.


Go to the 'Visual Studio Extensibility (VSX)' web site for more articles like this (Articles section)