* rar_forms.prg
#Define C_FORM_WIDTH  800
#Define C_FORM_HEIGHT 600
#Define C_BTN_WIDTH   120
#Define C_BTN_HEIGHT  30
#Define C_API_TIMEOUT 30

Close Databases All
Set Century On
Set Exact On
Set Ansi On
Set Deleted On
Set Date Dmy
Set Hours To 24
Set Notify Off
Set Safety Off

lcPath = Justpath(Sys(16,0))
Set Default To (m.lcPath)

Set Procedure To rar_autopass Additive
Set Procedure To nfjsonread Additive

Do Main

* Form principal pentru managementul RAR AutoPass
Define Class RarAutoPassForm As Form
	Caption = "RAR AutoPass Manager"
	Width = C_FORM_WIDTH
	Height = C_FORM_HEIGHT
	AutoCenter = .T.
	MaxButton = .F.
	WindowType = 1
	BackColor = Rgb(240,240,240)

	* Membri privati
	Hidden oRar
	Hidden nTimerHandle
	Hidden cLastXmlPath

	ErrorMsg = ""

	* Adaugam PageFrame-ul ?i paginile sale
	Add Object PageFrame1 As PageFrame With ;
		Left = 10, ;
		Top = 10, ;
		Width = C_FORM_WIDTH - 20, ;
		Height = C_FORM_HEIGHT - 80, ;
		PageCount = 4, ;
		Visible = .T.

	Function Init
		Local loRar, llSuccess, llTestMode
		llSuccess = .F.
		llTestMode = .T.

		Try
			* Adaugam controalele pentru fiecare pagina
			This.SetupPage1()  && Procesare
			This.SetupPage2()  && Mapari
			This.SetupPage3()  && Monitorizare
			This.SetupPage4()  && Prezentari

			* Initializare RAR AutoPass
			This.oRar = Createobject("RarAutoPass")
			If !This.oRar.SetCredentials(m.llTestMode)
				Messagebox("Eroare setare credentiale: " + This.oRar.ErrorMsg, 16, "Eroare")
				llSuccess = .F.
				Return llSuccess
			Endif

			* Deschidem tabelele necesare
			Use mapare_prestatii In 0 Shared
			Use rar_log In 0 Shared
			Use prestatii_rar In 0 Shared

			Create Cursor xml_preview ;
				(nr_comanda C(20), ;
				data D, ;
				vin C(20), ;
				nr_inm C(10), ;
				km_final N(10), ;
				km_init N(10), ;
				observatii M)

			This.SetupGridMapari()
			This.SetupGridLog()
			This.SetupLogFilter()

			This.nTimerHandle = 0
			This.cLastXmlPath = ""

			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la initializarea formularului: " + ;
				loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Setup pentru Page1 (Procesare Comenzi)
	Function SetupPage1
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page1
				.Caption = "Procesare Comenzi"

				.AddObject("lblXmlPath", "Label")
				With .lblXmlPath
					.Caption = "Fisier XML:"
					.Left = 20
					.Top = 20
					.Visible = .T.
				Endwith

				.AddObject("txtXmlPath", "TextBox")
				With .txtXmlPath
					.Left = 100
					.Top = 20
					.Width = 500
					.Visible = .T.
				Endwith

				.AddObject("btnBrowse", "CommandButton")
				With .btnBrowse
					.Caption = "..."
					.Left = 610
					.Top = 20
					.Width = 30
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				* Ata?am handler-ul pentru evenimentul Click
				Bindevent(.btnBrowse, "Click", This, "OnBrowseClick")

				.AddObject("btnProcess", "CommandButton")
				With .btnProcess
					.Caption = "Proceseaza"
					.Left = 20
					.Top = 60
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				* Ata?am handler-ul pentru evenimentul Click
				Bindevent(.btnProcess, "Click", This, "OnProcessClick")

				.AddObject("chkAutoProcess", "CheckBox")
				With .chkAutoProcess
					.Caption = "Procesare automata"
					.Left = 160
					.Top = 65
					.AutoSize = .T.
					.Visible = .T.
				Endwith

				* Ata?am handler pentru AutoProcess
				Bindevent(.chkAutoProcess, "InteractiveChange", This, "OnAutoProcessChange")

				.AddObject("txtInterval", "TextBox")
				With .txtInterval
					.Left = 300
					.Top = 65
					.Width = 50
					.Value = "5"
					.Visible = .T.
				Endwith

				.AddObject("lblMinute", "Label")
				With .lblMinute
					.Caption = "minute"
					.Left = 360
					.Top = 65
					.Visible = .T.
				Endwith

				.AddObject("edtStatus", "EditBox")
				With .edtStatus
					.Left = 20
					.Top = 100
					.Width = 700
					.Height = 200
					.ReadOnly = .T.
					.ScrollBars = 2
					.Visible = .T.
				Endwith

				.AddObject("grdPreview", "Grid")
				With .grdPreview
					.Left = 20
					.Top = 320
					.Width = 700
					.Height = 200
					.ReadOnly = .T.
					.Visible = .F.

					.ColumnCount = 7

					.Column1.Header1.Caption = "Nr. Comanda"
					.Column1.Width = 100

					.Column2.Header1.Caption = "Data"
					.Column2.Width = 80

					.Column3.Header1.Caption = "VIN"
					.Column3.Width = 120

					.Column4.Header1.Caption = "Nr. Inmatriculare"
					.Column4.Width = 100

					.Column5.Header1.Caption = "KM Final"
					.Column5.Width = 80

					.Column6.Header1.Caption = "KM Initial"
					.Column6.Width = 80

					.Column7.Header1.Caption = "Observatii"
					.Column7.Width = 140
				Endwith

				.AddObject("lblPreview", "Label")
				With .lblPreview
					.Caption = "Preview comenzi din XML:"
					.Left = 20
					.Top = 300
					.Visible = .F.
				Endwith
			Endwith

			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup Page1: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Continuare din partea anterioara...

	* Setup pentru Page2 (Mapare Operatii)
	Function SetupPage2
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page2
				.Caption = "Mapare Operatii"

				.AddObject("Grid1", "Grid")
				With .Grid1
					.Left = 20
					.Top = 20
					.Width = 700
					.Height = 300
					.AllowAddNew = .T.
					.DeleteMark = .F.
					.Visible = .T.
				Endwith

				.AddObject("btnSaveMapari", "CommandButton")
				With .btnSaveMapari
					.Caption = "Salveaza"
					.Left = 20
					.Top = 330
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				.AddObject("btnRefreshNomenclator", "CommandButton")
				With .btnRefreshNomenclator
					.Caption = "Actualizare Nomenclator"
					.Left = 150
					.Top = 330
					.Width = 150
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				Bindevent(.btnSaveMapari, "Click", This, "OnSaveMappingsClick")
				Bindevent(.btnRefreshNomenclator, "Click", This, "OnRefreshNomenclatorClick")
			Endwith

			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup Page2: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Setup pentru Page3 (Monitorizare)
	Function SetupPage3
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page3
				.Caption = "Monitorizare"

				.AddObject("Grid2", "Grid")
				With .Grid2
					.Left = 20
					.Top = 50
					.Width = 700
					.Height = 300
					.Visible = .T.
				Endwith

				.AddObject("cboLogFilter", "ComboBox")
				With .cboLogFilter
					.Left = 20
					.Top = 20
					.Width = 150
					.Style = 2
					.Visible = .T.

					.AddItem("Toate")
					.AddItem("Succes")
					.AddItem("Erori")
					.ListIndex = 1
				Endwith

				.AddObject("btnRefreshLog", "CommandButton")
				With .btnRefreshLog
					.Caption = "Refresh"
					.Left = 180
					.Top = 20
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				.AddObject("btnAdvSearch", "CommandButton")
				With .btnAdvSearch
					.Caption = "Cautare avansata"
					.Left = 320
					.Top = 20
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				.AddObject("btnExportExcel", "CommandButton")
				With .btnExportExcel
					.Caption = "Export Excel"
					.Left = 450
					.Top = 20
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				* Ata?am event handlers
				Bindevent(.cboLogFilter, "InteractiveChange", This, "OnLogFilterChange")
				Bindevent(.btnRefreshLog, "Click", This, "OnRefreshLogClick")
				Bindevent(.btnAdvSearch, "Click", This, "OnAdvSearchClick")
				Bindevent(.btnExportExcel, "Click", This, "OnExportExcelClick")
			Endwith

			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup Page3: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Setup pentru Page4 (Prezentari Finalizate)
	Function SetupPage4
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page4
				.Caption = "Prezentari Finalizate"

				* Grid pentru prezentari
				.AddObject("grdPrezentari", "Grid")
				With .grdPrezentari
					.Left = 20
					.Top = 50
					.Width = 700
					.Height = 300
					.ReadOnly = .T.
					.DeleteMark = .F.
					.Visible = .T.

					.ColumnCount = 7
					.Column1.Header1.Caption = "ID"
					.Column1.Width = 60
					.Column2.Header1.Caption = "Data Presta?ie"
					.Column2.Width = 100
					.Column3.Header1.Caption = "VIN"
					.Column3.Width = 120
					.Column4.Header1.Caption = "Nr. Înmatriculare"
					.Column4.Width = 100
					.Column5.Header1.Caption = "Km Final"
					.Column5.Width = 80
					.Column6.Header1.Caption = "Status"
					.Column6.Width = 80
					.Column7.Header1.Caption = "Observa?ii"
					.Column7.Width = 160
				Endwith

				* Buton refresh prezentari
				.AddObject("btnRefreshPrez", "CommandButton")
				With .btnRefreshPrez
					.Caption = "Actualizeaza"
					.Left = 20
					.Top = 20
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				* Buton anulare prezentare
				.AddObject("btnAnulare", "CommandButton")
				With .btnAnulare
					.Caption = "Anuleaza Prezentare"
					.Left = 150
					.Top = 20
					.Width = C_BTN_WIDTH
					.Height = C_BTN_HEIGHT
					.Visible = .T.
				Endwith

				* Ata?am event handlers
				Bindevent(.btnRefreshPrez, "Click", This, "OnRefreshPrezentariClick")
				Bindevent(.btnAnulare, "Click", This, "OnAnularePrezentareClick")
			Endwith

			* Cream cursor pentru prezentari
			If Used("prezentari_fin")
				Use In prezentari_fin
			Endif

			Create Cursor prezentari_fin ;
				(Id I, ;
				data_prestatie D, ;
				vin C(20), ;
				nr_inmatriculare C(10), ;
				odometru_final N(10), ;
				status C(20), ;
				observatii M)

			* Setam sursa pentru grid
			This.PageFrame1.Page4.grdPrezentari.RecordSource = "prezentari_fin"
			With This.PageFrame1.Page4.grdPrezentari
				.Column1.ControlSource = "prezentari_fin.id"
				.Column2.ControlSource = "prezentari_fin.data_prestatie"
				.Column3.ControlSource = "prezentari_fin.vin"
				.Column4.ControlSource = "prezentari_fin.nr_inmatriculare"
				.Column5.ControlSource = "prezentari_fin.odometru_final"
				.Column6.ControlSource = "prezentari_fin.status"
				.Column7.ControlSource = "prezentari_fin.observatii"
			Endwith

			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup Page4: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Event Handlers pentru Page1
	Function OnBrowseClick
		Local lcFile
		lcFile = Getfile("XML", "Alege fisier XML", "Deschide", 0)
		If !Empty(lcFile)
			This.PageFrame1.Page1.txtXmlPath.Value = lcFile
			This.AddStatus("Fisier selectat: " + lcFile)
			This.ParseXMLToPreview(lcFile)
		Endif
	Endfunc

	Function OnProcessClick
		Local lcFile
		lcFile = This.PageFrame1.Page1.txtXmlPath.Value
		If Empty(lcFile)
			Messagebox("Selecta?i un fisier XML!", 16, "Aten?ie")
			Return
		Endif

		This.ProcessXML(lcFile)
	Endfunc

	Function OnAutoProcessChange
		Local loControl
		loControl = This.PageFrame1.Page1.chkAutoProcess

		If loControl.Value
			This.StartAutoProcessing()
		Else
			This.StopAutoProcessing()
		Endif
	Endfunc

	* Event Handlers pentru Page3 (Monitorizare)
	Function OnLogFilterChange
		Lparameters toControl
		Local lcFilter

		Do Case
			Case toControl.ListIndex = 1  && Toate
				lcFilter = ""
			Case toControl.ListIndex = 2  && Succes
				lcFilter = "status = 'SUCCESS'"
			Case toControl.ListIndex = 3  && Erori
				lcFilter = "status = 'ERROR'"
		Endcase

		This.ApplyLogFilter(lcFilter)
	Endfunc

	Function OnRefreshLogClick
		Select rar_log
		Use In rar_log
		Use rar_log In 0 Shared
		Go Top
		This.PageFrame1.Page3.Grid2.Refresh()
		This.AddStatus("Log actualizat.")
	Endfunc

	Function OnAdvSearchClick
		Do Form search_log
		This.PageFrame1.Page3.Grid2.Refresh()
	Endfunc

	* Event Handlers pentru Page4 (Prezentari)
	Function OnRefreshPrezentariClick
		This.RefreshPrezentari()
	Endfunc

	Function OnAnularePrezentareClick
		This.AnularePrezentare(prezentari_fin.id)
	Endfunc

	* Func?ii utilitare
	Function AddStatus
		Lparameters tcMessage
		With This.PageFrame1.Page1.edtStatus
			.Value = .Value + Ttoc(Datetime()) + ": " + tcMessage + Chr(13) + Chr(10)
			.SelStart = Len(.Value)
		Endwith
	Endfunc

	Function ApplyLogFilter
		Parameter tcFilter
		Select rar_log
		If !Empty(tcFilter)
			Set Filter To &tcFilter
		Else
			Set Filter To
		Endif
		Go Top
		This.PageFrame1.Page3.Grid2.Refresh()
	Endfunc

	* Func?ii pentru procesare XML
	Function ParseXMLToPreview
		Parameters tcXMLFile
		Local loXML As MSXML2.DOMDocument.6.0
		Local loNodes As MSXML2.IXMLDOMNodeList
		Local loNode As MSXML2.IXMLDOMNode
		Local llSuccess, lcData
		llSuccess = .F.

		Try
			loXML = Createobject("MSXML2.DOMDocument.6.0")
			loXML.Async = .F.

			If !loXML.Load(tcXMLFile)
				This.ErrorMsg = "Eroare incarcare XML: " + loXML.parseError.reason
				This.AddStatus(This.ErrorMsg)
				llSuccess = .F.
				Return llSuccess
			Endif

			* Obtinem toate nodurile de comenzi
			loNodes = loXML.selectNodes("/comenzi/comanda")

			If Used("xml_preview")
				Select xml_preview
				Delete All
			Endif

			For Each loNode In loNodes
				lcData = loNode.selectSingleNode("data").Text

				ldData = This.Data2Date(m.lcData)
				Insert Into xml_preview ;
					(nr_comanda, ;
					data, ;
					vin, ;
					nr_inm, ;
					km_final, ;
					km_init, ;
					observatii) ;
					VALUES ;
					(loNode.selectSingleNode("nr_comanda").Text, ;
					M.ldData, ;
					loNode.selectSingleNode("vin").Text, ;
					loNode.selectSingleNode("nr_inmatriculare").Text, ;
					VAL(loNode.selectSingleNode("km_final").Text), ;
					VAL(loNode.selectSingleNode("km_initial").Text), ;
					NVL(loNode.selectSingleNode("observatii").Text, ""))
			Endfor

			Go Top
			This.PageFrame1.Page1.grdPreview.Refresh()
			This.PageFrame1.Page1.grdPreview.Visible = .T.
			This.PageFrame1.Page1.lblPreview.Visible = .T.

			This.AddStatus("XML citit cu succes: " + Transform(Reccount()) + " comenzi")
			llSuccess = .T.

		Catch To loError
			This.ErrorMsg = "Eroare parsare XML: " + loError.Message
			This.AddStatus(This.ErrorMsg)
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Func?ii pentru prezentari
	Function RefreshPrezentari
		Local llSuccess
		llSuccess = .F.

		This.AddStatus("Actualizare prezentari...")
		Try
			If !This.oRar.Login()
				This.AddStatus("Eroare login: " + This.oRar.ErrorMsg)
				Return .F.
			Endif

			This.oRar.loXMLHTTP.Open("GET", This.oRar.lcUrl + "/prezentari/getAllPrezentariFinalizate", .F.)
			This.oRar.loXMLHTTP.setRequestHeader("Authorization", "Bearer " + This.oRar.lcToken)
			This.oRar.loXMLHTTP.Send()

			If This.oRar.loXMLHTTP.Status != 200
				This.ErrorMsg = "Eroare obtinere prezentari: " + This.oRar.loXMLHTTP.responseText
				This.AddStatus(This.ErrorMsg)
				Return .F.
			Endif

			loJson = nfjsonread(This.oRar.loXMLHTTP.responseText)

			If Type('loJson.data.content') == 'O'
				Select prezentari_fin
				Delete All

				For Each loItem In loJson.Data.content
					ldData = This.Data2Date(loItem.dataPrestatie)

					Insert Into prezentari_fin ;
						(Id, ;
						data_prestatie, ;
						vin, ;
						nr_inmatriculare, ;
						odometru_final, ;
						status, ;
						observatii) ;
						VALUES ;
						(loItem.Id, ;
						M.ldData, ;
						loItem.vin, ;
						loItem.nrInmatriculare, ;
						loItem.odometruFinal, ;
						loItem.Status, ;
						loItem.obs)
				Endfor

				Go Top
				This.PageFrame1.Page4.grdPrezentari.Refresh()
				This.AddStatus("Prezentari actualizate cu succes.")
				llSuccess = .T.
			Endif

		Catch To loError
			This.ErrorMsg = "Eroare actualizare prezentari: " + loError.Message
			This.AddStatus(This.ErrorMsg)
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Anulare prezentare
	Function AnularePrezentare
		Parameters tnIdPrezentare
		Local llSuccess
		llSuccess = .F.

		If !This.oRar.Login()
			Return .F.
		Endif

		Try
			* Facem request de tip PATCH pentru anulare
			This.oRar.loXMLHTTP.Open("PATCH", ;
				THIS.oRar.lcUrl + "/prezentari/markPrezentareAnulataById/" + ALLTRIM(Transform(tnIdPrezentare)), ;
				.F.)
			This.oRar.loXMLHTTP.setRequestHeader("Authorization", "Bearer " + This.oRar.lcToken)
			This.oRar.loXMLHTTP.Send()

			This.oRar.LastResponse = This.oRar.loXMLHTTP.responseText

			* Parsam raspunsul JSON pentru a verifica statusul
			loResponse = nfjsonread(This.oRar.LastResponse)

			Do Case
				Case This.oRar.loXMLHTTP.Status != 200
					This.ErrorMsg = "Eroare la anularea prezentarii: " + This.oRar.LastResponse
					This.AddStatus(This.ErrorMsg)
					llSuccess = .F.


				Case Type('loResponse.STATUS_ANULATA') = 'C'
					* Anulare reusita
					This.AddStatus('Anulare reusita ID: ' + ALLTRIM(TRANSFORM(tnIdPrezentare)))					

					llSuccess = .T.
					This.oRar.LogPrezentare(Ttoc(Date()), ;
						"", ;                 && nr_comanda
					"", ;                 && vin
					"", ;                 && nr_inm
					0, ;                  && km_final
					0, ;                  && km_initial
					"", ;                 && prestatii
					"ANULATA", ;          && status
					loResponse.STATUS_ANULATA)     && mesaj succes
					This.AddStatus('Prezentare anulata')

				Case Type('loResponse.EROARE_STATUS_ANULARE') = 'C'
					This.ErrorMsg = loResponse.EROARE_STATUS_ANULARE
					This.oRar.LogPrezentare(Ttoc(Date()), ;
						"", ;
						"", ;
						"", ;
						0, ;
						0, ;
						"", ;
						"ERROR", ;
						THIS.ErrorMsg)
						
					This.AddStatus(This.ErrorMsg)						
					llSuccess = .F.

				Otherwise
					This.ErrorMsg = "Raspuns neasteptat: " + This.oRar.LastResponse
					This.AddStatus(This.ErrorMsg)					
					llSuccess = .F.

			Endcase

		Catch To loEx
			This.ErrorMsg = "Eroare anulare prezentare: " + loEx.Message
			This.AddStatus(This.ErrorMsg)				
			llSuccess = .F.
		Endtry

		* Actualizam statusul in log daca exista inregistrarea
		If Used("rar_log")
			Select rar_log
			Locate For Id = tnIdPrezentare
			If Found()
				Replace Status With Iif(llSuccess, "ANULATA", "ERROR"), ;
					error_msg With Iif(!llSuccess, This.ErrorMsg, ""), ;
					data_trim With Datetime()
			Endif
		Endif

		Return llSuccess
	Endfunc

	* Func?ii pentru procesare automata
	Function StartAutoProcessing
		Local lnInterval

		If !Empty(This.nTimerHandle)
			Return
		Endif

		lnInterval = Val(This.PageFrame1.Page1.txtInterval.Value)
		If lnInterval <= 0
			Messagebox("Interval invalid!", 16, "Eroare")
			This.PageFrame1.Page1.chkAutoProcess.Value = .F.
			Return
		Endif

		* Convertim intervalul din minute în milisecunde
		lnInterval = lnInterval * 60 * 1000

		This.nTimerHandle = _Screen.AddProperty("Timer" + Sys(2015), ;
			NEWOBJECT("Timer"))

		With _Screen.&("Timer" + Sys(2015))
			.Interval = lnInterval
			Bindevent(.Timer, This, "OnAutoProcessTimer")
			.Enabled = .T.
		Endwith

		This.AddStatus("Procesare automata pornita. Interval: " + ;
			TRANSFORM(Val(This.PageFrame1.Page1.txtInterval.Value)) + " minute")
	Endfunc

	Function StopAutoProcessing
		If !Empty(This.nTimerHandle)
			_Screen.RemoveObject("Timer" + Sys(2015))
			This.nTimerHandle = 0
			This.AddStatus("Procesare automata oprita.")
		Endif
	Endfunc

	Function OnAutoProcessTimer
		Local lcFile
		lcFile = This.PageFrame1.Page1.txtXmlPath.Value

		If !Empty(lcFile) And File(lcFile)
			This.ProcessXML(lcFile)
		Else
			This.AddStatus("EROARE: Fi?ier XML invalid sau lipsa!")
			This.StopAutoProcessing()
			This.PageFrame1.Page1.chkAutoProcess.Value = .F.
		Endif
	Endfunc


	* Event Handlers pentru Page2 (Mapari)
	Function OnSaveMappingsClick
		Local llSuccess
		llSuccess = .F.

		Try
			Select mapare_prestatii
			Tableupdate(.T.)
			Messagebox("Mapari salvate cu succes!", 64, "Succes")
			llSuccess = .T.
			This.AddStatus("Mapari actualizate cu succes.")

		Catch To loError
			Messagebox("Eroare salvare mapari: " + loError.Message, 16, "Eroare")
			This.AddStatus("EROARE salvare mapari: " + loError.Message)
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	Function OnRefreshNomenclatorClick
		Local llSuccess
		llSuccess = .F.

		Wait Window "Actualizare nomenclator în curs..." Nowait

		Try
			If !This.oRar.UpdateNomenclator(.T.)
				Messagebox("Eroare actualizare nomenclator: " + This.oRar.ErrorMsg, 16, "Eroare")
				This.AddStatus("EROARE actualizare nomenclator: " + This.oRar.ErrorMsg)
				llSuccess = .F.
			Else
				Messagebox("Nomenclator actualizat cu succes!", 64, "Succes")
				This.AddStatus("Nomenclator actualizat cu succes.")
				llSuccess = .T.

				* Reîmprospatam grid-ul cu mapari
				Select mapare_prestatii
				Go Top
				This.PageFrame1.Page2.Grid1.Refresh()
			Endif

		Catch To loError
			Messagebox("Eroare actualizare nomenclator: " + loError.Message, 16, "Eroare")
			This.AddStatus("EROARE actualizare nomenclator: " + loError.Message)
			llSuccess = .F.
		Finally
			Wait Clear
		Endtry

		Return llSuccess
	Endfunc

	* Functii pentru procesare XML
	Function ProcessXML
		Parameters tcXMLFile
		Local llSuccess
		llSuccess = .F.

		This.AddStatus("Procesare " + tcXMLFile + "...")

		Try
			If !This.oRar.ProcessXMLComenzi(tcXMLFile)
				This.AddStatus("EROARE: " + This.oRar.ErrorMsg)
				Messagebox(This.oRar.ErrorMsg, 16, "Eroare")
				llSuccess = .F.
			Else
				This.AddStatus("Procesare finalizata cu succes!")
				Messagebox("Procesare finalizata cu succes!", 64, "Succes")
				llSuccess = .T.
			Endif

		Catch To loError
			This.AddStatus("EROARE: " + loError.Message)
			Messagebox(loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Handler pentru activare/dezactivare procesare automata
	Function OnAutoProcessChange
		Local loControl
		loControl = This.PageFrame1.Page1.chkAutoProcess

		If loControl.Value
			This.StartAutoProcessing()
		Else
			This.StopAutoProcessing()
		Endif
	Endfunc

	* Handler pentru timer procesare automata
	Function OnAutoProcessTimer
		Local lcFile
		lcFile = This.PageFrame1.Page1.txtXmlPath.Value

		If !Empty(lcFile) And File(lcFile)
			This.ProcessXML(lcFile)
		Else
			This.AddStatus("EROARE: Fi?ier XML invalid sau lipsa!")
			This.StopAutoProcessing()
			This.PageFrame1.Page1.chkAutoProcess.Value = .F.
		Endif
	Endfunc


	* Export Excel pentru log
	Function OnExportExcelClick
		Local lcFile, loExcel, loWorkbook, loWorksheet
		Local lnRow, lnCol

		lcFile = Putfile("Excel files|*.xlsx", "RAR_Log_Export.xlsx", "", 0)
		If Empty(lcFile)
			Return
		Endif

		This.AddStatus("Export Excel în " + lcFile + "...")

		Try
			loExcel = Createobject("Excel.Application")
			loExcel.Visible = .F.

			loWorkbook = loExcel.Workbooks.Add()
			loWorksheet = loWorkbook.Sheets(1)

			* Setam headerele
			With loWorksheet
				.Cells(1,1).Value = "Data prezentare"
				.Cells(1,2).Value = "Nr. comanda"
				.Cells(1,3).Value = "VIN"
				.Cells(1,4).Value = "Nr. înmatriculare"
				.Cells(1,5).Value = "Km final"
				.Cells(1,6).Value = "Km initial"
				.Cells(1,7).Value = "Status"
				.Cells(1,8).Value = "Eroare"
				.Cells(1,9).Value = "Data trimitere"

				* Formatare header
				.Range(.Cells(1,1), .Cells(1,9)).Font.Bold = .T.
				.Range(.Cells(1,1), .Cells(1,9)).Interior.Color = Rgb(200,200,200)
			Endwith

			* Populam datele
			Select rar_log
			lnRow = 2
			Scan
				loWorksheet.Cells(lnRow, 1).Value = Dtoc(data_prez)
				loWorksheet.Cells(lnRow, 2).Value = nr_comanda
				loWorksheet.Cells(lnRow, 3).Value = vin
				loWorksheet.Cells(lnRow, 4).Value = nr_inm
				loWorksheet.Cells(lnRow, 5).Value = Transform(km_final)
				loWorksheet.Cells(lnRow, 6).Value = Transform(km_init)
				loWorksheet.Cells(lnRow, 7).Value = Status
				loWorksheet.Cells(lnRow, 8).Value = error_msg
				loWorksheet.Cells(lnRow, 9).Value = Ttoc(data_trim)

				* Coloram randurile cu erori in rosu deschis
				If Status = "ERROR"
					loWorksheet.Range(loWorksheet.Cells(lnRow,1), ;
						loWorksheet.Cells(lnRow,9)).Interior.Color = Rgb(255,200,200)
				Endif

				lnRow = lnRow + 1
			Endscan

			* Auto-fit coloane
			loWorksheet.Range("A:I").Columns.AutoFit()

			* Salvam si inchidem
			loWorkbook.SaveAs(lcFile)
			loWorkbook.Close()
			loExcel.Quit()

			This.AddStatus("Export Excel finalizat cu succes")

			* Deschidem fisierul
			Run /N "explorer.exe" &lcFile

		Catch To loError
			This.AddStatus("EROARE la export Excel: " + loError.Message)
			Messagebox("Eroare la export Excel: " + loError.Message, 16, "Eroare")

			Try
				loWorkbook.Close()
				loExcel.Quit()
			Catch
			Endtry
		Endtry
	Endfunc

	* Refresh pentru grid-ul de log
	Function OnRefreshLogClick
		Select rar_log
		Use In rar_log
		Use rar_log In 0 Shared
		Go Top
		This.PageFrame1.Page3.Grid2.Refresh()
		This.AddStatus("Log actualizat.")
	Endfunc

	* Cautare avansata în log
	Function OnAdvSearchClick
		Local loSearch
		loSearch = Createobject("SearchLogForm")
		loSearch.Show(1)
		This.PageFrame1.Page3.Grid2.Refresh()
	Endfunc

	* Handler pentru filtrul de log
	Function OnLogFilterChange
		Lparameters toControl
		Local lcFilter

		Do Case
			Case toControl.ListIndex = 1  && Toate
				lcFilter = ""
			Case toControl.ListIndex = 2  && Succes
				lcFilter = "status = 'SUCCESS'"
			Case toControl.ListIndex = 3  && Erori
				lcFilter = "status = 'ERROR'"
		Endcase

		This.ApplyLogFilter(lcFilter)
	Endfunc

	* Aplicare filtru pentru log
	Function ApplyLogFilter
		Parameter tcFilter
		Select rar_log
		If !Empty(tcFilter)
			Set Filter To &tcFilter
		Else
			Set Filter To
		Endif
		Go Top
		This.PageFrame1.Page3.Grid2.Refresh()
	Endfunc

	* Helper pentru procesare automata
	Function StartAutoProcessing
		Local lnInterval

		If !Empty(This.nTimerHandle)
			Return
		Endif

		lnInterval = Val(This.PageFrame1.Page1.txtInterval.Value)
		If lnInterval <= 0
			Messagebox("Interval invalid!", 16, "Eroare")
			This.PageFrame1.Page1.chkAutoProcess.Value = .F.
			Return
		Endif

		* Convertim intervalul din minute în milisecunde
		lnInterval = lnInterval * 60 * 1000

		This.nTimerHandle = _Screen.AddProperty("Timer" + Sys(2015), ;
			NEWOBJECT("Timer"))

		With _Screen.&("Timer" + Sys(2015))
			.Interval = lnInterval
			Bindevent(.Timer, This, "OnAutoProcessTimer")
			.Enabled = .T.
		Endwith

		This.AddStatus("Procesare automata pornita. Interval: " + ;
			TRANSFORM(Val(This.PageFrame1.Page1.txtInterval.Value)) + " minute")
	Endfunc

	Function StopAutoProcessing
		If !Empty(This.nTimerHandle)
			_Screen.RemoveObject("Timer" + Sys(2015))
			This.nTimerHandle = 0
			This.AddStatus("Procesare automata oprita.")
		Endif
	Endfunc


	Function SetupLogFilter
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page3.cboLogFilter
				.Clear()
				.AddItem("Toate")
				.AddItem("Succes")
				.AddItem("Erori")
				.ListIndex = 1
			Endwith

			* Aplicam filtrul ini?ial (fara filtru)
			This.ApplyLogFilter("")

			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup filtru log: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Gestionare grid-uri
	Function SetupGridMapari
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page2.Grid1
				.RecordSource = "mapare_prestatii"
				.ColumnCount = 4

				.Column1.Header1.Caption = "Cod Operatie"
				.Column1.ControlSource = "mapare_prestatii.cod_op"
				.Column1.Width = 150

				.Column2.Header1.Caption = "Descriere"
				.Column2.ControlSource = "mapare_prestatii.descr_op"
				.Column2.Width = 250

				.Column3.Header1.Caption = "Cod RAR"
				.Column3.ControlSource = "mapare_prestatii.cod_rar"
				.Column3.Width = 100

				.Column4.Header1.Caption = "Auto Send"
				.Column4.ControlSource = "mapare_prestatii.auto_send"
				.Column4.Width = 80

				.SetAll("ReadOnly", .F., "Column")
				.Refresh()
			Endwith
			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup grid mapari: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	Function SetupGridLog
		Local llSuccess
		llSuccess = .F.

		Try
			With This.PageFrame1.Page3.Grid2
				.RecordSource = "rar_log"
				.ColumnCount = 6

				.Column1.Header1.Caption = "Data"
				.Column1.ControlSource = "rar_log.data_prez"
				.Column1.Width = 100

				.Column2.Header1.Caption = "Comanda"
				.Column2.ControlSource = "rar_log.nr_comanda"
				.Column2.Width = 100

				.Column3.Header1.Caption = "VIN"
				.Column3.ControlSource = "rar_log.vin"
				.Column3.Width = 150

				.Column4.Header1.Caption = "Status"
				.Column4.ControlSource = "rar_log.status"
				.Column4.Width = 80

				.Column5.Header1.Caption = "Eroare"
				.Column5.ControlSource = "rar_log.error_msg"
				.Column5.Width = 200

				.Column6.Header1.Caption = "Data Trimitere"
				.Column6.ControlSource = "rar_log.data_trim"
				.Column6.Width = 150

				.SetAll("ReadOnly", .T., "Column")
				.Refresh()
			Endwith
			llSuccess = .T.

		Catch To loError
			Messagebox("Eroare la setup grid log: " + loError.Message, 16, "Eroare")
			llSuccess = .F.
		Endtry

		Return llSuccess
	Endfunc

	* Convertim din YYYY-MM-DD în data VFP
	Function Data2Date
		Lparameters lcData
		Local lnAn, lnLuna, lnZi, ldData
		lnAn = Val(Getwordnum(lcData,1,'-'))
		lnLuna = Val(Getwordnum(lcData,2,'-'))
		lnZi = Val(Getwordnum(lcData,3,'-'))
		ldData = Date(lnAn,lnLuna,lnZi)
		Return m.ldData
	Endfunc

	Function Destroy
		This.StopAutoProcessing()

		* Închidem toate tabelele
		If Used("mapare_prestatii")
			Use In mapare_prestatii
		Endif

		If Used("rar_log")
			Use In rar_log
		Endif

		If Used("prestatii_rar")
			Use In prestatii_rar
		Endif

		If Used("prezentari_fin")
			Use In prezentari_fin
		Endif

		If Used("xml_preview")
			Use In xml_preview
		Endif

		DoDefault()
	Endfunc
Enddefine

Enddefine

Function Main
	Local loForm, llSuccess
	llSuccess = .F.

	Try
		loForm = Createobject("RarAutoPassForm")
		loForm.Show(1)
		llSuccess = .T.

	Catch To loError
		Messagebox("Eroare la lansare aplicatie: " + loError.Message, 16, "Eroare")
		llSuccess = .F.
	Endtry

	Return llSuccess
Endfunc
