async Task <CodeContainer> RunAcquisition(IProgress <ServiceProgressData> downloadProgress, CancellationToken cancellationToken, IRepositoryModel repository) { CloneDialogResult request = null; try { var uiProvider = await Task.Run(() => Package.GetGlobalService(typeof(IGitHubServiceProvider)) as IGitHubServiceProvider); await ShowTeamExplorerPage(uiProvider); request = await ShowCloneDialog(uiProvider, downloadProgress, repository); } catch (Exception e) { log.Error(e, "Error showing Start Page clone dialog"); } if (request == null) { return(null); } var uri = request.Repository.CloneUrl.ToRepositoryUrl(); return(new CodeContainer( localProperties: new CodeContainerLocalProperties(request.Path, CodeContainerType.Folder, new CodeContainerSourceControlProperties(request.Repository.Name, request.Path, new Guid(Guids.GitSccProviderId))), remote: new RemoteCodeContainer(request.Repository.Name, new Guid(Guids.CodeContainerProviderId), uri, new Uri(uri.ToString().TrimSuffix(".git")), DateTimeOffset.UtcNow), isFavorite: false, lastAccessed: DateTimeOffset.UtcNow)); }
public async Task Skip_OpenRepository_When_Already_Open(string repositoryPath, string solutionPath, bool isFolder, int openRepository) { var repositoryUrl = "https://github.com/owner/repo"; var cloneDialogResult = new CloneDialogResult(repositoryPath, repositoryUrl); var serviceProvider = Substitutes.GetServiceProvider(); var operatingSystem = serviceProvider.GetOperatingSystem(); operatingSystem.Directory.DirectoryExists(repositoryPath).Returns(true); var dte = Substitute.For <EnvDTE.DTE>(); serviceProvider.GetService <EnvDTE.DTE>().Returns(dte); dte.Solution.FileName.Returns(solutionPath); if (isFolder) { operatingSystem.Directory.DirectoryExists(solutionPath).Returns(true); } var cloneService = CreateRepositoryCloneService(serviceProvider); await cloneService.CloneOrOpenRepository(cloneDialogResult); var teamExplorerServices = serviceProvider.GetTeamExplorerServices(); teamExplorerServices.Received(openRepository).OpenRepository(repositoryPath); }
/// <inheritdoc/> public async Task CloneOrOpenRepository( CloneDialogResult cloneDialogResult, object progress = null) { Guard.ArgumentNotNull(cloneDialogResult, nameof(cloneDialogResult)); var repositoryPath = cloneDialogResult.Path; var url = cloneDialogResult.Url; if (DestinationFileExists(repositoryPath)) { throw new InvalidOperationException("Can't clone or open a repository because a file exists at: " + repositoryPath); } var repositoryUrl = url.ToRepositoryUrl(); var isDotCom = HostAddress.IsGitHubDotComUri(repositoryUrl); if (DestinationDirectoryExists(repositoryPath)) { if (!IsSolutionInRepository(repositoryPath)) { teamExplorerServices.OpenRepository(repositoryPath); } if (isDotCom) { await usageTracker.IncrementCounter(x => x.NumberOfGitHubOpens); } else { await usageTracker.IncrementCounter(x => x.NumberOfEnterpriseOpens); } } else { var cloneUrl = repositoryUrl.ToString(); await CloneRepository(cloneUrl, repositoryPath, progress).ConfigureAwait(true); if (isDotCom) { await usageTracker.IncrementCounter(x => x.NumberOfGitHubClones); } else { await usageTracker.IncrementCounter(x => x.NumberOfEnterpriseClones); } } // Give user a chance to choose a solution teamExplorerServices.ShowHomePage(); // Navigate to context for supported URL types (e.g. /blob/ URLs) var context = gitHubContextService.FindContextFromUrl(url); if (context != null) { gitHubContextService.TryNavigateToContext(repositoryPath, context); } }
public async Task CloneOrOpenRepository_CloneDialogResult_Returned_By_ShowCloneDialog() { var downloadProgress = Substitute.For <IProgress <ServiceProgressData> >(); var cancellationToken = CancellationToken.None; var dialogService = Substitute.For <IDialogService>(); var result = new CloneDialogResult(@"x:\repo", "https://github.com/owner/repo"); dialogService.ShowCloneDialog(null).ReturnsForAnyArgs(result); var cloneService = Substitute.For <IRepositoryCloneService>(); var target = CreateGitHubContainerProvider(dialogService: dialogService, cloneService: cloneService); await target.AcquireCodeContainerAsync(downloadProgress, cancellationToken); await cloneService.Received(1).CloneOrOpenRepository(result, downloadProgress, cancellationToken); }
public async Task UpdatesMetricsWhenCloneOrOpenRepositoryAsync(string cloneUrl, bool dirExists, int numberOfCalls, string counterName) { var repositoryPath = @"c:\dev\bar"; var cloneDialogResult = new CloneDialogResult(repositoryPath, cloneUrl); var operatingSystem = Substitute.For <IOperatingSystem>(); var usageTracker = Substitute.For <IUsageTracker>(); operatingSystem.Directory.DirectoryExists(repositoryPath).Returns(dirExists); var cloneService = CreateRepositoryCloneService(operatingSystem: operatingSystem, usageTracker: usageTracker); await cloneService.CloneOrOpenRepository(cloneDialogResult); await usageTracker.Received(numberOfCalls).IncrementCounter( Arg.Is <Expression <Func <UsageModel.MeasuresModel, int> > >(x => ((MemberExpression)x.Body).Member.Name == counterName)); }
/// <inheritdoc/> public async Task CloneOrOpenRepository( CloneDialogResult cloneDialogResult, object progress = null) { Guard.ArgumentNotNull(cloneDialogResult, nameof(cloneDialogResult)); var repositoryPath = cloneDialogResult.Path; var url = cloneDialogResult.Url; if (DestinationFileExists(repositoryPath)) { throw new InvalidOperationException("Can't clone or open a repository because a file exists at: " + repositoryPath); } var repositoryUrl = url.ToRepositoryUrl(); var isDotCom = HostAddress.IsGitHubDotComUri(repositoryUrl); if (DestinationDirectoryExists(repositoryPath)) { teamExplorerServices.OpenRepository(repositoryPath); if (isDotCom) { await usageTracker.IncrementCounter(x => x.NumberOfGitHubOpens); } else { await usageTracker.IncrementCounter(x => x.NumberOfEnterpriseOpens); } } else { var cloneUrl = repositoryUrl.ToString(); await CloneRepository(cloneUrl, repositoryPath, progress).ConfigureAwait(true); if (isDotCom) { await usageTracker.IncrementCounter(x => x.NumberOfGitHubClones); } else { await usageTracker.IncrementCounter(x => x.NumberOfEnterpriseClones); } } teamExplorerServices.ShowHomePage(); }
async Task <CloneDialogResult> ShowCloneDialog( IGitHubServiceProvider gitHubServiceProvider, IProgress <ServiceProgressData> progress, IRepositoryModel repository = null) { var dialogService = gitHubServiceProvider.GetService <IDialogService>(); var cloneService = gitHubServiceProvider.GetService <IRepositoryCloneService>(); var usageTracker = gitHubServiceProvider.GetService <IUsageTracker>(); CloneDialogResult result = null; if (repository == null) { result = await dialogService.ShowCloneDialog(null); } else { var basePath = await dialogService.ShowReCloneDialog(repository); if (basePath != null) { result = new CloneDialogResult(basePath, repository); } } if (result != null) { try { await cloneService.CloneRepository( result.Repository.CloneUrl, result.Repository.Name, result.Path, progress); usageTracker.IncrementCounter(x => x.NumberOfStartPageClones).Forget(); } catch { var teServices = gitHubServiceProvider.TryGetService <ITeamExplorerServices>(); teServices.ShowError($"Failed to clone the repository '{result.Repository.Name}'"); result = null; } } return(result); }
public async Task Completes_When_Returning_CodeContainer() { var downloadProgress = Substitute.For <IProgress <ServiceProgressData> >(); var cancellationToken = CancellationToken.None; var dialogService = Substitute.For <IDialogService>(); var result = new CloneDialogResult(@"x:\repo", "https://github.com/owner/repo"); dialogService.ShowCloneDialog(null).ReturnsForAnyArgs(result); var cloneService = Substitute.For <IRepositoryCloneService>(); var target = CreateGitHubContainerProvider(dialogService: dialogService, cloneService: cloneService); var codeContainer = await target.AcquireCodeContainerAsync(downloadProgress, cancellationToken); Assert.That(codeContainer, Is.Not.Null); downloadProgress.Received(1).Report( Arg.Is <ServiceProgressData>(x => x.TotalSteps > 0 && x.CurrentStep == x.TotalSteps)); }
public async Task Pass_DisplayUrl_To_ShowCloneDialog() { var displayUrl = "https://github.com/owner/displayUrl"; var browseOnlineUrl = "https://github.com/owner/browseOnlineUrl"; var remoteCodeContainer = new RemoteCodeContainer("Name", Guid.NewGuid(), new Uri(displayUrl), new Uri(browseOnlineUrl), DateTimeOffset.Now, new Dictionary <string, string>()); var downloadProgress = Substitute.For <IProgress <ServiceProgressData> >(); var cancellationToken = CancellationToken.None; var dialogService = Substitute.For <IDialogService>(); var result = new CloneDialogResult(@"x:\repo", "https://github.com/owner/repo"); dialogService.ShowCloneDialog(null).ReturnsForAnyArgs(result); var cloneService = Substitute.For <IRepositoryCloneService>(); var target = CreateGitHubContainerProvider(dialogService: dialogService, cloneService: cloneService); await target.AcquireCodeContainerAsync(remoteCodeContainer, downloadProgress, cancellationToken); await dialogService.Received(1).ShowCloneDialog(Arg.Any <IConnection>(), displayUrl); }
public async Task UpdatesMetricsWhenCloneOrOpenRepositoryAsync(string cloneUrl, bool dirExists, int numberOfCalls, string counterName) { var repositoryPath = @"c:\dev\bar"; var cloneDialogResult = new CloneDialogResult(repositoryPath, cloneUrl); var serviceProvider = Substitutes.ServiceProvider; var operatingSystem = serviceProvider.GetOperatingSystem(); operatingSystem.Directory.DirectoryExists(repositoryPath).Returns(dirExists); var vsGitServices = serviceProvider.GetVSGitServices(); var teamExplorerServices = Substitute.For <ITeamExplorerServices>(); var graphqlFactory = Substitute.For <IGraphQLClientFactory>(); var usageTracker = Substitute.For <IUsageTracker>(); var cloneService = new RepositoryCloneService(operatingSystem, vsGitServices, teamExplorerServices, graphqlFactory, usageTracker); await cloneService.CloneOrOpenRepository(cloneDialogResult); await usageTracker.Received(numberOfCalls).IncrementCounter( Arg.Is <Expression <Func <UsageModel.MeasuresModel, int> > >(x => ((MemberExpression)x.Body).Member.Name == counterName)); }
async Task <CodeContainer> RunAcquisition(IProgress <ServiceProgressData> downloadProgress, RepositoryModel repository, CancellationToken cancellationToken) { CloneDialogResult request = null; try { var uiProvider = await Task.Run(() => gitHubServiceProvider.Value); request = await ShowCloneDialog(uiProvider, downloadProgress, cancellationToken, repository); } catch (Exception e) { log.Error(e, "Error showing Start Page clone dialog"); } if (request == null) { return(null); } var uri = request.Url.ToRepositoryUrl(); var repositoryName = request.Url.RepositoryName; // Report all steps complete before returning a CodeContainer downloadProgress.Report(new ServiceProgressData(string.Empty, string.Empty, 1, 1)); return(new CodeContainer( localProperties: new CodeContainerLocalProperties(request.Path, CodeContainerType.Folder, new CodeContainerSourceControlProperties(repositoryName, request.Path, new Guid(Guids.GitSccProviderId))), remote: new RemoteCodeContainer(repositoryName, new Guid(Guids.CodeContainerProviderId), uri, new Uri(uri.ToString().TrimSuffix(".git")), DateTimeOffset.UtcNow), isFavorite: false, lastAccessed: DateTimeOffset.UtcNow)); }