using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using System.Net.Http;
using System.Text;
using System.Xml;
using System.Xml.Linq;
using System.Net;
using System.Text.RegularExpressions;

namespace TrayCheckoutApi.Controllers
{
    public class CreateTransactionController : Controller
    {
        private string xmlResponse;
        private string dataResponse;
        private string resultError;
        private string dataRequest;
        private string message;
        private string methodPayment;
        private string linkPayment;
        const string PAYMENT_CARD = "card";
        const string PAYMENT_TRANSFER = "transfer";
        const string PAYMENT_BANK_SLIP = "bank_slip";

        public ActionResult Index()
        {
            resultError = "";
            message = "";
            CreateTransaction();
            ViewData["xmlResponse"] = xmlResponse;
            ViewData["dataResponse"] = dataResponse;
            ViewData["linkPayment"] = linkPayment;
            ViewData["dataRequest"] = dataRequest;
            messageService();
            return View();
        }

        private void messageService()
        {
            ViewData["messageColor"] = (resultError.Count() > 0) ? "#ff0000" : "#00ff00";
            ViewData["resultMessage"] = " Create Transaction - message_response[" + message + "]! \n" + resultError;
        }

        private List<KeyValuePair<string, string>> formData()
        {
            methodPayment = PAYMENT_TRANSFER;
            var list = new List<KeyValuePair<string, string>>();
            list.Add(new KeyValuePair<string, string>("token_account", ConfigTrayCheckout.tokenAccount));
            list.Add(new KeyValuePair<string, string>("transaction[url_notification]", ConfigTrayCheckout.urlNotification));
            list.Add(new KeyValuePair<string, string>("customer[name]", "Nome do Cliente"));
            list.Add(new KeyValuePair<string, string>("customer[cpf]", "98489882380"));
            list.Add(new KeyValuePair<string, string>("customer[email]", "emaildo@cliente.com.br"));

            list.Add(new KeyValuePair<string, string>("customer[contacts][][number_contact]", "1133120001"));
            list.Add(new KeyValuePair<string, string>("customer[contacts][][type_contact]", "H"));
            list.Add(new KeyValuePair<string, string>("customer[addresses][][type_address]", "B"));
            list.Add(new KeyValuePair<string, string>("customer[addresses][][postal_code]", "04001001"));

            list.Add(new KeyValuePair<string, string>("customer[addresses][][street]", "Av Paulista"));
            list.Add(new KeyValuePair<string, string>("customer[addresses][][number]", "112"));
            list.Add(new KeyValuePair<string, string>("customer[addresses][][neighborhood]", "Centro"));
            list.Add(new KeyValuePair<string, string>("customer[addresses][][city]", "São Paulo"));
            list.Add(new KeyValuePair<string, string>("customer[addresses][][state]", "SP"));
            list.Add(new KeyValuePair<string, string>("transaction[order_number]", "xx6"));

            string price = "";
            // Consulte todas formas de pagamento em: http://wiki.traycheckout.com.br/index.php/Integra%C3%A7%C3%A3o#Tabelas_Auxiliares
            if (methodPayment.Equals(PAYMENT_CARD))
            {
                price = "199.99";
                list.Add(new KeyValuePair<string, string>("payment[payment_method_id]", "3"));
                list.Add(new KeyValuePair<string, string>("payment[split]", "5"));
                list.Add(new KeyValuePair<string, string>("payment[card_name]", "Nome Impresso"));
                list.Add(new KeyValuePair<string, string>("payment[card_number]", "55a55666677778884"));
                list.Add(new KeyValuePair<string, string>("payment[card_expdate_month]", "01"));
                list.Add(new KeyValuePair<string, string>("payment[card_expdate_year]", "2017"));
                list.Add(new KeyValuePair<string, string>("payment[card_cvv]", "123"));

            }
            else if (methodPayment.Equals(PAYMENT_TRANSFER))
            {
                price = "185.50"; //desconto para pagamento com transferência
                list.Add(new KeyValuePair<string, string>("payment[payment_method_id]", "7"));
                list.Add(new KeyValuePair<string, string>("payment[split]", "1"));
            }
            else if (methodPayment.Equals(PAYMENT_BANK_SLIP))
            {
                price = "180.10"; //desconto para pagamento com boleto
                list.Add(new KeyValuePair<string, string>("payment[payment_method_id]", "6"));
                list.Add(new KeyValuePair<string, string>("payment[split]", "1"));
            }

            list.Add(new KeyValuePair<string, string>("transaction_product[0][description]", "Notebook preto"));
            list.Add(new KeyValuePair<string, string>("transaction_product[0][quantity]", "1"));
            list.Add(new KeyValuePair<string, string>("transaction_product[0][price_unit]", "" + price));
            return list;
        }

        private void formatForm(List<KeyValuePair<string, string>> form)
        {
            dataRequest = string.Join(",", form.ToArray());
            dataRequest = Regex.Replace(dataRequest, @"[,]", "\n");
        }

        private void CreateTransaction()
        {
            var form = formData();
            var content = new FormUrlEncodedContent(form);
            //Método pode ser excluido, utilizado apenas para quebrar linha dos dados do form para melhor visualização
            formatForm(form); 
            TrayCheckout tc = new TrayCheckout();
            tc.RequestTrayCheckout(content, ConfigTrayCheckout.UrlCreateTransaction());
            if (tc.getHttpStatusCode().Equals(HttpStatusCode.OK))
            {
                XmlDocument xml = new XmlDocument();
                xmlResponse = tc.getContent();
                xml.LoadXml(xmlResponse);
                tc.setXml(xml);
                if (!tc.sucessResponse())
                {
                    message = tc.getMessage();
                    //atribuir erros para ser exibido
                    resultError += tc.getGeneralError();
                    resultError += tc.getValidationError();
                    return; //
                }
                message = tc.getMessage();
                XmlNodeList transaction = xml.GetElementsByTagName("transaction");
                dataTransaction(transaction[0]);
                XmlNodeList payment = xml.GetElementsByTagName("payment");
                dataPayment(payment[0]);
                SendMail();
            }
        }

        private void dataPayment(XmlNode nodePayment)
        {
            string price_payment = nodePayment["price_payment"].InnerText;
            string payment_response = nodePayment["payment_response"].InnerText;
            string url_payment = nodePayment["url_payment"].InnerText;
            string tid = nodePayment["tid"].InnerText;
            string split = nodePayment["split"].InnerText;
            string payment_method_id = nodePayment["payment_method_id"].InnerText;
            string payment_method_name = nodePayment["payment_method_name"].InnerText;
            string linha_digitavel = nodePayment["price_payment"].InnerText;
            dataResponse += "\nMethod: " + payment_method_id + " - " + payment_method_name + " Split: " + split + " Price: " + price_payment;

            if (!methodPayment.Equals(PAYMENT_CARD))
                dataResponse += "\n************** Atenção - pagamento com [" + methodPayment + "]. Segue a URL para finalizar pagamento: " + url_payment + " ***********";
            else
                dataResponse += "\nUrl Payment:" + url_payment + "";
            linkPayment = url_payment;
            dataResponse += "\nResponse: " + payment_response;
        }

        private void dataTransaction(XmlNode nodeTransaction)
        {
            string order_number = nodeTransaction["order_number"].InnerText;
            string status_id = nodeTransaction["status_id"].InnerText;
            string status_name = nodeTransaction["status_name"].InnerText;
            string transaction_id = nodeTransaction["transaction_id"].InnerText;
            string token_transaction = nodeTransaction["token_transaction"].InnerText;
            dataResponse += "\nPedido: " + order_number;
            dataResponse += "\nStatus: " + status_id + " - " + status_name;
            dataResponse += "\nId Transação: " + transaction_id;
            dataResponse += "\nToken Transação: " + token_transaction;
        }

        private void SendMail()
        {
            dataResponse += "\nImplementar rotida para envio de email! " ;
        }
    }
}
