Imports System.Data.SqlClient
Imports System.IO
Imports System.Net
Imports Newtonsoft.Json

Public Class Envoc
    Inherits System.Web.UI.Page

    Private Function _get(Of T)(name As String, def As T)
        If Request.QueryString(name) Is Nothing Then Return def
        Return Request.QueryString(name)
    End Function

    Protected Sub Page_Load() Handles Me.Load

        ' For some reason, we aren't set to use this by default, and it's required
        ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12

        Dim responseText As String
        Select Case Request.QueryString("command")
            Case "get_webhooks"
                responseText = GetWebhooks(_get("page", 1))
            Case "add_webhook"
                responseText = AddWebhook(_get("name", ""), _get("event", ""))
            Case "delete_webhook"
                responseText = DeleteWebhook(_get("webhookId", 0))
            Case Nothing
                responseText = ParseNotification()
            Case Else
                Throw New HttpException(400, "Bad Request")
        End Select

        Response.Clear()
        Response.Write(responseText)
        Response.End()
    End Sub

    Private Function GetWebhooks(page As Integer) As String
        Dim api As New EnvocAPI.Api(My.Settings.EnvocApiKey)
        Return api.getWebhooks(page)
    End Function

    Private Function AddWebhook(name As String, [event] As String) As String
        Dim api As New EnvocAPI.Api(My.Settings.EnvocApiKey)
        Return api.addWebhook(New EnvocAPI.Api.AddWebhookRequest With {
            .name = name,
            .targetUrl = My.Settings.baseUrl & "Services/Envoc.aspx",
            .contentType = "application/json",
            .[event] = [event]})
    End Function

    Private Function DeleteWebhook(webhookId As Integer) As String
        Dim api As New EnvocAPI.Api(My.Settings.EnvocApiKey)
        Return api.deleteWebhook(webhookId)
    End Function

    Private Function ParseNotification() As String
        
        ' The payload is in the body
        Dim payload As String
        Using stream = Request.InputStream
            Using reader As New StreamReader(stream)
                payload = reader.ReadToEnd()
            End Using
        End Using

        ' Let's log the traffic first
        Using connection As New SqlConnection(Logic.Database.ConnectionString) 'My.Settings.connectionString)
            connection.Open()
            Dim cmd As New SqlCommand("INSERT INTO EnvocLog(dateCreated,source,data) VALUES (GETDATE(),'Webhook',@data)", connection)
            cmd.Parameters.AddWithValue("data", payload)
            cmd.ExecuteNonQuery()
        End Using

        ' Parse the notification
        Dim notification = JsonConvert.DeserializeObject(Of EnvocAPI.Api.WebhookNotification)(payload)

        ' Send the email
        Dim bodybuilder As New StringBuilder
        Using connection As New SqlConnection(Logic.Database.ConnectionString) 'My.Settings.connectionString)
            connection.Open()
            Dim cmd As New SqlCommand("", connection)

            bodybuilder.AppendLine("A driver monitored by Envoc has been flagged.")
            bodybuilder.AppendLine()
            bodybuilder.AppendLine("Message " & notification.description)
            bodybuilder.AppendLine()

            ' Collect the drivers
            cmd.CommandText =
                "SELECT d.FirstName,d.MiddleName,d.LastName,d.ContractID, cust.Name
                FROM Driver d
                LEFT JOIN ServiceContract sc ON sc.ID=d.ContractID
                LEFT JOIN Customer cust ON cust.ID=sc.CustomerID
                WHERE d.DLNumber=@dlNumber"
            cmd.Parameters.AddWithValue("dlNumber", notification.driversLicenseNumber)
            Using dReader = cmd.ExecuteReader()
                While dReader.Read()
                    bodybuilder.AppendFormat("Driver: {0} {1} {2}{3}", dReader(0), dReader(1), dReader(2), vbCrLf)
                    bodybuilder.AppendFormat("Contract: {0} - {1}{2}", dReader(4), dReader(3), vbCrLf)
                End While
            End Using

            bodybuilder.AppendLine("License Number: " & notification.driversLicenseNumber)
            bodybuilder.AppendLine("Decription: " & notification.description)

            cmd.CommandText = "INSERT INTO AutomationServer_EmailsSent (EmailFrom,EmailFromName,EmailTo,EmailSubject,EmailBody,EmailSent)
                SELECT AutomationServerEmailUser,AutomationServerEmailUser,@emailTo,@emailSubject,@emailBody,0
                FROM Company"
            cmd.Parameters.AddWithValue("emailTo", "support@trucksafety.com")
            cmd.Parameters.AddWithValue("emailSubject", "Envoc Driver Flagged")
            cmd.Parameters.AddWithValue("emailBody", bodybuilder.ToString())
            cmd.ExecuteNonQuery()

        End Using

        Return ""
    End Function

End Class