<commit_before>﻿using IntelliTect.Coalesce.CodeGeneration.Configuration;
using IntelliTect.Coalesce.CodeGeneration.Generation;
using IntelliTect.Coalesce.CodeGeneration.Knockout.Generators;
using McMaster.Extensions.CommandLineUtils;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using System;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.Versioning;

namespace IntelliTect.Coalesce.Cli
{
    [HelpOption]
    public class Program
    {
        [Option(CommandOptionType.NoValue, Description = "Wait for a debugger to be attached before starting generation", LongName = "debug", ShortName = "d")]
        public string Debug { get; }

        [Argument(0, "config", Description = "coalesce.json configuration file that will drive generation." )]
        public string ConfigFile { get;  }

        [Option(ShortName = "v", LongName = "verbosity", Description = "Output verbosity. Options are Trace, Debug, Information, Warning, Error, Critical, None." )]
        public LogLevel LogLevel { get; }

        public static void Main(string[] args)
        {
#if DEBUG
            if (args.Contains("--debug", StringComparer.OrdinalIgnoreCase))
            {
                WaitForDebugger();
            }
#endif

            var app = new CommandLineApplication(false)
            {
                Name = "Coalesce"
            };

            // Get the target framework (e.g. ".NETCoreApp,Version=v2.0") that Coalesce was compiled against.
            // I added this originally for debugging, but its kinda nice to show regardless.
            var attr = Assembly.GetEntryAssembly().GetCustomAttribute<TargetFrameworkAttribute>();

            // This reflects the version of the nuget package.
            string version = FileVersionInfo.GetVersionInfo(Assembly.GetExecutingAssembly().Location).ProductVersion;

            Console.WriteLine($"Starting Coalesce {version}, running under {attr.FrameworkName}");
            Console.WriteLine("https://github.com/IntelliTect/Coalesce");
            Console.WriteLine();

            var configFile = app.Argument("[config]", "coalesce.json configuration file that will drive generation.");

            var debug = app.Option("--debug", "Wait for a debugger to be attached before starting generation", CommandOptionType.NoValue);
            var logLevel = app.Option(
                "-v|--verbosity <level>",
                $"Output verbosity. Options are {string.Join(", ", Enum.GetNames(typeof(LogLevel)).Select(l => l.ToLower()))}.",
                CommandOptionType.SingleValue
            );


            app.OnExecute(async () =>
            {

                var configFilePath = LocateConfigFile(configFile.Value);
                Directory.SetCurrentDirectory(Path.GetDirectoryName(configFilePath));
                Console.WriteLine($"Working in '{Directory.GetCurrentDirectory()}', using '{Path.GetFileName(configFilePath)}'");

                CoalesceConfiguration config;

                using (var reader = new StreamReader(configFilePath))
                using (var jsonReader = new JsonTextReader(reader))
                {
                    var serializer = new JsonSerializer();
                    config = serializer.Deserialize<CoalesceConfiguration>(jsonReader);
                }

                var level = LogLevel.Information;
                if (logLevel.HasValue())
                {
                    Enum.TryParse(logLevel.Value(), true, out level);
                }

                var executor = new GenerationExecutor(config, level);
                await executor.GenerateAsync<KnockoutSuite>();

                if (Debugger.IsAttached)
                {
                    Console.WriteLine("Press Enter to quit");
                    Console.Read();
                }

                return 0;
            });

            try
            {
                app.Execute(args);
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.ToString());
                Environment.Exit(-1);
            }
        }




        private static void WaitForDebugger()
        {
            Console.WriteLine($"Attach a debugger to processID: {System.Diagnostics.Process.GetCurrentProcess().Id}. Waiting...");
            var waitStep = 10;
            for (int i = 60; i > 0; i -= waitStep)
            {
                if (System.Diagnostics.Debugger.IsAttached)
                {
                    Console.WriteLine("Debugger attached.");
                    break;
                }
                if (i % 10 == 0) Console.WriteLine($"Waiting {i}...");
                System.Threading.Thread.Sleep(1000 * waitStep);
            }
        }

        private static string LocateConfigFile(string explicitLocation)
        {
            if (!string.IsNullOrWhiteSpace(explicitLocation))
            {
                if (!File.Exists(explicitLocation))
                {
                    throw new FileNotFoundException("Couldn't find Coalesce configuration file", Path.GetFullPath(explicitLocation));
                }
                return explicitLocation;
            }
            else
            {
                var curDirectory = new DirectoryInfo(Directory.GetCurrentDirectory());
                const string configFileName = "coalesce.json";
                while (curDirectory != null)
                {
                    var matchingFiles = curDirectory.EnumerateFiles(configFileName);
                    if (matchingFiles.Any())
                    {
                        return matchingFiles.First().FullName;
                    }
                    curDirectory = curDirectory.Parent;
                }
            }

            throw new FileNotFoundException("Couldn't locate a coalesce.json configuration file");
        }
    }
}<commit_msg>Cleaned up main program after success<commit_after>﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Reflection;
using System.Runtime.Versioning;
using System.Threading;
using System.Threading.Tasks;
using IntelliTect.Coalesce.CodeGeneration.Configuration;
using IntelliTect.Coalesce.CodeGeneration.Generation;
using IntelliTect.Coalesce.CodeGeneration.Knockout.Generators;
using McMaster.Extensions.CommandLineUtils;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;

// ReSharper disable UnassignedGetOnlyAutoProperty

namespace IntelliTect.Coalesce.Cli
{
    [HelpOption]
    public class Program
    {
        [Option(CommandOptionType.NoValue,
            Description = "Wait for a debugger to be attached before starting generation", LongName = "debug",
            ShortName = "d")]
        public bool Debug { get; }

        [Argument(0, "config", Description =
            "Path to a coalesce.json configuration file that will drive generation.  If not specified, it will search in current folder.")]
        public string ConfigFile { get; }

        [Option(CommandOptionType.SingleValue, ShortName = "v", LongName = "verbosity",
            Description = "Output verbosity. Options are Trace, Debug, Information, Warning, Error, Critical, None.")]
        // TODO: Change this type to be the Enum once Nate McMaster ships v2.2.0 of his library.
        public string LogLevelOption { get; }

        private static Task<int> Main(string[] args)
        {
            return CommandLineApplication.ExecuteAsync<Program>(args);
        }

        private async Task<int> OnExecuteAsync(CommandLineApplication app)
        {
#if DEBUG
            if (Debug) WaitForDebugger();
#endif

            // Get the target framework (e.g. ".NETCoreApp,Version=v2.0") that Coalesce was compiled against.
            // I added this originally for debugging, but its kinda nice to show regardless.
            var attr = Assembly.GetEntryAssembly().GetCustomAttribute<TargetFrameworkAttribute>();

            // This reflects the version of the nuget package.
            string version = FileVersionInfo.GetVersionInfo(Assembly.GetExecutingAssembly().Location).ProductVersion;

            Console.WriteLine($"Starting Coalesce {version}, running under {attr.FrameworkName}");
            Console.WriteLine("https://github.com/IntelliTect/Coalesce");
            Console.WriteLine();


            string configFilePath = LocateConfigFile(ConfigFile);
            Directory.SetCurrentDirectory(Path.GetDirectoryName(configFilePath));
            Console.WriteLine(
                $"Working in '{Directory.GetCurrentDirectory()}', using '{Path.GetFileName(configFilePath)}'");

            CoalesceConfiguration config;

            using (var reader = new StreamReader(configFilePath))
            using (var jsonReader = new JsonTextReader(reader))
            {
                var serializer = new JsonSerializer();
                config = serializer.Deserialize<CoalesceConfiguration>(jsonReader);
            }

            if (!Enum.TryParse(LogLevelOption, out LogLevel logLevel)) logLevel = LogLevel.Information;


            var executor = new GenerationExecutor(config, logLevel);
            await executor.GenerateAsync<KnockoutSuite>();

            if (!Debugger.IsAttached) return 0;
            Console.WriteLine("Press Enter to quit");
            Console.Read();

            return 0;
        }


        private static void WaitForDebugger()
        {
            Console.WriteLine($"Attach a debugger to processID: {Process.GetCurrentProcess().Id}. Waiting...");
            var waitStep = 10;
            for (var i = 60; i > 0; i -= waitStep)
            {
                if (Debugger.IsAttached)
                {
                    Console.WriteLine("Debugger attached.");
                    break;
                }

                if (i % 10 == 0) Console.WriteLine($"Waiting {i}...");
                Thread.Sleep(1000 * waitStep);
            }
        }

        private static string LocateConfigFile(string explicitLocation)
        {
            if (!string.IsNullOrWhiteSpace(explicitLocation))
            {
                if (!File.Exists(explicitLocation))
                    throw new FileNotFoundException("Couldn't find Coalesce configuration file",
                        Path.GetFullPath(explicitLocation));
                return explicitLocation;
            }

            var curDirectory = new DirectoryInfo(Directory.GetCurrentDirectory());
            const string configFileName = "coalesce.json";
            while (curDirectory != null)
            {
                List<FileInfo> matchingFiles = curDirectory.EnumerateFiles(configFileName).ToList();
                if (matchingFiles.Any()) return matchingFiles.First().FullName;
                curDirectory = curDirectory.Parent;
            }

            throw new FileNotFoundException("Couldn't locate a coalesce.json configuration file");
        }
    }
}
{'fraction_non_alphanumeric': 0.09420223900973879, 'fraction_numerical': 0.0033676162737781012, 'mean_word_length': 2.0471436494731003, 'pattern_counts': {'":': 0, '<': 14, '<?xml version=': 0, '>': 18, 'https://': 2, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5987518', 'n_tokens_mistral': 2719, 'n_tokens_neox': 2570, 'n_words': 656}