/// <summary> /// <para> /// This is a bit of a hack. There currently isn't a good way to determine if the /// <paramref name="node"/> represents a project backed by the managed project /// system. In the interests of getting something working, here we check if the /// Solution Explorer thinks the node is a project and then check that it has a /// supported extension. /// </para> /// <para> /// The _right_ way to do this probably involves getting the project GUID from the /// node and then running that throught the Project API to determine if the project /// has the appropriate capabilities. At the moment there's no good way to /// achieve that first step, however. /// </para> /// </summary> private static bool NodeRepresentsAManagedProject(WorkspaceVisualNodeBase node) { return(node?.VSSelectionMoniker != null && node.VSSelectionKind == CloudEnvironment.SolutionViewProjectGuid && node.NodeMoniker != null && s_supportedProjectExtensions.Any(extension => node.NodeMoniker.EndsWith(extension, StringComparison.OrdinalIgnoreCase))); }
/// <summary> /// Handles opening the file associated with the given <paramref name="node"/>. /// </summary> /// <param name="node"></param> private void OpenFile(WorkspaceVisualNodeBase node) { if (node == null || string.IsNullOrEmpty(node.NodeMoniker)) { return; } _taskContext.Factory.RunAsync(async() => { var serviceContainer = _serviceProvider.GetService <SVsBrokeredServiceContainer, IBrokeredServiceContainer>(); var serviceBroker = serviceContainer.GetFullAccessServiceBroker(); var openDocumentService = await serviceBroker.GetProxyAsync <IOpenDocumentService>(VisualStudioServices.VS2019_4.OpenDocumentService); try { await openDocumentService.OpenDocumentAsync(node.NodeMoniker, cancellationToken: default); } finally { (openDocumentService as IDisposable)?.Dispose(); } }); }
/// <summary> /// Handles opening the file associated with the given <paramref name="node"/>. /// </summary> /// <param name="node"></param> private void OpenFile(WorkspaceVisualNodeBase node) { if (node == null || string.IsNullOrEmpty(node.NodeMoniker)) { return; } _taskContext.Factory.RunAsync(async() => { IBrokeredServiceContainer serviceContainer = _serviceProvider.GetService <SVsBrokeredServiceContainer, IBrokeredServiceContainer>(); ServiceHub.Framework.IServiceBroker serviceBroker = serviceContainer.GetFullAccessServiceBroker(); IOpenDocumentService?openDocumentService = await serviceBroker.GetProxyAsync <IOpenDocumentService>(VisualStudioServices.VS2019_4.OpenDocumentService); try { if (openDocumentService != null && node is IFileSystemNode fileSystemNode) { await openDocumentService.OpenDocumentAsync(fileSystemNode.FullPath, cancellationToken: default); } //else // TODO: figure out what to tell the user if we can't get the service // https://github.com/dotnet/project-system/issues/6306 } finally { (openDocumentService as IDisposable)?.Dispose(); } }); }
// Note: all the Exec commands are async, this allows us to call them in a fire and forget // pattern, without blocking the UI or losing any logging private async void ExecNpmInstallMissing(WorkspaceVisualNodeBase node) { using (var npmController = this.CreateController(node.Workspace)) using (var commander = npmController.CreateNpmCommander()) { await commander.Install(); } }
private async void ExecNpmUpdate(WorkspaceVisualNodeBase node) { using (var npmController = this.CreateController(node.Workspace)) using (var commander = npmController.CreateNpmCommander()) { await commander.UpdatePackagesAsync(); } }
public bool IsPackageManagerUISupported(WorkspaceVisualNodeBase workspaceVisualNodeBase) { if (workspaceVisualNodeBase is null) { return(false); } return(IsPackageManagerUISupportAvailable); }
private void ExecNpmInstallNew(WorkspaceVisualNodeBase node) { using (var npmController = this.CreateController(node.Workspace)) using (var npmWorker = new NpmWorker(npmController)) using (var manager = new NpmPackageInstallWindow(npmController, npmWorker)) { manager.ShowModal(); } }
/// <summary> /// Provides our <see cref="IWorkspaceCommandHandler"/> for nodes representing /// managed projects. /// </summary> public IWorkspaceCommandHandler?ProvideCommandHandler(WorkspaceVisualNodeBase parentNode) { if (NodeRepresentsAManagedProject(parentNode)) { return(_commandHandler); } return(null); }
public IWorkspaceCommandHandler ProvideCommandHandler(WorkspaceVisualNodeBase parentNode) { if (parentNode is IFolderNode) { return(_handler); } return(null); }
public IWorkspaceCommandHandler ProvideCommandHandler(WorkspaceVisualNodeBase parentNode) { if (EnsurePackageJson(parentNode)) { this.outputPane.ShowWindow(); return(this.npmHandler); } return(null); }
public IWorkspaceCommandHandler ProvideCommandHandler(WorkspaceVisualNodeBase parentNode) { if (EnsurePackageJson(parentNode)) { return(this.npmHandler); } // we only have a command handler for 'package.json' files return(null); }
private async void ExecDynamic(WorkspaceVisualNodeBase node, uint nCmdID) { // Unfortunately the NpmController (and NpmCommander), used for the install and update commands // doesn't support running arbitrary scripts. And changing that is outside // the scope of these changes. var filePath = ((IFileNode)node).FullPath; if (TryGetCommand(nCmdID, filePath, out var commandName)) { using (var npmController = this.CreateController(node.Workspace)) using (var commander = npmController.CreateNpmCommander()) { await commander.ExecuteNpmCommandAsync($"run-script {commandName}", showConsole : true); } } }
private async void ExecDebugAsync(WorkspaceVisualNodeBase node) { var workspace = node.Workspace; var packageJson = PackageJsonFactory.Create(((IFileNode)node).FullPath); //invoke debuglaunchtargetprovider on this file var fileContextActions = await node.Workspace.GetFileContextActionsAsync(packageJson.Main, new[] { DebugLaunchActionContext.ContextTypeGuid }); if (fileContextActions.Any()) { // we requested a single context, so there should be a single grouping. Use the First action, since they're ordered by priority. var action = fileContextActions.Single().FirstOrDefault(); Debug.Assert(action != null, "Why is action null, when we did get a fileContextActions?"); await action.ExecuteAsync(DefaultBuildProgressUpdater, CancellationToken.None); } }
private async Task ShowPackageManagerUIAsync(WorkspaceVisualNodeBase workspaceVisualNodeBase) { await NuGetUIThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(); if (ShouldMEFBeInitialized()) { await InitializeMEFAsync(); } IVsWindowFrame window = await CreateNewWindowFrameAsync(workspaceVisualNodeBase); if (window != null) { Search(window, string.Empty); window.Show(); } }
private async void ExecDynamic(WorkspaceVisualNodeBase node, uint nCmdID) { // Unfortunately the NpmController (and NpmCommander), used for the install, update commands // doesn't support running arbitrary scripts. And changing that is outside // the scope of these changes. var filePath = ((IFileNode)node).FullPath; if (TryGetCommand(nCmdID, filePath, out var commandName)) { var npmPath = NpmHelpers.GetPathToNpm(); await NpmWorker.ExecuteNpmCommandAsync( npmPath, executionDirectory : Path.GetDirectoryName(filePath), arguments : new[] { "run-script", commandName }, visible : true); // show the CMD window } }
private async Task <IVsWindowFrame> CreateNewWindowFrameAsync(WorkspaceVisualNodeBase workspaceVisualNodeBase) { await NuGetUIThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(); // Find existing hierarchy and item id of the document window if it's already registered. var rdt = await _asyncServiceProvider.GetServiceAsync <IVsRunningDocumentTable, IVsRunningDocumentTable>(); Assumes.Present(rdt); IVsHierarchy hier; uint itemId; var docData = IntPtr.Zero; int hr; try { uint cookie; hr = rdt.FindAndLockDocument( (uint)_VSRDTFLAGS.RDT_NoLock, workspaceVisualNodeBase.NodeMoniker, out hier, out itemId, out docData, out cookie); if (hr != VSConstants.S_OK) { // the docuemnt window is not registered yet. So use the hierarchy from the current selection. itemId = (uint)VSConstants.VSITEMID.Root; } } finally { if (docData != IntPtr.Zero) { Marshal.Release(docData); docData = IntPtr.Zero; } } return(await CreateToolWindowAsync(workspaceVisualNodeBase, hier, itemId)); }
public IWorkspaceCommandHandler ProvideCommandHandler(WorkspaceVisualNodeBase parentNode) => parentNode is IFolderNode ? _handler : null;
private static bool EnsurePackageJson(WorkspaceVisualNodeBase node) { return(node is IFileNode fileNode && StringComparer.OrdinalIgnoreCase.Equals(fileNode.FileName, "package.json")); }
private static bool EnsurePackageJson(WorkspaceVisualNodeBase node) { return(node is IFileNode fileNode && PackageJsonFactory.IsPackageJsonFile(fileNode.FileName)); }
public IChildrenSource ProvideChildren(WorkspaceVisualNodeBase parentNode) { // We don't provide new children so return null return(null); }
public IChildrenSource ProvideChildren(WorkspaceVisualNodeBase parentNode) => null;
public IChildrenSource?ProvideChildren(WorkspaceVisualNodeBase parentNode) { return(null); }
/// <summary> /// Provides our <see cref="IWorkspaceCommandHandler"/> for nodes representing /// managed projects. /// </summary> public IWorkspaceCommandHandler ProvideCommandHandler(WorkspaceVisualNodeBase parentNode) { return(_commandHandler); }
public void OpenPackageManagerUI(WorkspaceVisualNodeBase workspaceVisualNodeBase) { _joinableTaskFactory.RunAsync(() => OpenPackageManagerUIAsync(workspaceVisualNodeBase)).PostOnFailure(nameof(PackageManagerUICommandHandler)); }
private async Task OpenPackageManagerUIAsync(WorkspaceVisualNodeBase workspaceVisualNodeBase) { await NuGetUIThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(); await ShowPackageManagerUIAsync(workspaceVisualNodeBase); }
private Task OpenPackageManagerUIAsync(WorkspaceVisualNodeBase workspaceVisualNodeBase) { return(Task.CompletedTask); }
public void OpenPackageManagerUI(WorkspaceVisualNodeBase workspaceVisualNodeBase) { _joinableTaskFactory.RunAsync(() => OpenPackageManagerUIAsync(workspaceVisualNodeBase)); }
private async ValueTask <IVsWindowFrame> CreateToolWindowAsync(WorkspaceVisualNodeBase workspaceVisualNodeBase, IVsHierarchy hier, uint itemId) { await NuGetUIThreadHelper.JoinableTaskFactory.SwitchToMainThreadAsync(); if (!Guid.TryParse(IProjectContextInfoUtility.GetProjectGuidStringFromVslsQueryString(workspaceVisualNodeBase.VSSelectionMoniker), out Guid projectGuid)) { throw new InvalidOperationException(); } IVsWindowFrame windowFrame = null; var uiShell = await _asyncServiceProvider.GetServiceAsync <SVsUIShell, IVsUIShell>(); Assumes.Present(uiShell); uint toolWindowId; bool foundToolWindowId = _projectGuidToToolWindowId.TryGetValue(projectGuid.ToString(), out toolWindowId); const uint FTW_none = 0; if (foundToolWindowId) { ErrorHandler.ThrowOnFailure( uiShell.FindToolWindowEx( FTW_none, //grfFTW - badly-documented enum value. typeof(PackageManagerToolWindowPane).GUID, // rguidPersistenceSlot toolWindowId, // dwToolWindowId out windowFrame)); if (windowFrame != null) { ((IVsWindowFrame2)windowFrame).ActivateOwnerDockedWindow(); } else { _projectGuidToToolWindowId.Remove(projectGuid.ToString()); } } if (windowFrame == null) { IServiceBroker serviceBroker = await ServiceBrokerProvider.Value.GetAsync(); IProjectContextInfo projectContextInfo = await IProjectContextInfoUtility.CreateAsync(serviceBroker, projectGuid.ToString(), CancellationToken.None); INuGetUI uiController = await UIFactory.Value.CreateAsync(serviceBroker, projectContextInfo); // This model takes ownership of --- and Dispose() responsibility for --- the INuGetUI instance. var model = new PackageManagerModel(uiController, isSolution: false, editorFactoryGuid: GuidList.NuGetEditorType); var control = await PackageManagerControl.CreateAsync(model, OutputConsoleLogger.Value); var caption = string.Format(CultureInfo.CurrentCulture, Resx.Label_NuGetWindowCaption, Path.GetFileNameWithoutExtension(workspaceVisualNodeBase.NodeMoniker)); int[] pfDefaultPosition = null; var windowPane = new PackageManagerToolWindowPane(control, projectGuid.ToString()); ErrorHandler.ThrowOnFailure( uiShell.CreateToolWindow( (uint)__VSCREATETOOLWIN.CTW_fInitNew, ++_maxToolWindowId, // dwToolWindowId windowPane, // ToolWindowPane Guid.Empty, // rclsidTool = GUID_NULL typeof(PackageManagerToolWindowPane).GUID, // rguidPersistenceSlot Guid.Empty, // reserved - do not use - GUID_NULL null, // IServiceProvider caption, pfDefaultPosition, out windowFrame)); _projectGuidToToolWindowId.Add(projectGuid.ToString(), _maxToolWindowId); windowPane.Closed += WindowPane_Closed; if (windowFrame != null) { WindowFrameHelper.AddF1HelpKeyword(windowFrame, keywordValue: F1KeywordValuePmUI); WindowFrameHelper.DisableWindowAutoReopen(windowFrame); WindowFrameHelper.DockToolWindow(windowFrame); } } return(windowFrame); }