/*
** Job Arranger for ZABBIX
** Copyright (C) 2025 Daiwa Institute of Research Ltd. All Rights Reserved.
**
** This program is free software; you can redistribute it and/or modify
** it under the terms of the GNU General Public License as published by
** the Free Software Foundation; either version 2 of the License, or
** (at your option) any later version.
**
** This program is distributed in the hope that it will be useful,
** but WITHOUT ANY WARRANTY; without even the implied warranty of
** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
** GNU General Public License for more details.
**
** You should have received a copy of the GNU General Public License
** along with this program; if not, write to the Free Software
** Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.
**/

package main

import (
	"jobarranger2/src/libs/golibs/common"
	"jobarranger2/src/libs/golibs/config_reader/server"
	"jobarranger2/src/libs/golibs/logger/logger"
	"jobarranger2/src/libs/golibs/utils"
)

var (
	JOBNETMANAGER_IN_DIR   string
	JOBNETMANAGER_RUN_DIR  string
	JOBNETMANAGER_WAIT_DIR string
	JOBNETMANAGER_END_DIR  string
	JobnetRunLogger        logger.Logging
	runJobnetTable         common.RunJobnetTable
)

const (
	IN    string = "in"
	RUN   string = "run"
	WAIT  string = "wait"
	END   string = "end"
	ERROR string = "error"
)

// Main entry: uses the dispatcher instead of a switch.
func ProcessEventData(data common.Data) {

	initJobnetManagerDirs(server.Options.TmpDir)

	// Idiomatic: check for nil and log error, return if not present
	if data.DBConn == nil {
		return
	}

	var eventData common.EventData
	err := utils.UnmarshalEventData(data.EventData, &eventData)
	if err != nil {
		return
	}

	var currentFilePath string
	if eventData.Event.Name == common.EventStandAloneJob || eventData.Event.Name == common.EventJobnetIconStop {
		currentFilePath = eventData.Transfer.Files[0].Source
	} else {
		currentFilePath = eventData.Transfer.Files[0].Destination
	}

	funcname := "ProcessEventData"
	JobnetRunLogger.JaLog("JAJOBNETRUN400001", `JobnetManager Run's`+funcname)
	event := eventData.Event.Name

	jobnetRunData, err := getJobnetRunData(eventData.NextProcess.Data)
	if err != nil {
		return
	}

	runJobnetTable, err = utils.GetRunJobnetTableDataByInnerJobnetId(data.DBConn, jobnetRunData.InnerJobnetId)
	if err != nil {
		return
	}

	JobnetRunLogger = logger.Logging{
		InnerJobnetMainID: runJobnetTable.InnerJobnetMainID,
		InnerJobnetID:     runJobnetTable.InnerJobnetID,
		UpdateDate:        runJobnetTable.UpdateDate,
		JobnetStatus:      common.StatusRun,
		RunType:           runJobnetTable.RunType,
		PublicFlag:        runJobnetTable.PublicFlag,
		JobnetID:          runJobnetTable.JobnetID,
		JobnetName:        runJobnetTable.JobnetName,
		UserName:          runJobnetTable.UserName,
	}

	dispatcher := NewEventDispatcher()
	dispatcher.Register(common.EventStandAloneJob, runHandler)
	dispatcher.Register(common.EventJobnetLoad, runHandler)
	dispatcher.Register(common.EventJobnetIconRun, runHandler)
	dispatcher.Register(common.EventJobnetTimeout, timeoutHandler)
	dispatcher.Register(common.EventIconTimeoutWarning, timeoutHandler)
	dispatcher.Register(common.EventDelayedStart, delayStartHandler)
	dispatcher.Register(common.EventScheduleDelete, scheduleDeleteHandler)
	dispatcher.Register(common.EventEndIconEnd, stopAndEndHandler)
	dispatcher.Register(common.EventJobnetStop, stopAndEndHandler)
	dispatcher.Register(common.EventJobnetIconStop, stopAndEndHandler)
	dispatcher.Register(common.EventJobnetRunError, runErrHandler)
	dispatcher.Register(common.EventDBJobnetRunQueryFailure, runErrHandler)
	dispatcher.Register(common.EventScheduleUpdate, scheduleUpdateHandler)
	dispatcher.Register(common.EventJobnetHold, holdHandler)
	dispatcher.Register(common.EventJobnetUnhold, unHoldHandler)
	dispatcher.Register(common.EventIconRunErrSkip, iconRerunHandler)
	dispatcher.Register(common.EventIconRerunStatusSync, iconRerunHandler)
	dispatcher.Register(common.EventFlowJobnetIconStatusChange, iconRerunHandler)

	if err := dispatcher.Dispatch(event, eventData, data.DBConn); err != nil {
		JobnetRunLogger.JaLog("JAJOBNETRUN200007", err, string(event), currentFilePath, jobnetRunData.InnerJobnetId)
		err = utils.MoveToSubFolder(currentFilePath, ERROR)
		if err != nil {
			return
		}
	}
	JobnetRunLogger.JaLog("JAJOBNETRUN400002", funcname)
}
