using System;
using System.IO;
using System.Threading;
using System.Windows.Forms;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using GEUTEBRUECK.GeViSoftSDKNET.ActionsWrapper;
using GEUTEBRUECK.GeViSoftSDKNET.ActionsWrapper.ActionDispatcher;
using GEUTEBRUECK.GeViSoftSDKNET.ActionsWrapper.SystemActions;
using GEUTEBRUECK.GeViSoftSDKNET.ActionsWrapper.DataBaseQueries;
using GEUTEBRUECK.GeViSoftSDKNET.ActionsWrapper.DataBaseAnswers;

namespace GeViSoftConfigReader
{
    public class MainForm : Form
    {
        private GeViDatabase database;
        private string[] args;

        public MainForm(string[] arguments)
        {
            this.args = arguments;
            this.Shown += MainForm_Shown;
            this.WindowState = FormWindowState.Minimized;
            this.ShowInTaskbar = false;
            this.Size = new System.Drawing.Size(1, 1);
        }

        private void MainForm_Shown(object sender, EventArgs e)
        {
            this.Hide();

            // Global exception handler - catch EVERYTHING
            try
            {
                File.WriteAllText(@"C:\GEVISOFT\SHOWN_EVENT_FIRED.txt", "Event fired at " + DateTime.Now);
                RunExport();
                File.WriteAllText(@"C:\GEVISOFT\RUNEXPORT_COMPLETED.txt", "RunExport completed at " + DateTime.Now);
            }
            catch (Exception ex)
            {
                try
                {
                    File.WriteAllText(@"C:\GEVISOFT\GLOBAL_EXCEPTION.txt",
                        "GLOBAL EXCEPTION at " + DateTime.Now + Environment.NewLine +
                        "Message: " + ex.Message + Environment.NewLine +
                        "Type: " + ex.GetType().FullName + Environment.NewLine +
                        "Stack: " + ex.StackTrace + Environment.NewLine +
                        "ToString: " + ex.ToString());
                }
                catch { /* Ultimate fallback - can't even write error */ }
            }
            finally
            {
                // Give file operations time to complete before exiting
                System.Threading.Thread.Sleep(2000);
                Application.Exit();
            }
        }

    private void RunExport()
        {
            string logFile = @"C:\GEVISOFT\GeViSoftConfigReader.log";
            void Log(string message)
            {
                try
                {
                    string logLine = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss") + ": " + message + Environment.NewLine;
                    File.AppendAllText(logFile, logLine);
                    // Also force flush by reopening
                    System.Threading.Thread.Sleep(10);
                }
                catch (Exception ex)
                {
                    File.WriteAllText(@"C:\GEVISOFT\log_error.txt",
                        "Log Error at " + DateTime.Now + Environment.NewLine + ex.ToString());
                }
            }

            try
            {
                // Write immediate confirmation that we entered this method
                File.WriteAllText(@"C:\GEVISOFT\runexport_started.txt",
                    "RunExport started at " + DateTime.Now + Environment.NewLine +
                    "Args count: " + (args != null ? args.Length.ToString() : "null"));
                System.Threading.Thread.Sleep(50); // Ensure file write completes

                // Delete old log if exists
                if (File.Exists(logFile))
                {
                    try { File.Delete(logFile); } catch { }
                }

                Log("=== GeViSoft Configuration Reader Started ===");
                Log("Working Directory: " + Directory.GetCurrentDirectory());
                Log("Application Path: " + Application.ExecutablePath);

                // Parse arguments with defaults
                string hostname = "localhost";
                string username = "sysadmin";
                string password = "masterkey";
                string outputFile = @"C:\GEVISOFT\geviSoft_config.json"; // Explicit full path

                if (args != null && args.Length >= 1) hostname = args[0];
                if (args != null && args.Length >= 2) username = args[1];
                if (args != null && args.Length >= 3) password = args[2];
                if (args != null && args.Length >= 4) outputFile = args[3];

                // Ensure output file has full path
                if (!Path.IsPathRooted(outputFile))
                {
                    outputFile = Path.Combine(@"C:\GEVISOFT", outputFile);
                }

                Log($"Server: {hostname}, User: {username}, Output: {outputFile}");
                Log("Creating database connection...");

                File.WriteAllText(@"C:\GEVISOFT\before_gevidatabase.txt",
                    "About to create GeViDatabase at " + DateTime.Now);

                database = new GeViDatabase();

                File.WriteAllText(@"C:\GEVISOFT\after_gevidatabase.txt",
                    "GeViDatabase created at " + DateTime.Now);

                Log("GeViDatabase object created successfully");
                Log($"Calling Create({hostname}, {username}, ***)");

                database.Create(hostname, username, password);
                Log("Create() completed, calling RegisterCallback()");

                database.RegisterCallback();
                Log("RegisterCallback() completed, calling Connect()");

                GeViConnectResult result = database.Connect();
                Log($"Connect() returned: {result}");

                if (result != GeViConnectResult.connectOk)
                {
                    Log($"ERROR: Connection failed: {result}");
                    File.WriteAllText(@"C:\GEVISOFT\connection_failed.txt",
                        "Connection failed: " + result.ToString());
                    return;
                }

                Log("Connected successfully!");

                JObject config = new JObject();
                config["ServerInfo"] = new JObject
                {
                    ["Hostname"] = hostname,
                    ["Connected"] = true,
                    ["ConnectionResult"] = result.ToString(),
                    ["Time"] = DateTime.Now.ToString("yyyy-MM-dd HH:mm:ss")
                };

                Log("Saving configuration to: " + outputFile);
                string jsonContent = config.ToString(Formatting.Indented);
                File.WriteAllText(outputFile, jsonContent);
                Log($"File written successfully. Size: {new FileInfo(outputFile).Length} bytes");

                Log($"SUCCESS! Config saved to: {outputFile}");

                database.Disconnect();
                database.Dispose();
                Log("Database disconnected and disposed");
            }
            catch (Exception ex)
            {
                string errorLog = @"C:\GEVISOFT\RUNEXPORT_ERROR.txt";
                try
                {
                    string errorInfo = "=== RUNEXPORT EXCEPTION ===" + Environment.NewLine +
                                     "Time: " + DateTime.Now + Environment.NewLine +
                                     "Message: " + ex.Message + Environment.NewLine +
                                     "Type: " + ex.GetType().FullName + Environment.NewLine +
                                     "Stack Trace:" + Environment.NewLine + ex.StackTrace + Environment.NewLine +
                                     Environment.NewLine + "Full ToString:" + Environment.NewLine + ex.ToString();

                    File.WriteAllText(errorLog, errorInfo);

                    // Try to log it too
                    try { Log("EXCEPTION: " + ex.Message); } catch { }
                }
                catch
                {
                    // Last resort - write minimal error
                    try { File.WriteAllText(@"C:\GEVISOFT\ERROR_WRITING_ERROR.txt", "Failed to write error log"); } catch { }
                }
            }
        }
    }
}
