package.path = "/usr/share/kses/templating/?.lua;"..package.path
--package.path = "/home/default/luatests/?.lua;"..package.path
package.path = "/srv/http/?.lua;"..package.path


require("luamods/command")
require("config/rsm_conf")
require("luamods/rsm_serials")


local loader = {}


retTable = {}
--package.path = "/home/dusty/git_repos/templating/?.lua;"..package.path




--package.path = "/home/default/luatests/?.lua;"..package.path
--package.path = "/srv/http/?.lua;"..package.path


local configPars = require("configParser")
local pretty = require("pl.pretty")
local xml = require("pl.xml")








function testIfDevicesMatch(dev1,dev2)

  local IsAMatch = true

  if dev1["Type"].__value__ ~= dev2["Type"].__value__ then
    IsAMatch = false
  end

  if dev1["Version"].__value__ ~= dev2["Version"].__value__ then
    IsAMatch = false
  end

  if dev1["NAnalogIn"].__value__ ~= dev2["NAnalogIn"].__value__ then
    IsAMatch = false
  end

  if dev1["NAnalogOut"].__value__ ~= dev2["NAnalogOut"].__value__ then
    IsAMatch = false
  end

  if dev1["NDiscIn"].__value__ ~= dev2["NDiscIn"].__value__ then
    IsAMatch = false
  end

  if dev1["NDiscOut"].__value__ ~= dev2["NDiscOut"].__value__ then
    IsAMatch = false
  end

  return IsAMatch
end



function getXmlContent(templateDir, filename)


  local savedXml = configPars.parse(templateDir..filename,"xml")
  --local savedXml = configPars.parse("templates/testwriting.xml","xml")

  if savedXml ~= nil then
    return savedXml
  else
    return nil
  end
end





function getCurrentDevices(templateDir, filename)


  local currentSetup = configParser.parse(templateDir..filename,"xml")
  --local currentSetup = configPars.parse("templates/testwriting.xml","xml")

  if currentSetup ~= nil then

    return currentSetup
  else
    return nil
  end
end


function setRsmDPorts(device, newDevId)

  --print("In set RSMD Ports")
  local cmd = rsm_conf.rsmc_path .. " SET:"

  --print("SETTING ANALOGS")
  local analogInEditor= require("analogIn")

  if device["Ports"]["Analog"] ~= nil then
    if device["Ports"]["Analog"][1] ~= nil then
      for key, port in ipairs(device["Ports"]["Analog"]) do
        local count = 1
        if port["type"].__value__ == 03 then
          cmd=cmd.." "..analogInEditor:getUpdateCommand(port, newDevId)
          command.ex(cmd)
        else
          print("Analog In port type doesnt match.")
        end
        if ((count % 3) == 0) then command.ex("sleep 1") end
      end
    else
      port = device["Ports"]["Analog"]
      --print("will update for device not array: "..newDevId)
      cmd=cmd.." "..analogInEditor:getUpdateCommand(port, newDevId)
      command.ex(cmd)

    end
  end

  --print("SETTING ANALOG OUTS")
  local analogOutEditor= require("analogOut")
  cmd = rsm_conf.rsmc_path .. " SET:"
  if device["Ports"]["AnalogOut"] ~= nil then
    if device["Ports"]["AnalogOut"][1] ~= nil then
      for key, port in ipairs(device["Ports"]["AnalogOut"]) do
        if port["type"].__value__ == 04 then
          cmd=cmd.." "..analogOutEditor:getUpdateCommand(port, newDevId)
          command.ex(cmd)
        else
          print("Analog Out port type doesnt match.")
        end

      end
    else
      port = device["Ports"]["AnalogOut"]
      --print("will update for device not array: "..newDevId)
      cmd=cmd.." "..analogOutEditor:getUpdateCommand(port, newDevId)
      command.ex(cmd)
    end
  end

  --print("SETTING INS")
  local InputsEditor= require("digitalIn")
  cmd = rsm_conf.rsmc_path .. " SET:"
  if device["Ports"]["Input"] ~= nil then
    if device["Ports"]["Input"][1] ~= nil then
      for key, port in ipairs(device["Ports"]["Input"]) do
        if port["type"].__value__ == "01" then
          --print("will update")
          cmd=cmd.." "..InputsEditor:getUpdateCommand(port, newDevId)
          command.ex(cmd)
        else
          print("Input port type doesnt match. Value: "..port["type"].__value__ )
        end
      end
    else
      port = device["Ports"]["Input"]
      --print("will update for device not array: "..newDevId)
      cmd=cmd.." "..InputsEditor:getUpdateCommand(port, newDevId)
      command.ex(cmd)

    end
  end

  --print("SETTING OUTS")
  local OutEditor= require("digitalOut")
  cmd = rsm_conf.rsmc_path .. " SET:"
  if device["Ports"]["Output"] ~= nil then
    if device["Ports"]["Output"][1] ~= nil then
      for key, port in ipairs(device["Ports"]["Output"]) do
        --print(pretty.write(port))
        if port["type"].__value__ == "02" then
          --print("will update out for device: "..newDevId)
          cmd=cmd.." "..OutEditor:getUpdateCommand(port, newDevId)
          command.ex(cmd)
          --OutEditor:updatePort(port, newDevId)
        else
          print("Output port type doesnt match.")
        end
      end
    else
      port = device["Ports"]["Output"]
      --print("will update out for device not array: "..newDevId)
      cmd=cmd.." "..OutEditor:getUpdateCommand(port, newDevId)
      command.ex(cmd)
    end
  end

  --print(cmd)


end

--uses the xml file to load all the devices from the various services
--doesnt load the ports.
function loadDevicesFromFile(SetupFromFile)

  --print("starting services again")

  command.ex(rsm_conf.sdd_down)
  command.ex(rsm_conf.mdd_down)
  command.ex(rsm_conf.ddd_down)
  command.ex(rsm_conf.fldd_down)
  command.ex(rsm_conf.wtr_down)
  command.ex(rsm_conf.cdd_down)

  --print("In loadDevicesFromFile")

  if SetupFromFile["site"]["snmpSummary"] ~= nil then
    local snmpManager = require("snmpEditor")
    snmpManager:writeXmlFiles(SetupFromFile["site"]["snmpSummary"])
  end



  if SetupFromFile["site"]["mddSummary"] ~= nil then
    local mddManager = require("mddEditor")
    mddManager:writeXmlFiles(SetupFromFile["site"]["mddSummary"])
  end

  if SetupFromFile["site"]["dddSummary"] ~= nil then
    local dddManager = require("dddEditor")
    dddManager:writeXmlFiles(SetupFromFile["site"]["dddSummary"])
  end

  if SetupFromFile["site"]["flddSummary"] ~= nil then
    local flddManager = require("flddEditor")
    flddManager:writeXmlFiles(SetupFromFile["site"]["flddSummary"])
  end

  if SetupFromFile["site"]["cddSummary"] ~= nil then
    local cddManager = require("cddEditor")
    cddManager:writeXmlFiles(SetupFromFile["site"]["cddSummary"])
  end

  if SetupFromFile["site"]["gsmSummary"] ~= nil then
    local gsmManager = require("gsmEditor")
    gsmManager:writeXmlFiles(SetupFromFile["site"]["gsmSummary"])
  end

  if SetupFromFile["site"]["staticSummary"] ~= nil then
    local staticManager = require("staticEditor")
    staticManager:writeXmlFiles(SetupFromFile["site"]["staticSummary"])
  end

  --starting services again
  command.ex(rsm_conf.sdd_up)
  command.ex(rsm_conf.mdd_up)
  command.ex(rsm_conf.ddd_up)
  command.ex(rsm_conf.fldd_up)
  command.ex(rsm_conf.wtr_up)
  command.ex(rsm_conf.cdd_up)





end

function loadRsmDprofile(currentSummary)
  --print("IN loadRsmDprofile")

  local deviceEditor = require("device")
  local devices = deviceEditor:getAllDevices()

  if currentSummary["site"]["device"][1] ~= nil then
    for curkey, curdev in ipairs(currentSummary["site"]["device"]) do
      for key, dev in ipairs(devices) do
        local matching = testIfDevicesMatch(curdev,dev)
        if matching == true and dev["used"] == nil   then
          --print("Devices match devid: "..dev["Id"].__value__.. " used")
          setRsmDPorts(curdev, dev["Id"].__value__)
          dev["used"] = true
        elseif matching == true and dev["used"] ~= nil then
          --print("match but used")
        else
          --print("Devices DONT match")
        end
      end
    end
  else
    --print("Single device match: ")
    local curdev = currentSummary["site"]["device"]
    local dev = devices[1]

    setRsmDPorts(curdev, dev["Id"].__value__)

  end
end

--Used when just wanting to load the devices and their configs and not their ports
--ie stage 2 of loading full config
function loader:loadConfigToFile(templateDir,filename,profile)

  --print("IN loadConfiFile")
  if profile == "RsmD" then
    --print("trying to getCurrentDevices")
    local currSetup = getXmlContent(templateDir, filename)
    if currSetup ~= nil then
      loadRsmDprofile(currSetup)
    else
      print("currSetup is nil")
      return nil
    end
  else
    return nil
  end
end

--Used when just wanting to load the devices and their configs and not their ports
--ie stage 1 of loading full config
function loader:loadSiteConfig(templateDir,filename)

  --print("trying to getCurrentDevices")
  local currSetup = getXmlContent(templateDir, filename)
  if currSetup ~= nil then
    loadDevicesFromFile(currSetup)
  else
    print("currSetup is nil")
    return nil
  end
end




return loader
