/// <summary> /// Initializes a new instance of the <see cref="CakeConsole"/> class. /// </summary> /// <param name="environment">The environment.</param> public CakeConsole(ICakeEnvironment environment) { if (environment == null) { throw new ArgumentNullException(nameof(environment)); } _supportAnsiEscapeCodes = new Lazy <bool>(() => AnsiDetector.SupportsAnsi(environment)); }
public void Should_Return_False_When_Running_TeamCity_9_0_Or_Lower(string teamCityVersion) { // Given var fakeEnvironment = FakeEnvironment.CreateUnixEnvironment(); // When fakeEnvironment.SetEnvironmentVariable("TEAMCITY_VERSION", teamCityVersion); // Then Assert.False(AnsiDetector.SupportsAnsi(fakeEnvironment)); }
private static (bool Ansi, bool Legacy) DetectAnsi(AnsiConsoleSettings settings, System.IO.TextWriter buffer) { var supportsAnsi = settings.Ansi == AnsiSupport.Yes; var legacyConsole = false; if (settings.Ansi == AnsiSupport.Detect) { (supportsAnsi, legacyConsole) = AnsiDetector.Detect(buffer.IsStandardError(), true); // Check whether or not this is a legacy console from the existing instance (if any). // We need to do this because once we upgrade the console to support ENABLE_VIRTUAL_TERMINAL_PROCESSING // on Windows, there is no way of detecting whether or not we're running on a legacy console or not. if (AnsiConsole.Created && !legacyConsole && (buffer.IsStandardOut() || buffer.IsStandardError()) && AnsiConsole.Profile.Capabilities.Legacy) { legacyConsole = AnsiConsole.Profile.Capabilities.Legacy; } } else { if (buffer.IsStandardOut() || buffer.IsStandardError()) { // Are we running on Windows? if (RuntimeInformation.IsOSPlatform(OSPlatform.Windows)) { // Not the first console we're creating? if (AnsiConsole.Created) { legacyConsole = AnsiConsole.Profile.Capabilities.Legacy; } else { // Try detecting whether or not this is a legacy console (_, legacyConsole) = AnsiDetector.Detect(buffer.IsStandardError(), false); } } } } return(supportsAnsi, legacyConsole); }
/// <summary> /// Runs the application. /// </summary> /// <param name="args">Arguments.</param> /// <param name="appRoot">Application root folder</param> /// <returns>The result of the run.</returns> public async Task <RunResult> RunAsync(IEnumerable <string> args, string appRoot = null) { var console = new CakeConsole(); var logger = new SafeCakeLog(console); ICakeDataService dataService = new CodeCakeDataService(); var engine = new CakeEngine(dataService, logger); ICakePlatform platform = new CakePlatform(); ICakeRuntime runtime = new CakeRuntime(); IFileSystem fileSystem = new FileSystem(); MutableCakeEnvironment environment = new MutableCakeEnvironment(platform, runtime, appRoot); console.SupportAnsiEscapeCodes = AnsiDetector.SupportsAnsi(environment); IGlobber globber = new Globber(fileSystem, environment); IRegistry windowsRegistry = new WindowsRegistry(); // Parse options. var argumentParser = new ArgumentParser(logger, fileSystem); CakeOptions options = argumentParser.Parse(args); Debug.Assert(options != null); CakeConfigurationProvider configProvider = new CakeConfigurationProvider(fileSystem, environment); ICakeConfiguration configuration = configProvider.CreateConfiguration(environment.ApplicationRoot, options.Arguments); IToolRepository toolRepo = new ToolRepository(environment); IToolResolutionStrategy toolStrategy = new ToolResolutionStrategy(fileSystem, environment, globber, configuration, logger); IToolLocator locator = new ToolLocator(environment, toolRepo, toolStrategy); IToolLocator toolLocator = new ToolLocator(environment, toolRepo, toolStrategy); IProcessRunner processRunner = new ProcessRunner(fileSystem, environment, logger, toolLocator, configuration); logger.SetVerbosity(options.Verbosity); ICakeArguments arguments = new CakeArguments(options.Arguments); var context = new CakeContext( fileSystem, environment, globber, logger, arguments, processRunner, windowsRegistry, locator, dataService, configuration); CodeCakeBuildTypeDescriptor choosenBuild; if (!AvailableBuilds.TryGetValue(options.Script, out choosenBuild)) { logger.Error("Build script '{0}' not found.", options.Script); return(new RunResult(-1, context.InteractiveMode())); } // Set the working directory: the solution directory. logger.Information($"Working in Solution directory: '{_solutionDirectory}'."); environment.WorkingDirectory = new DirectoryPath(_solutionDirectory); try { SetEnvironmentVariablesFromCodeCakeBuilderKeyVault(logger, context); // Instantiates the script object. CodeCakeHost._injectedActualHost = new BuildScriptHost(engine, context); CodeCakeHost c = (CodeCakeHost)Activator.CreateInstance(choosenBuild.Type); var target = context.Arguments.GetArgument("target") ?? "Default"; var execSettings = new ExecutionSettings().SetTarget(target); var exclusiveTargetOptional = context.Arguments.HasArgument("exclusiveOptional"); var exclusiveTarget = exclusiveTargetOptional | context.Arguments.HasArgument("exclusive"); var strategy = new CodeCakeExecutionStrategy(logger, exclusiveTarget ? target : null); if (exclusiveTargetOptional && !engine.Tasks.Any(t => t.Name == target)) { logger.Warning($"No task '{target}' defined. Since -exclusiveOptional is specified, nothing is done."); return(new RunResult(0, context.InteractiveMode())); } var report = await engine.RunTargetAsync(context, strategy, execSettings); if (report != null && !report.IsEmpty) { var printerReport = new CakeReportPrinter(console); printerReport.Write(report); } } catch (CakeTerminateException ex) { switch (ex.Option) { case CakeTerminationOption.Error: logger.Error("Termination with Error: '{0}'.", ex.Message); return(new RunResult(-2, context.InteractiveMode())); case CakeTerminationOption.Warning: logger.Warning("Termination with Warning: '{0}'.", ex.Message); break; default: Debug.Assert(ex.Option == CakeTerminationOption.Success); logger.Information("Termination with Success: '{0}'.", ex.Message); break; } } catch (TargetInvocationException ex) { logger.Error("Error occurred: '{0}'.", ex.InnerException?.Message ?? ex.Message); return(new RunResult(-3, context.InteractiveMode())); } catch (AggregateException ex) { logger.Error("Error occurred: '{0}'.", ex.Message); foreach (var e in ex.InnerExceptions) { logger.Error(" -> '{0}'.", e.Message); } return(new RunResult(-4, context.InteractiveMode())); } catch (Exception ex) { logger.Error("Error occurred: '{0}'.", ex.Message); return(new RunResult(-5, context.InteractiveMode())); } return(new RunResult(0, context.InteractiveMode())); }