C# Console Application in .NET Framework 4.5 (edit)

Display Unicode in console window of a C# Console Application

How to write Unicode characters to the console?
https://stackoverflow.com/questions/5750203/how-to-write-unicode-characters-to-the-console

Size of console application font
https://www.codeproject.com/Questions/626384/Size-of-console-application-font

Changing Console Font Programmatically (HAY)
https://social.msdn.microsoft.com/Forums/sqlserver/en-US/c276b9ae-dc4c-484a-9a59-1ee66cf0f1cc/c-changing-console-font-programmatically?forum=csharpgeneral

Console.OutputEncoding = Encoding.UTF8;

Show/Hide the console window of a C# Console Application

https://amitpatriwala.wordpress.com/2008/04/14/hide-console-application/

https://stackoverflow.com/questions/3571627/show-hide-the-console-window-of-a-c-sharp-console-application

class Program
{
    [DllImport("user32.dll")]
    public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

    [DllImport("user32.dll")]
    private static extern bool ShowWindow(IntPtr hWnd, int nCmdShow);

    private static void Main(string[] args)
    {
        Console.Title = "eBill.Net";

        IntPtr hWnd = FindWindow(null, "eBill.Net");

        if (hWnd != IntPtr.Zero)
        {
            //Hide the window
            ShowWindow(hWnd, 0); // 0 = SW_HIDE
        }

        ...

    }

}

C# Console Application - Config

Project properties > Build > General

Check into "Allow unsafe code" to display Unicode (UTF8) in console window output

App.Config

<?xml version="1.0" encoding="utf-8"?>
<configuration>
<configSections>
<section name="log4net" type="log4net.Config.Log4NetConfigurationSectionHandler, log4net" />
</configSections>
<appSettings>
<add key="BareTailExePath" value="D:\Tools\BareTail\baretail.exe" />
</appSettings>
<connectionStrings>
<add name="MainConnectionString" connectionString="Data Source=localhost; Initial Catalog=DbTest; User Id=sa; Password=123456; Persist Security Info=False; MultipleActiveResultSets=True;" providerName="System.Data.SqlClient" />
</connectionStrings>
<!-- log4net -->
<log4net>
<appender name="RollingFileAppender" type="log4net.Appender.RollingFileAppender">
<file value="Logs\\Api.Test.log" />
<appendToFile value="true" />
<encoding value="UTF-8" />
<rollingStyle value="Size" />
<maxSizeRollBackups value="5" />
<maximumFileSize value="5MB" />
<staticLogFileName value="true" />
<lockingModel type="log4net.Appender.FileAppender+MinimalLock" />
<layout type="log4net.Layout.PatternLayout">
<param name="ConversionPattern" value="%date{dd-MM-yy HH:mm:ss} %-5level %message%newline" />
</layout>
</appender>

<appender name="TraceAppender" type="log4net.Appender.TraceAppender">
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%date{dd-MM-yy HH:mm:ss} %-5level %message%newline" />
</layout>
</appender>

<appender name="ConsoleAppender" type="log4net.Appender.ConsoleAppender">
<layout type="log4net.Layout.PatternLayout">
<conversionPattern value="%-5level %message%newline" />
</layout>
</appender>

<root>
<level value="All" />
<appender-ref ref="RollingFileAppender" />
<appender-ref ref="TraceAppender" />
<appender-ref ref="ConsoleAppender" />
</root>
</log4net>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
</startup>
</configuration>

Properties\AssemblyInfo.cs

[assembly: log4net.Config.XmlConfigurator(Watch = true)]

C# Console Application - Code

using Dapper;
using log4net;
using Newtonsoft.Json;
using Newtonsoft.Json.Serialization;
using OfficeOpenXml;
using System;
using System.Collections.Generic;
using System.Configuration;
using System.Data;
using System.Data.SqlClient;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Net.Http;
using System.Text;

namespace Api.Test
{
    internal class Program
    {
        private static readonly HttpClient client = new HttpClient();

        private static void Main(string[] args)
        {
            Console.OutputEncoding = Encoding.UTF8;
            Console.ForegroundColor = ConsoleColor.Blue;
            Console.BackgroundColor = ConsoleColor.Yellow;

            string CurrentDir = Directory.GetCurrentDirectory();
            string LogFilePath = Path.Combine(CurrentDir, "Logs", "API.GATEWAY.TEST.log");

            try
            {
                //Xóa trắng log file
                File.WriteAllText(LogFilePath, string.Empty, Encoding.UTF8);
            }
            catch (Exception ex)
            {
                MyLogger.Log.Error(ex.ToString());
                CloseViewLogFile();
                ViewLogFile(LogFilePath);
            }
        }

        public static bool WaitForFileInUse(string filename, TimeSpan timeToWait)
        {
            bool ready = false;

            if (!File.Exists(filename)) ready = true;

            while (!ready)
                try
                {
                    File.Open(filename, FileMode.Open, FileAccess.Write, FileShare.None).Dispose();
                    ready = true;
                }
                catch (IOException)
                {
                    if (timeToWait.TotalMilliseconds <= 0)
                        break;
                    int wait = (int)Math.Min(timeToWait.TotalMilliseconds, 1000.0);
                    timeToWait -= TimeSpan.FromMilliseconds(wait);
                    System.Threading.Thread.Sleep(wait); // sleep one second
                }

            return ready;
        }

        private static void CloseViewLogFile()
        {
            try
            {
                foreach (Process baretail in Process.GetProcessesByName("baretail"))
                    baretail.Kill();
            }
            catch (Exception ex)
            {
                MyLogger.Log.Error(ex.ToString());
            }
        }

        private static void OpenMicrosoftExcel(string file)
        {
            if (!File.Exists(file)) return;
            ProcessStartInfo startInfo = new ProcessStartInfo();
            startInfo.FileName = "EXCEL.EXE";
            startInfo.Arguments = file;
            Process.Start(startInfo);
        }

        private static void OpenNotepad2(string file)
        {
            if (!File.Exists(file)) return;
            ProcessStartInfo startInfo = new ProcessStartInfo();
            startInfo.FileName = "NOTEPAD2.EXE";
            startInfo.Arguments = file;
            Process.Start(startInfo);
        }

        private static void ViewLogFile(string file)
        {
            if (!File.Exists(file)) return;
            string BareTailExePath = ConfigurationManager.AppSettings["BareTailExePath"];
            if (!File.Exists(BareTailExePath)) return;
            ProcessStartInfo startInfo = new ProcessStartInfo();
            startInfo.FileName = BareTailExePath;
            startInfo.Arguments = file;
            Process.Start(startInfo);
        }

        private static void UpdateExcelFile(string filePath, List listInfoSchemaColumns)
        {
            FileInfo file = new FileInfo(filePath);
            using (ExcelPackage excelPackage = new ExcelPackage(file))
            {
                ExcelWorkbook excelWorkBook = excelPackage.Workbook;

                #region Sheet 1: Stored Procedure

                //Sheet 1: Stored Procedure
                List excelWorksheets = excelWorkBook.Worksheets.ToList();

                ExcelWorksheet sheet1 = excelWorksheets[0]; //Sheet 1

                //Update column B2 -> Bn
                for (int i = 0, n = listInfoSchemaColumns.Count; i < n; i++)
                {
                    sheet1.Cells[i + 2, 2].Value = listInfoSchemaColumns[i].COLUMN_NAME;
                }

                #endregion Sheet 1: Stored Procedure

                excelPackage.Save();
            }
        }

        private static void CreateExcelFile(string filePath)
        {
            ExcelPackage ExcelPkg = new ExcelPackage();
            ExcelWorksheet wsSheet1 = ExcelPkg.Workbook.Worksheets.Add("Sheet1");
            using (ExcelRange Rng = wsSheet1.Cells[2, 2, 2, 2])
            {
                Rng.Value = "Welcome to Everyday be coding - tutorials for beginners";
                Rng.Style.Font.Size = 16;
                Rng.Style.Font.Bold = true;
                Rng.Style.Font.Italic = true;
            }
            wsSheet1.Protection.IsProtected = false;
            wsSheet1.Protection.AllowSelectLockedCells = false;
            ExcelPkg.SaveAs(new FileInfo(filePath));
        }
    }

    public class JsonUtils
    {
        public static string SerializeObject(object obj)
        {
            if (obj == null) return string.Empty;

            DefaultContractResolver contractResolver = new DefaultContractResolver
            {
                NamingStrategy = new CamelCaseNamingStrategy()
            };

            return JsonConvert.SerializeObject(obj, new JsonSerializerSettings
            {
                ContractResolver = contractResolver,
                Formatting = Formatting.None
            });
        }

        ///
        /// Convert to JSON object from Stringified value
        ///
        ///
        ///
        /// 
        public static T DeserializeObject(string stringify) where T : class
        {
            if (stringify == null) return null;
            var result = JsonConvert.DeserializeObject(stringify);
            return result;
        }
    }

    internal class MyLogger
    {
        private static readonly ILog log = LogManager.GetLogger(typeof(MyLogger));

        public static ILog Log
        {
            get { return MyLogger.log; }
        }
    }

    #region Models

    public class InfoSchemaColumns
    {
        public string COLUMN_NAME { get; set; }
        public string IS_NULLABLE { get; set; }
        public string DATA_TYPE { get; set; }
    }

    #endregion Models

    #region Data Access Layer

    public class ConnectionFactory : IDisposable
    {
        public static string ConnectionString { get; } = ConfigurationManager.ConnectionStrings["MainConnectionString"].ConnectionString;

        //phương thức trả về đối tượng kết nối
        public static IDbConnection GetInstance()
        {
            IDbConnection connection = new SqlConnection(ConnectionString);
            return connection;
        }

        public void Dispose()
        {
            this.Dispose();
        }
    }

    public class StoredProcedureFactory
    {
        public string Execute(Dictionary<string, object> parameters, string spname)
        {
            var error = "";
            using (var con = ConnectionFactory.GetInstance())
            {
                con.Open();
                var param = new DynamicParameters();
                foreach (var key in parameters.Keys)
                {
                    param.Add(key, parameters[key]);
                }
                param.Add("Error", dbType: DbType.String, size: 4000, direction: ParameterDirection.Output);
                con.Execute(spname, param, commandType: CommandType.StoredProcedure);
                error = param.Get("Error");
            }
            return error;
        }

        public IEnumerable GetList(string spname)
        {
            IEnumerable data;
            using (var con = ConnectionFactory.GetInstance())
            {
                data = con.Query(spname, commandType: CommandType.StoredProcedure);
            }
            return data;
        }

        public T GetOneBy(Dictionary<string, object> parameters, string spname)
        {
            T entity;
            using (var con = ConnectionFactory.GetInstance())
            {
                var param = new DynamicParameters();
                foreach (var key in parameters.Keys)
                {
                    param.Add(key, parameters[key]);
                }
                entity = con.Query(spname, param, commandType: CommandType.StoredProcedure).FirstOrDefault();
            }
            return entity;
        }

        public IEnumerable GetListBy(Dictionary<string, object> parameters, string spname)
        {
            IEnumerable data;
            using (var con = ConnectionFactory.GetInstance())
            {
                var param = new DynamicParameters();
                foreach (var key in parameters.Keys)
                {
                    param.Add(key, parameters[key]);
                }
                data = con.Query(spname, param, commandType: CommandType.StoredProcedure);
            }
            return data;
        }

        public List GetMultiListBy(Dictionary<string, object> parameters, string spname)
        {
            List data = new List();
            using (var con = ConnectionFactory.GetInstance())
            {
                var param = new DynamicParameters();
                foreach (var key in parameters.Keys)
                {
                    param.Add(key, parameters[key]);
                }
                using (var multi = con.QueryMultiple(spname, param, commandType: CommandType.StoredProcedure))
                {
                    var list1 = multi.Read().FirstOrDefault();
                    var list2 = multi.Read().FirstOrDefault();
                    var list3 = multi.Read().FirstOrDefault();
                    var list4 = multi.Read().FirstOrDefault();
                    data.Add(list1);
                    data.Add(list2);
                    data.Add(list3);
                    data.Add(list4);
                }
            }
            return data;
        }
    }

    #endregion Data Access Layer
}