Imports System.ComponentModel
Imports ComponentPro.Net
Imports ComponentPro

Namespace MultipleThreads
	Partial Public Class MTForm
		Inherits Form
		Private ReadOnly _exception As Boolean
		Private _settings As SettingInfo

		Public Sub New()
			Try
				InitializeComponent()

#If Not Framework4_5 Then
				AddHandler Me.emailValidator.ValidateEmailsCompleted, AddressOf sfbEmailValidator_ValidateTextFileCompleted
#End If
			Catch exc As ComponentPro.Licensing.EmailValidator.UltimateLicenseException
				MessageBox.Show(exc.Message)
				_exception = True
				Return
			End Try
		End Sub

		''' <summary>
		''' Handles the form's Load event.
		''' </summary>
		''' <param name="e">The event arguments.</param>
		Protected Overrides Sub OnLoad(ByVal e As EventArgs)
			MyBase.OnLoad(e)
			If _exception Then
				Me.Close()
			End If

			_settings = SettingInfo.LoadConfig()

			emailValidator.ProxyHttpConnectAuthMethodMethod = _settings.ProxyMethod
			emailValidator.ProxyHost = _settings.ProxyServer
			emailValidator.ProxyPassword = _settings.ProxyPassword
			emailValidator.ProxyPort = _settings.ProxyPort
			emailValidator.ProxyType = _settings.ProxyType
			emailValidator.ProxyUserName = _settings.ProxyUser
			emailValidator.ProxyDomain = _settings.ProxyDomain

'			#Region "Settings"

			' Initialize the text box.
			txtEmailListThread.Text = _settings.EmailListFile

'			#End Region
		End Sub

		''' <summary>
		''' Handles the form's Closing event.
		''' </summary>
		''' <param name="e">The event arguments.</param>
		Protected Overrides Sub OnClosing(ByVal e As System.ComponentModel.CancelEventArgs)
			_settings.EmailListFile = txtEmailListThread.Text
			_settings.SaveConfig()

			MyBase.OnClosing(e)
		End Sub

		''' <summary>
		''' Handles the Browse file button's Click event.
		''' </summary>
		''' <param name="sender">The button object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub btnBrowseFile_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnBrowseFile.Click
			Dim dlg As New OpenFileDialog()
			Try
				dlg.FileName = txtEmailListThread.Text
				dlg.Filter = "List File (*.txt)|*.txt|All files (*.*)|*.*"
				dlg.FilterIndex = 1
				dlg.Title = "Select Email List File"
				' Show Open file dialog.
				If dlg.ShowDialog() <> System.Windows.Forms.DialogResult.OK Then
					Return
				End If

				txtEmailListThread.Text = dlg.FileName
			Catch
				MessageBox.Show(dlg.FileName & " is not a valid address list", "Error")
			End Try
		End Sub

		Private Sub EnableDialog(ByVal enable As Boolean)
			txtEmailListThread.Enabled = enable
			btnBrowseFile.Enabled = enable
			btnProxy.Enabled = enable

			btnSingleThread.Enabled = enable
			btnTwoThreads.Enabled = enable
			btnAbort.Enabled = Not enable

			Util.EnableCloseButton(Me, enable)
		End Sub

		''' <summary>
		''' Handles the TwoThreads button's Click.
		''' </summary>
		''' <param name="sender">The button object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub btnTwoThreads_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnTwoThreads.Click
			' Clear logs.
			lst1AdvancedLog.Items.Clear()
			lst2AdvancedLog.Items.Clear()
			lst1Log.Items.Clear()
			lst2Log.Items.Clear()

			Try
				' Disable controls.
				EnableDialog(False)
				' Start validating emails in the specified file with multi-threads (2).
				emailValidator.MultiThreadsValidateTextFile(txtEmailListThread.Text, 2, True)
			Catch exc As Exception
				MessageBox.Show(exc.Message, "Error", MessageBoxButtons.OK, MessageBoxIcon.Stop)
				EnableDialog(True)
			End Try
		End Sub

		Private Sub sfbEmailValidator_MessageLogging(ByVal sender As Object, ByVal e As ComponentPro.Net.EmailValidatorLogEventArgs) Handles emailValidator.MessageLogging
			If Not IsDisposed Then
				Invoke(New EventHandler(Of EmailValidatorLogEventArgs)(AddressOf MessageLogging), sender, e)
			End If
		End Sub

		''' <summary>
		''' Handles the emailvalidator's MessageLogging event.
		''' </summary>
		''' <param name="sender">The email validator object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub MessageLogging(ByVal sender As Object, ByVal e As ComponentPro.Net.EmailValidatorLogEventArgs)
			AdvancedLog(e.SmtpTranscript, e.ThreadId)
		End Sub

		''' <summary>
		''' Logs message.
		''' </summary>
		''' <param name="message">The message to log.</param>
		''' <param name="threadId">The Thread Id.</param>
		Private Sub AdvancedLog(ByVal message As String, ByVal threadId As Integer)
			message = message.Replace(vbCrLf, String.Empty)

			' Validate Email Addresses loaded from a file with two threads                    
			Dim lb As ListBox
			If threadId = 0 Then
				lb = lst1AdvancedLog
			Else
				lb = lst2AdvancedLog
			End If
			lb.Items.Add(message)
		End Sub

		''' <summary>
		''' Logs message.
		''' </summary>
		''' <param name="message">The message to log.</param>
		''' <param name="threadId">The Thread Id.</param>
		Private Sub Log(ByVal message As String, ByVal threadId As Integer)
			' Validate Email Addresses loaded from a file with two threads
			Dim lb As ListBox
			If threadId = 0 Then
				lb = lst1Log
			Else
				lb = lst2Log
			End If
			lb.Items.Add(message)
		End Sub

		''' <summary>
		''' Handles the Single Thread button's Click event.
		''' </summary>
		''' <param name="sender">The button object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub btnAbort_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnAbort.Click
			' Abort the operation.
			btnAbort.Enabled = False
			emailValidator.Cancel()
		End Sub

		''' <summary>
		''' Handles the Single Thread button's Click event.
		''' </summary>
		''' <param name="sender">The button object.</param>
		''' <param name="e">The event arguments.</param>
#If Framework4_5 Then
		Private Async Sub btnSingleThread_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnSingleThread.Click
#Else
			Private Sub btnSingleThread_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnSingleThread.Click
#End If
			' Make sure the email list file textbox is not empty.
			If txtEmailListThread.Text.Length = 0 Then
				MessageBox.Show("Please enter file name.")
				Return
			End If

			' Disable controls.
			EnableDialog(False)

			' Clear logs.
			lst1AdvancedLog.Items.Clear()
			lst2AdvancedLog.Items.Clear()
			lst1Log.Items.Clear()
			lst2Log.Items.Clear()

			' Reset counters.
			_processed = 0
			_passed = 0

#If Framework4_5 OrElse SYNC Then
			Try
#If SYNC Then
				emailValidator.ValidateTextFile(txtEmailListThread.Text)
#Else
				' Asynchronously Validate a Text File.
				Await emailValidator.ValidateTextFileAsync(txtEmailListThread.Text)
#End If
				MessageBox.Show(String.Format("Single thread validation completed. {0} email(s) processed, {1} passed", _processed, _passed))
			Catch ex As Exception
				Util.ShowError(exc)
			End Try

			' Enable controls.
			EnableDialog(True)
			End Sub
#Else
			' Asynchronously Validate a Text File.
			emailValidator.ValidateTextFileAsync(txtEmailListThread.Text)
#End If
			End Sub

		Private Sub sfbEmailValidator_ThreadsCompleted(ByVal sender As Object, ByVal e As EmailValidatorThreadsCompletedEventArgs) Handles emailValidator.ThreadsCompleted
			If Not IsDisposed Then
				Invoke(New EventHandler(Of EmailValidatorThreadsCompletedEventArgs)(AddressOf ThreadsCompleted), sender, e)
			End If
		End Sub

		''' <summary>
		''' Handles the emailvalidator's ThreadsCompleted event.
		''' </summary>
		''' <param name="sender">The emailverifer object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub ThreadsCompleted(ByVal sender As Object, ByVal e As EmailValidatorThreadsCompletedEventArgs)
			MessageBox.Show(String.Format("Multi-threads validation completed. {0} email(s) processed, {1} passed", e.EmailsProcessed, e.EmailsPassed))
			EnableDialog(True)
		End Sub

		Private Sub sfbEmailValidator_ThreadCompleted(ByVal sender As Object, ByVal e As EmailValidatorThreadCompletedEventArgs) Handles emailValidator.ThreadCompleted
			If Not IsDisposed Then
				Invoke(New EventHandler(Of EmailValidatorThreadCompletedEventArgs)(AddressOf ThreadCompleted), sender, e)
			End If
		End Sub

		''' <summary>
		''' Handles the emailvalidator's ThreadCompleted event.
		''' </summary>
		''' <param name="sender">The emailverifer object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub ThreadCompleted(ByVal sender As Object, ByVal e As EmailValidatorThreadCompletedEventArgs)
			Log(String.Format("Validation completed. {0} email(s) processed, {1} passed", e.EmailsProcessed, e.EmailsPassed), e.ThreadId)
			If e.LastException IsNot Nothing Then
				Log("Last error: " & e.LastException.Message, e.ThreadId)
			End If
		End Sub

#If Not Framework4_5 Then
		''' <summary>
		''' Handles the emailvalidator's ValidateTextFileCompleted event.
		''' </summary>
		''' <param name="sender">The email validator object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub sfbEmailValidator_ValidateTextFileCompleted(ByVal sender As Object, ByVal e As AsyncCompletedEventArgs)
			If e.Error IsNot Nothing Then
				Util.ShowError(e.Error)
			Else
				MessageBox.Show(String.Format("Single thread validation completed. {0} email(s) processed, {1} passed", _processed, _passed))
			End If

			' Enable controls.
			EnableDialog(True)
		End Sub
#End If

		''' <summary>
		''' Handles the proxy settings button's Click event.
		''' </summary>
		''' <param name="sender">The button object.</param>
		''' <param name="e">The event arguments.</param>
		Private Sub btnProxy_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnProxy.Click
			Dim dlg As New ProxySettings(_settings)

			' Show the proxy settings dialog.
			If dlg.ShowDialog() = System.Windows.Forms.DialogResult.OK Then
				' Update emailvalidator's proxy settings.
				emailValidator.ProxyHttpConnectAuthMethodMethod = _settings.ProxyMethod
				emailValidator.ProxyHost = _settings.ProxyServer
				emailValidator.ProxyPassword = _settings.ProxyPassword
				emailValidator.ProxyPort = _settings.ProxyPort
				emailValidator.ProxyType = _settings.ProxyType
				emailValidator.ProxyUserName = _settings.ProxyUser
				emailValidator.ProxyDomain = _settings.ProxyDomain
			End If
		End Sub

		Private Sub sfbEmailValidator_EmailValidated(ByVal sender As Object, ByVal e As EmailValidatedEventArgs) Handles emailValidator.EmailValidated
			If Not IsDisposed Then
				Invoke(New EventHandler(Of EmailValidatedEventArgs)(AddressOf EmailValidated), sender, e)
			End If
		End Sub

		Private _passed As Integer
		Private _processed As Integer

		Private Sub EmailValidated(ByVal sender As Object, ByVal e As EmailValidatedEventArgs)
			If e.Error IsNot Nothing Then
				AdvancedLog(String.Format("Email '{0}' validated at level {1} with error: {2}.", e.EmailAddress, e.ValidatedLevel, e.Error.Message), e.ThreadId)
				Log(String.Format("    Mailbox '{0}' is invalid - completed with error: {1}", e.EmailAddress, e.Error.Message), e.ThreadId)
			Else
				AdvancedLog(String.Format("Email '{0}' validated at level {1}.", e.EmailAddress, e.ValidatedLevel), e.ThreadId)

				If e.ValidatedLevel = ValidationLevel.Success Then
					Log(String.Format("    Completed successfully - Mailbox {0} is valid", e.EmailAddress), e.ThreadId)
					_passed += 1
				Else
					Log(String.Format("    Mailbox '{0}' is invalid - completed at level: {1}", e.EmailAddress, e.ValidatedLevel), e.ThreadId)
				End If
			End If
			AdvancedLog("------------------------------------", e.ThreadId)
			Log("----------------", e.ThreadId)
			_processed += 1

#If DEBUG Then
			Console.WriteLine("Evt Validated - " & Date.Now)
			Console.WriteLine("   Prg: " & e.ProgressPercentage)
			Console.WriteLine("   Processed: " & e.EmailsProcessed)
#End If
		End Sub

		Private Sub sfbEmailValidator_Progress(ByVal sender As Object, ByVal e As EmailValidatorProgressEventArgs) Handles emailValidator.Progress
			If Not IsDisposed Then
				Invoke(New EventHandler(Of EmailValidatorProgressEventArgs)(AddressOf Progress), sender, e)
			End If
		End Sub

		Private Sub Progress(ByVal sender As Object, ByVal e As EmailValidatorProgressEventArgs)
			If e.EmailAddress IsNot Nothing Then
				If e.Passed Then
					Log("    Passed: " & e.Level.ToString(), e.ThreadId)
				Else
					Log("    Failed: " & e.Level.ToString(), e.ThreadId)
				End If
			End If

			progressBar.Value = e.ProgressPercentage
		End Sub

		Private Sub sfbEmailValidator_EmailValidating(ByVal sender As Object, ByVal e As EmailValidatingEventArgs) Handles emailValidator.EmailValidating
			If Not IsDisposed Then
				Invoke(New EventHandler(Of EmailValidatingEventArgs)(AddressOf EmailValidating), sender, e)
			End If
		End Sub

		Private Sub EmailValidating(ByVal sender As Object, ByVal e As EmailValidatingEventArgs)
			Log(String.Format("Start validating e-mail address: '{0}'", e.EmailAddress), e.ThreadId)
#If DEBUG Then
			Console.WriteLine("Evt Validating - " & Date.Now)
			Console.WriteLine("   Prg: " & e.ProgressPercentage)
			Console.WriteLine("   Processed: " & e.EmailsProcessed)
#End If
		End Sub
	End Class
End Namespace