Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

VS2017, VSIX: just created AsyncPackage is not being instanced

This is default VSPackage. I added only ProvideAutoLoad attributes.

using System;
using System.ComponentModel.Design;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Globalization;
using System.Runtime.InteropServices;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.VisualStudio;
using Microsoft.VisualStudio.OLE.Interop;
using Microsoft.VisualStudio.Shell;
using Microsoft.VisualStudio.Shell.Interop;
using Microsoft.Win32;
using Task = System.Threading.Tasks.Task;

namespace VSIXProject1
{
    /// <summary>
    /// This is the class that implements the package exposed by this assembly.
    /// </summary>
    /// <remarks>
    /// <para>
    /// The minimum requirement for a class to be considered a valid package for Visual Studio
    /// is to implement the IVsPackage interface and register itself with the shell.
    /// This package uses the helper classes defined inside the Managed Package Framework (MPF)
    /// to do it: it derives from the Package class that provides the implementation of the
    /// IVsPackage interface and uses the registration attributes defined in the framework to
    /// register itself and its components with the shell. These attributes tell the pkgdef creation
    /// utility what data to put into .pkgdef file.
    /// </para>
    /// <para>
    /// To get loaded into VS, the package must be referred by &lt;Asset Type="Microsoft.VisualStudio.VsPackage" ...&gt; in .vsixmanifest file.
    /// </para>
    /// </remarks>
    [PackageRegistration(UseManagedResourcesOnly = true, AllowsBackgroundLoading = true)]
    [InstalledProductRegistration("#110", "#112", "1.0", IconResourceID = 400)] // Info on this package for Help/About
    [Guid(VSPackage1.PackageGuidString)]
    [ProvideAutoLoad(UIContextGuids.NoSolution, PackageAutoLoadFlags.BackgroundLoad)]
    [ProvideAutoLoad(UIContextGuids.SolutionExists, PackageAutoLoadFlags.BackgroundLoad)]
    [SuppressMessage("StyleCop.CSharp.DocumentationRules", "SA1650:ElementDocumentationMustBeSpelledCorrectly", Justification = "pkgdef, VS and vsixmanifest are valid VS terms")]
    public sealed class VSPackage1 : AsyncPackage
    {
        /// <summary>
        /// VSPackage1 GUID string.
        /// </summary>
        public const string PackageGuidString = "cca56365-4b14-4a96-9280-c30dce400195";

        /// <summary>
        /// Initializes a new instance of the <see cref="VSPackage1"/> class.
        /// </summary>
        public VSPackage1()
        {
            // Inside this method you can place any initialization code that does not require
            // any Visual Studio service because at this point the package object is created but
            // not sited yet inside Visual Studio environment. The place to do all the other
            // initialization is the Initialize method.
        }

        #region Package Members

        /// <summary>
        /// Initialization of the package; this method is called right after the package is sited, so this is the place
        /// where you can put all the initialization code that rely on services provided by VisualStudio.
        /// </summary>
        /// <param name="cancellationToken">A cancellation token to monitor for initialization cancellation, which can occur when VS is shutting down.</param>
        /// <param name="progress">A provider for progress updates.</param>
        /// <returns>A task representing the async work of package initialization, or an already completed task if there is none. Do not return null from this method.</returns>
        protected override async Task InitializeAsync(CancellationToken cancellationToken, IProgress<ServiceProgressData> progress)
        {
            // When initialized asynchronously, the current thread may be a background thread at this point.
            // Do any initialization that requires the UI thread after switching to the UI thread.
            await this.JoinableTaskFactory.SwitchToMainThreadAsync(cancellationToken);
        }

        #endregion
    }
}

Looks like it's not being instanced. If I'm adding break point or Debug.WriteLine(...) then nothing happening. When I'm adding Command then also nothing. I only can see my extension in Extensions and Updates window.

I recorded the little video with step by step reproduction my problem: https://youtu.be/B2T311Ug5FQ

What I should to do to my package gets instanced?

like image 892
Denis535 Avatar asked Jan 04 '19 18:01

Denis535


3 Answers

I started from the default package template and for me it turned out that adding the attribute

[ProvideAutoLoad(UIContextGuids80.NoSolution, PackageAutoLoadFlags.BackgroundLoad)]

to the package class made things work. Try going back to the default template and add that line, then debug.

To me this is a bug in the template. Templates should just work without needing to hunt around on stackoverflow for ages to find the magical missing incantation. Obviously you just want to hit the debug key and see the breakpoint hit, then build out from there.

like image 94
satnhak Avatar answered Nov 20 '22 05:11

satnhak


I had this problem with an extension taken over from Visual Studio 2017, which was before taken over through all intermediate Visual Studio Versions, I think maybe created on VS2010. I changed two things or more, but I don't know which of these made it work.

  1. Similar to satnhak above had to add

    [ProvideAutoLoad(VSConstants.UICONTEXT.SolutionExists_string, PackageAutoLoadFlags.BackgroundLoad)] [ProvideAutoLoad(VSConstants.UICONTEXT.SolutionHasMultipleProjects_string, PackageAutoLoadFlags.BackgroundLoad)] [ProvideAutoLoad(VSConstants.UICONTEXT.SolutionHasSingleProject_string, PackageAutoLoadFlags.BackgroundLoad)]

  2. In my .csproj removed a line

    <OldToolsVersion>14.0</OldToolsVersion>

I found these by comparing a newly created extension from template and comparing all properties (argh).

Also found out that after uninstalling the extension I had to start up Visual Studio one time with another solution to finish the uninstallation process completely. I guess it has a flag somewhere which blocks the instantiation of a newly installed one until this has been fully completed. Sorry all a bit fuzzy.

In any case also something good to know is that problems are logged in these locations:

  • %appdata%\Microsoft\VisualStudio\16.0_d1c373d5\ActivityLog.Setup.xml
  • %appdata%\Microsoft\VisualStudio\16.0_d1c373d5\ActivityLog.xsl
  • %appdata%..\Local\Temp\dd_VSIXInstaller_*.log

Every successful instantiation is logged in the last one.

like image 1
AndresRohrAtlasInformatik Avatar answered Nov 20 '22 03:11

AndresRohrAtlasInformatik


My scenario was: I created a VSIX project in VS2022 and then added an AsyncPackage to it. I hadn't noticed that the VSIX project already contained another package.

The other AsyncPackage was both instantiated and initialized. Therefore, I removed the one I added and used the pre-existing one, problem solved.

I cannot find any documentation about it, but it looks that each VSIX only loads just one package. see VSIX: how to pack two or more vspackage into a vsix

like image 1
Maziar Taheri Avatar answered Nov 20 '22 05:11

Maziar Taheri