#include <iostream>
#include "uCalc.h"

using namespace std;
using namespace uCalcSoftware;

#define tf(IsTrue) ((IsTrue) ? "True" : "False")

int main() {
   uCalc uc;
   {
      uCalc::Transformer validator;
      validator.Owned(); // Causes validator to be released when it goes out of scope
      // 1. Configure the transformer
      validator.DefaultRuleSet().StatementSensitive(false);
      validator.SkipOver(";{line}"); // Ignore comments

      // 2. Define rules with validation constraints
      auto serverRule = validator.Pattern("'['Server']' {body}").SetMinimum(1).SetMaximum(1);
      serverRule.Description("Server Section");

      auto local_t = serverRule.LocalTransformer();
      auto hostRule = local_t.Pattern("Host = {@Alpha}").SetMinimum(1).SetMaximum(1);
      hostRule.Description("Host Key");

      auto portRule = local_t.Pattern("Port = {@Number}").SetMinimum(1);
      portRule.Description("Port Key");

      // --- Test Data ---
      auto validConfig = "[Server]\nHost = db1\nPort = 1433";
      auto invalidConfig = "Host = web1\nPort = 80"; // Missing [Server] section


      // --- Validate validConfig ---
      cout << "--- Validating valid_config.ini ---" << endl;
      validator.SetText(validConfig).Find();
      cout << "  Server section check passed: " << tf(serverRule.Matches().Count() == 1) << endl;
      cout << "  Host key check passed: " << tf(hostRule.Matches().Count() == 1) << endl;
      cout << "  Port key check passed: " << tf(portRule.Matches().Count() >= 1) << endl;
      cout << "" << endl;

      // --- Validate invalidConfig ---
      cout << "--- Validating invalid_config.ini ---" << endl;
      validator.SetText(invalidConfig).Find();
      cout << "  Server section check passed: " << tf(serverRule.Matches().Count() == 1) << endl;
      // The host and port rules will have 0 matches because their parent rule (serverRule) failed.
      cout << "  Host key check passed: " << tf(hostRule.Matches().Count() == 1) << endl;
      cout << "  Port key check passed: " << tf(portRule.Matches().Count() >= 1) << endl;
   }
}