import csv
import json
import os
from django.db import IntegrityError, connection
from datetime import date, datetime, timedelta
from django.http import HttpResponse

from dateutil.relativedelta import relativedelta
from django.core.mail import EmailMultiAlternatives
from django.http import JsonResponse
from django.template.loader import render_to_string, get_template
from django.views.decorators.cache import never_cache
try: # for pip >= 10
    from pip._internal.req.req_install import logger
except ImportError: # for pip <= 9.0.3
    from pip.req.req_install import logger

from rest_framework.decorators import api_view, authentication_classes

from Plan.models import Plan
from StratFit import settings
from StratFit.settings import PAGING_ROWS
from Subscriber.Authentication import SessionAuthentication, IsAuthenticated, StartFitSessionUtil
from Subscriber.models import User
from Userplan.models import UserPlan, UserExercise
from payment.models import Order, OrderDetail, TransactionHistory
import urllib
from urllib.parse import parse_qs
from Subscriber.views import exceptionMail
from utility.models import PriceMapping
from utility.views import officeMail
from reportlab.lib.pagesizes import letter
import time
from reportlab.lib.enums import TA_JUSTIFY
from reportlab.platypus import SimpleDocTemplate, Paragraph, Spacer, Image
from reportlab.lib.styles import getSampleStyleSheet, ParagraphStyle
from reportlab.lib.units import inch




@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def createGymOrders(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    user = username['id']
    gpdata = json.loads(request.body.decode('utf-8'))
    req=gpdata
    url="payment/creategymorders"
    try:
        todayDate = date.today().strftime("%Y-%m-%d %H:%M:%S")
        print(todayDate)
        one_months = date.today() + relativedelta(days = 28)
        endDate = one_months.strftime("%Y-%m-%d %H:%M:%S")
        gpdata = json.loads(request.body.decode('utf-8'))
        datarange = len(gpdata['gympdata'])
        loginUserid= gpdata['loginUser']
        if username != None:
            if 'loginUser' in gpdata:
                gp = Order.objects.create(
                    user_id =  loginUserid,
                    totalAmount = gpdata['finalTotal'],
                    payFrom = todayDate,
                    payTo = endDate,
                    transation_id =1,
                    status =1
                )
                gp.save()
                order_id = gp.id
                for dt in gpdata['gympdata']:
                    print('++++++++++++++++++++++')
                    userplanstatus = OrderDetail.objects.select_related('Order__id','User__id').filter(forUser_id = dt['id']).values('id','order_id__user_id','forUser_id','payeeid_id','totalAmount')
                    print(userplanstatus)
                    if 'partnerPlanprice' in dt and dt['partnerPlanprice']!='':
                        if userplanstatus.exists():
                            payableamount = dt['partnerPlanprice']
                        else:
                            payableamount = 0
                        if dt['partnerPlanprice'] == None:
                            payableamount = 0
                    else:
                        payableamount = 0
                    print(payableamount,"sssss")
                    guserid = dt['id']
                    orderdet = OrderDetail(
                        order_id = order_id,
                        plan_id = dt['existingPlanid'],
                        totalAmount=payableamount
                    )
                    #orderdet.plan_id = dt['existingPlanid']
                    orderdet.forUser_id = guserid
                    orderdet.payeeid_id = loginUserid
                    #orderdet.totalAmount = payableamount
                    orderdet.save()
                return JsonResponse({"success":True,"message":"payment success","orderId":order_id})
        else:
            return JsonResponse({"success":False,"message":"user logged out"})
    except Exception as e:
        logger.error("error")
        exceptionMail(user, req, url, str(e))
        return JsonResponse({"msg": str(e)})

def next_weekday(d, weekday):
    days_ahead = weekday - d.weekday()
    if days_ahead < 0: # Target day already happened this week
        days_ahead += 7
    return d + timedelta(days=days_ahead)

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def updategymorders(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    user = username['id']
    data = json.loads(request.body.decode('utf-8'))
    req=data
    url="payment/updategymorders"
    try:
        todayDate = date.today().strftime("%Y-%m-%d %H:%M:%S")
        print(todayDate)
        one_months = date.today() + relativedelta(days = 28)
        endDate = one_months.strftime("%Y-%m-%d %H:%M:%S")
        if username != None:
            print("here")
            orderId = data['orderId']
            updateOrdetails = Order.objects.get(pk = orderId)
            updateOrdetails.transation_id = data['transactionId']
            updateOrdetails.save()
            userdetails = OrderDetail.objects.filter(order_id = orderId).values('id','plan_id','forUser_id')
            for val in userdetails:
                values = dict(val)
                planId =values['plan_id']
                planUser = values['forUser_id']
                existinguserplanDetails = UserPlan.objects.filter(plan_id = planId,user_id = planUser,status__in = [1,3]).values('id')
                if existinguserplanDetails.exists():
                    print("------------UserPlan Update-------------")
                    for data in existinguserplanDetails:
                        dataObj = dict(data)
                        updateuserplan = UserPlan.objects.get(pk = dataObj['id'])
                        updateuserplan.status = 2
                        updateuserplan.save()
                print("------------UserPlan Create-------------")
                renewalDate = date.today().strftime("%Y-%m-%d")
                d = datetime.now()
                next_monday = next_weekday(d, 0)  # 0 = Monday, 1=Tuesday, 2=Wednesday...
                nextMondayStr = next_monday.strftime("%Y-%m-%d")
                print(renewalDate)
                one_months = date.today() + relativedelta(months=+1)
                nextRenewalDate = one_months.strftime("%Y-%m-%d")
                userplanDetails = UserPlan.objects.create(
                    user_id=planUser,
                    plan_id=planId,
                    renewalDate=renewalDate + ' 00:00:00',
                    nextRenewalDate=nextRenewalDate + ' 00:00:00',
                    startDate=nextMondayStr + ' 00:00:00',
                    status=1,
                    freetrail=False
                )
                # userplanDetails.startDate = planInfo['start_date']
                userplanDetails.save()
                planinf = UserPlan.objects.select_related('Plan__id').filter(plan__id=planId).values(
                    'plan_id__planName')
                for data in planinf:
                    planname = data['plan_id__planName']
                instanceSub = User.objects.get(id=planUser)
                subject = "Plan Subscription"
                to_email = instanceSub.email
                ctx = {
                    'first_name': instanceSub.first_name,
                    'planname': planname
                }
                message = render_to_string('subscribeplan.html', ctx)
                officeMail(subject, message, to_email)
            return JsonResponse({"success":True,"message":"Program Subscribed Successfully"})
        else:
            return JsonResponse({"success":False,"message":"user logged out"})
    except Exception as e:
        logger.error("error")
        exceptionMail(user, req, url, str(e))
        return JsonResponse({"msg": str(e)})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def checkUserPlanStatus(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    user=username['id']
    pInfo = json.loads(request.body.decode('utf-8'))
    req=pInfo
    url="payment/checkuserplanstatus"
    try:
        if username!=None:
            #print(pInfo)
            existingStatus = False
            dataArr = []
            userArr = []
            userRange = len(pInfo['gympdata'])
            for i in range(userRange):

                userplanvalues = UserPlan.objects.filter(user_id = pInfo['gympdata'][i]['id'],plan_id = pInfo['gympdata'][i]['existingPlanid']).values('nextRenewalDate','id')
                if userplanvalues.exists():
                    print("iam Here")
                    for data in userplanvalues:
                        existObj = dict(data)
                        oneweek = existObj['nextRenewalDate'] - relativedelta(days = 7)
                        beforeoneweek = (oneweek. strftime("%Y-%m-%d"))
                        todaydate = date.today().strftime("%Y-%m-%d")
                        if todaydate>=beforeoneweek:
                            userplanstatus = OrderDetail.objects.select_related('Order__id','User__id').filter(forUser_id = pInfo['gympdata'][i]['id']).values('id','order_id__user_id','forUser_id','payeeid_id','totalAmount')#.exclude(order_id__user_id = existObj['id'])
                            beforeRenewal = True
                        else:
                            userplanstatus = OrderDetail.objects.select_related('Order__id','User__id').filter(forUser_id = pInfo['gympdata'][i]['id']).values('id','order_id__user_id','forUser_id','payeeid_id','totalAmount')
                else:
                    print("not In Here")
                    userplanstatus = OrderDetail.objects.select_related('Order__id','User__id').filter(forUser_id = pInfo['gympdata'][i]['id']).values('id','order_id__user_id','forUser_id','payeeid_id','totalAmount')
                if userplanstatus.exists():
                    existingStatus = True
                    for dt in userplanstatus:
                        dataObj = dict(dt)
                        dataArr.append(dataObj)
                else:
                    user_id = pInfo['gympdata'][i]['id']
                    userValues = {"existingStatus":False,"user_id":user_id}
                    userArr.append(userValues)
            return JsonResponse({"success": True, "existingStatus":existingStatus,"existingData":dataArr,"newusers":userArr})
        else:
            return JsonResponse({"success":False,"message":"user logged out"})
    except Exception as e:
        logger.error("error")
        exceptionMail(user, req, url, str(e))
        return JsonResponse({"msg": str(e)})

def paypalAuthToken(request):
    data = json.loads(request.body.decode('utf-8'))
    print(data['amount'])
    params = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'METHOD':'SetExpressCheckout',
        'VERSION':95,
        'PAYMENTREQUEST_0_PAYMENTACTION':'Authorization',     # type of payment
        'PAYMENTREQUEST_0_AMT':data['amount'],#50,              # amount of transaction
        'PAYMENTREQUEST_0_CURRENCYCODE':'USD',
        'CANCELURL':"http://"+request.META['HTTP_HOST']+"/#fail",    #For use if the consumer decides not to proceed with payment
        'RETURNURL':"http://"+request.META['HTTP_HOST']+"/#success"  #For use if the consumer proceeds with payment
    }

    params_string = urllib.parse.urlencode(params).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read() #gets the response and parse it.
    response_dict = parse_qs(response)
    print(response_dict)
    response_token = response_dict["TOKEN".encode("utf-8")][0]
    rurl = settings.PAYPAL_URL+str(response_token.decode("utf-8")) #gather the response token and redirect to paypal to authorize the payment
    return JsonResponse(rurl, safe=False)

def doCheckout(request):
    data = json.loads(request.body.decode('utf-8'))
    exparams = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'VERSION':95,

        'METHOD':'DoExpressCheckoutPayment',
        'TOKEN':data['token'],#'EC-8B556284J2540611G', #get the token from the request that is redirected
        'PAYERID':data['payerId'],#'5N4HH3FY9D52J',      # customer's unique PayPal ID
        'PAYMENTREQUEST_0_PAYMENTACTION':'Authorization',    # payment type
        'PAYMENTREQUEST_0_AMT':data['amount'],#50,             # transaction amount
        'PAYMENTREQUEST_0_CURRENCYCODE':'USD'
    }

    params_string = urllib.parse.urlencode(exparams).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read()
    print(response,"first")
    return JsonResponse(str(response), safe=False)


def checkPayment(request):
    data = json.loads(request.body.decode('utf-8'))
    exparams = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'VERSION':95,

        'METHOD':'DoCapture',
        'AUTHORIZATIONID':data['transactionId'],#'3H008600KT432091G', #get the token from the request that is redirected      # customer's unique PayPal ID
        'AMT':data['amount'],#50,      # transaction amount
        'CURRENCYCODE':'USD',
        'COMPLETETYPE':'Complete'
    }

    params_string = urllib.parse.urlencode(exparams).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read()
    print(response,"second")
    return JsonResponse(str(response), safe=False)


@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def paypalAuthToken1(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    data = json.loads(request.body.decode('utf-8'))
    req = data
    url = "paypalAuthToken1"
    try:
        if username!=None:
            print(data['amount'])
            params = {
                'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
                'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
                'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
                'METHOD':'SetExpressCheckout',
                'VERSION':95,
                'PAYMENTREQUEST_0_PAYMENTACTION':'Authorization',     # type of payment
                'PAYMENTREQUEST_0_AMT':data['amount'],#50,              # amount of transaction
                'PAYMENTREQUEST_0_CURRENCYCODE':'USD',
                'CANCELURL':"http://"+request.META['HTTP_HOST']+"/checkout/fail.html",    #For use if the consumer decides not to proceed with payment
                'RETURNURL':"http://"+request.META['HTTP_HOST']+"/checkout/success.html"  #For use if the consumer proceeds with payment
            }

            params_string = urllib.parse.urlencode(params).encode("utf-8")
            response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read() #gets the response and parse it.
            response_dict = parse_qs(response)
            print(response_dict)
            response_token = response_dict["TOKEN".encode("utf-8")][0]
            rurl = settings.PAYPAL_URL+str(response_token.decode("utf-8")) #gather the response token and redirect to paypal to authorize the payment
            return JsonResponse(rurl, safe=False)
    except Exception as e:
        logger.exception("something wrong")
        exceptionMail('1', req, url, str(e))
        return JsonResponse({"msg":str(e)})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def doCheckout1(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    try:
        if username!=None:
            data = json.loads(request.body.decode('utf-8'))
            print(data,"234534543")
            planId = data['plan_id']
            user_id = username['id']
            amount = data['amount']
            subsType = data['type']
            exparams = {
                'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
                'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
                'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
                'VERSION':95,

                'METHOD':'DoExpressCheckoutPayment',
                'TOKEN':data['token'],#'EC-8B556284J2540611G', #get the token from the request that is redirected
                'PAYERID':data['payerId'],#'5N4HH3FY9D52J',      # customer's unique PayPal ID
                'PAYMENTREQUEST_0_PAYMENTACTION':'Authorization',    # payment type
                'PAYMENTREQUEST_0_AMT':amount,             # transaction amount
                'PAYMENTREQUEST_0_CURRENCYCODE':'USD'
            }

            params_string = urllib.parse.urlencode(exparams).encode("utf-8")
            response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read()
            print(response,"first")
            #value = str(response)
            value= response.decode('utf-8')
            splitResponse = value.split('&')
            finalResult={}
            for va in splitResponse:
                temp = va.split('=')
                finalResult[temp[0]]=temp[1]
            result = finalResult
            transaction_id = result["PAYMENTINFO_0_TRANSACTIONID"]
            if result['PAYMENTINFO_0_ACK'] == "Success" and result['PAYMENTINFO_0_ACK'] !=None:
                print(result["PAYMENTINFO_0_TRANSACTIONID"],"234567")
                #print(value['PAYMENTINFO_0_TRANSACTIONID'])
                checkResponse = checkPayment1(transaction_id,planId,user_id,amount,subsType)
                return JsonResponse(checkResponse)
            else:
                return JsonResponse({"success":False,"message":"Payment Failed due to invalid token","statusCode":2})
    except Exception as e:
        logger.error("error")
        return JsonResponse({"msg": str(e)})

def checkPayment1(transaction_id,planId,user_id,amount,subsType):
    #data = json.loads(request.body.decode('utf-8'))
    exparams = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'VERSION':95,

        'METHOD':'DoCapture',
        'AUTHORIZATIONID':transaction_id,#'3H008600KT432091G', #get the token from the request that is redirected      # customer's unique PayPal ID
        'AMT':amount,      # transaction amount
        'CURRENCYCODE':'USD',
        'COMPLETETYPE':'Complete'
    }

    params_string = urllib.parse.urlencode(exparams).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read()
    print(response,"second")
    value = response.decode('utf-8')
    splitResponse = value.split('&')
    finalResult = {}
    for va in splitResponse:
        temp = va.split('=')
        finalResult[temp[0]] = temp[1]
    result = finalResult
    print(result['ACK'])
    if result['ACK'] == "Success":
        print("payment Success")
        try:
            planActive = UserPlan.objects.filter(user_id=user_id, plan_id=planId).values('id')
            print(subsType,"12345876")
            if planActive.exists() and subsType =="2":
                print("Renewing the Plan Details")
                statusCode = 1
                freetrail = False
                renewalDate = date.today().strftime("%Y-%m-%d")
                d = datetime.now()
                next_monday = next_weekday(d, 0)  # 0 = Monday, 1=Tuesday, 2=Wednesday...
                nextMondayStr = next_monday.strftime("%Y-%m-%d")
                # print(renewalDate)
                one_months = next_monday + relativedelta(days=+28)
                nextRenewalDate = one_months.strftime("%Y-%m-%d")
                for uplanid in planActive:
                    upid = dict(uplanid)
                    userPlanId = upid['id']
                renewPlan = UserPlan.objects.get(pk = userPlanId)
                renewPlan.renewalDate = renewalDate + ' 00:00:00'
                renewPlan.nextRenewalDate=nextRenewalDate + ' 00:00:00'
                renewPlan.startDate=nextMondayStr + ' 00:00:00'
                renewPlan.status=statusCode
                renewPlan.freetrail=freetrail
                renewPlan.save()
                planinf = UserPlan.objects.select_related('Plan__id').filter(plan__id=planId).values('plan_id__planName')
                for data in planinf:
                    planname = data['plan_id__planName']
                instanceSub = User.objects.get(id=user_id)
                subject = "Plan Subscription"
                to_email = instanceSub.email
                ctx = {
                    'first_name': instanceSub.first_name,
                    'planname': planname
                }
                message = render_to_string('subscribeplan.html', ctx)
                officeMail(subject, message, to_email)
                # print("User Plan entered")
                PlanDetails = UserPlan.objects.filter(user=user_id).filter(status__in=[1, 3]).values()
                plans = []
                for dt in PlanDetails:
                    planObj = dict(dt)
                    planInfos = Plan.objects.select_related('Goals__id', 'ProgramType__id', 'User__id').filter(id=planObj['plan_id']).values('id', 'planName', 'createdBy__first_name', 'createdBy__last_name','price', 'duration_weeks', 'ability', 'planGoal__goalName','planDescription', 'programType__programTypeName')
                    for dtp in planInfos:
                        planInfo = dict(dtp)
                    planObj['info'] = planInfo
                    plans.append(planObj)
                responseVal = {"success": True, "message": "User Plan Saved Successfully","data": {"startDate": renewalDate, "plans": plans, "renewalDate": renewalDate,"nextRenewalDate": nextRenewalDate, "freeTrial": False, "planId": planId,"statusCode":1}}
                return responseVal
            elif subsType =="1":
                print("Craating a New User plan")
                planexist = UserPlan.objects.filter(user_id=user_id, plan_id=planId,status__in=[1, 3]).values('id')
                if planexist.exists():
                    responseVal =  {"success": False, "message": "UserPlan Already Exists"}
                    return responseVal
                UserPlan.objects.filter(user_id=user_id, status=3).update(status=2)
                planActive = UserPlan.objects.filter(user_id=user_id, status=1).values('id')
                print("error Not here")
                if planActive.exists():
                    statusCode = 3
                    freetrail = False
                else:
                    statusCode = 1
                    freetrail = True
                renewalDate = date.today().strftime("%Y-%m-%d")
                d = datetime.now()
                next_monday = next_weekday(d, 0)  # 0 = Monday, 1=Tuesday, 2=Wednesday...
                nextMondayStr = next_monday.strftime("%Y-%m-%d")
                # print(renewalDate)
                one_months = next_monday + relativedelta(days=+28)
                nextRenewalDate = one_months.strftime("%Y-%m-%d")
                print("error Not here1111111")
                userplanDetails = UserPlan.objects.create(
                    user_id=user_id,
                    plan_id=planId,
                    renewalDate=renewalDate + ' 00:00:00',
                    nextRenewalDate=nextRenewalDate + ' 00:00:00',
                    startDate=nextMondayStr + ' 00:00:00',
                    status=statusCode,
                    freetrail=freetrail
                )
                # userplanDetails.startDate = planInfo['start_date']
                userplanDetails.save()
                print("error Not here2222222")
                planinf = UserPlan.objects.select_related('Plan__id').filter(plan__id=planId).values('plan_id__planName')
                for data in planinf:
                    planname = data['plan_id__planName']
                instanceSub = User.objects.get(id=user_id)
                print("error Not here333333")
                subject = "Plan Subscription"
                to_email = instanceSub.email
                ctx = {
                    'first_name': instanceSub.first_name,
                    'planname': planname
                }
                message = render_to_string('subscribeplan.html', ctx)
                officeMail(subject, message, to_email)
                # print("User Plan entered")
                PlanDetails = UserPlan.objects.filter(user=user_id).filter(status__in=[1, 3]).values()
                plans = []
                for dt in PlanDetails:
                    planObj = dict(dt)
                    planInfos = Plan.objects.select_related('Goals__id', 'ProgramType__id', 'User__id').filter(id=planObj['plan_id']).values('id', 'planName', 'createdBy__first_name', 'createdBy__last_name','price', 'duration_weeks', 'ability', 'planGoal__goalName','planDescription', 'programType__programTypeName')
                    for dtp in planInfos:
                        planInfo = dict(dtp)
                    planObj['info'] = planInfo
                    plans.append(planObj)
                print("error Not here44444444")
                responseVal = {"success": True, "message": "User Plan Saved Successfully", "data":{"startDate":renewalDate, "plans":plans, "renewalDate":renewalDate, "nextRenewalDate":nextRenewalDate, "freeTrial":False, "planId":planId},"statusCode": 1}
                return responseVal
            else:
                print("invalid Plan Details")
                responseVal = {"success": False, "message": "invalid Plan Details,Please contact Admin",
                               "statusCode": 1}
                return responseVal
        except Exception as e:
            exceptionMail(user_id, "PAYMENT FAILURE", '/payment', str(e))
            responseVal = {"success":False,"message":str(e),"statusCode":1}
            return responseVal
    else:
        print("payment Failure")
        responseVal = {"success":False,"message":"Payment Failed,Invalid Transaction","statusCode":2}
        return responseVal

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def amountTobePaid(request):
    stratsessionutil = StartFitSessionUtil()
    try:
        username = stratsessionutil.get_user_insession(request)
        url="payment/amountTobePaid"
        data = json.loads(request.body.decode('utf-8'))
        try:
            if username!=None:
                #user = username['id']
                plan_id = data['plan_id']
                planvalues = Plan.objects.get(id = plan_id)
                planPrice = planvalues.price
                '''userPlanDetails = UserPlan.objects.select_related('Plan').filter(user_id = user,status = 1).values('plan_id__price','id','plan_id')
                if userPlanDetails.exists():
                    for val in userPlanDetails:
                        value = dict(val)
                    planPrice = value['plan_id__price']
                    userplan_id = value['id']
                    plan_id = value['plan_id']'''
                return JsonResponse({"success":True,"amount":planPrice,"plan_id":plan_id})
                #else:
                #return JsonResponse({"message":"You do not have any active plan","success":False})
            else:
                return JsonResponse({"message":"userLogged out","success":False})
        except Exception as e:
            logger.error("error")
            exceptionMail(username, "GET", url, str(e))
            return JsonResponse({"message":"Invalid Details","success":False})
    except Exception as e:
        logger.error("error")
        return JsonResponse({"message":"Invalid Details","success":False})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def paymentsInformation(request):
    stratsessionutil = StartFitSessionUtil()
    try:
        username = stratsessionutil.get_user_insession(request)
        url="payment/paymentsInfo"
        try:
            if username!=None:
                if 'rows' in request.POST and request.POST['rows'] != '':
                    rows = int(request.POST['rows'])
                else:
                    rows = PAGING_ROWS
                if 'page' in request.POST and request.POST['page'] != '':
                    page = int(request.POST['page'])
                else:
                    page = 1
                offset = (page - 1) * rows
                tot = page * rows
                dataArr = []
                user = username['id']
                paymentsInfo = TransactionHistory.objects.select_related('User').filter(paidBy_id = user).values('paidBy__first_name','paidTo','purpose','amount','transation_id','createdDate')
                total = len(paymentsInfo)
                data = paymentsInfo[offset:tot]
                if paymentsInfo.exists():
                    for val in data:
                        value = dict(val)
                        value['createdDate'] = value['createdDate'].strftime("%d/%m/%Y %H:%M:%S")
                        dataArr.append(value)
                    return JsonResponse({"rows": dataArr, "total": total})
                else:
                    return JsonResponse({"message":"You do not have any Active Program","success":False})
            else:
                return JsonResponse({"message":"userLogged out","success":False})
        except Exception as e:
            logger.error("error")
            exceptionMail(username, "GET", url, str(e))
            return JsonResponse({"msg": str(e)})
    except Exception as e:
        logger.error("error")
        return JsonResponse({"msg": str(e),"success":False})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def saveTrasactions(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    url="payment/paymentsInfo"
    data = json.loads(request.body.decode('utf-8'))
    print(data,"123")
    try:
        if username!=None:
            user = username['id']
            values = data['trArr']
            for val in values:
                if val['stratfitcharges'] !=0 and val['stratfitcharges'] != None:
                    transactions = TransactionHistory.objects.create(
                        paidBy_id=user,
                        paidTo="StratFit",
                        purpose="Platform Charges",
                        amount=float(val['stratfitcharges']),
                        transation_id=data['transactionId'],
                    )
                    transactions.save()
                if val['coachcharges'] !=0 and val['coachcharges'] != None:
                    transactions = TransactionHistory.objects.create(
                        paidBy_id=user,
                        paidTo=val['coachName'],
                        purpose="Coach Charges",
                        amount=float(val['coachcharges']),
                        transation_id=data['transactionId'],
                    )
                    transactions.save()
                if val['servicetax'] !=0 and val['servicetax'] != None:
                    transactions = TransactionHistory.objects.create(
                        paidBy_id=user,
                        paidTo="Govt",
                        purpose="Service Tax",
                        amount=float(val['servicetax']),
                        transation_id=data['transactionId'],
                    )
                    transactions.save()
            print("came Into Here")
            return JsonResponse({"success":True,"message":"Transaction Successful" })
    except Exception as e:
        logger.error("error")
        return JsonResponse({"msg": str(e),"success":False})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def ionicSaveTransactions(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    url="payment/paymentsInfo"
    data = json.loads(request.body.decode('utf-8'))
    try:
        if username!=None:
            user = username['id']
            #planPrice = int(data['amount'])
            coachVal = Plan.objects.filter(id = data['plan_id']).select_related('User').values('createdBy_id__first_name','price','indianIosPrice','indianPrice','iosPrice')
            for val in coachVal:
                coachObj = dict(val)
                coachName = coachObj['createdBy_id__first_name']
                if 'deviceType' in data and data['deviceType']!='':
                    if data['deviceType'] == "ios":
                        if username['userCountry'] == 88:
                            planPriceVal = coachObj['indianIosPrice']
                            priceMap = PriceMapping.objects.get(inr=planPriceVal)
                            planPrice = priceMap.usd
                        else:
                            planPriceVal = coachObj['iosPrice']
                            priceMap = PriceMapping.objects.get(inr=planPriceVal)
                            planPrice = priceMap.usd
                    else:
                        if username['userCountry'] == 88:
                            planPrice = coachObj['indianPrice']
                        else:
                            planPrice = coachObj['price']
                else:
                    planPrice = coachObj['price']

            serviceTax = planPrice - (planPrice / 1.18)
            stratfitPlatform = (planPrice - serviceTax) * 0.2
            strfitTDS = stratfitPlatform * 0.1
            stratfitNet = stratfitPlatform - strfitTDS
            coachRevenue = planPrice - stratfitPlatform - serviceTax
            coachTDS = coachRevenue * 0.1
            coachNet = coachRevenue - coachTDS
            transactions = TransactionHistory.objects.create(
                paidBy_id=user,
                paidTo="Govt",
                purpose="Service Tax",
                amount=float(serviceTax)+float(strfitTDS)+float(coachTDS),
                transation_id=data['transactionId'],
            )
            transactions.save()
            transactions1 = TransactionHistory.objects.create(
                paidBy_id=user,
                paidTo="Govt",
                purpose="StratFit PlatForm",
                amount=float(stratfitNet),
                transation_id=data['transactionId'],
            )
            transactions1.save()

            transactions2 = TransactionHistory.objects.create(
                paidBy_id=user,
                paidTo=coachName,
                purpose="CoachCharges",
                amount=float(coachNet),
                transation_id=data['transactionId'],
            )
            transactions2.save()
        return JsonResponse({"success":True,"message":"Transaction Successful" })
    except Exception as e:
        logger.error("error")
        return JsonResponse({"msg": str(e),"success":False})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def newpdf(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    url = "payment/newpdf"
    data = json.loads(request.body.decode('utf-8'))
    print(data, "123")
    try:
        file_name = os.path.join(settings.MEDIA_URL, datetime.now().strftime('%Y_%m_%d_%H_%M_%S.pdf'))
        doc = SimpleDocTemplate(file_name, pagesize=letter,rightMargin=72, leftMargin=72,topMargin=72, bottomMargin=18)
        Story = []
        logo = "http://stratfit.net/assets/images/fulllogo.png"
        magName = "Pythonista"
        issueNum = 12
        subPrice = "99.00"
        limitedDate = "03/05/2010"
        freeGift = "tin foil hat"

        formatted_time = time.ctime()
        full_name = "Mike Driscoll"
        address_parts = ["411 State St.", "Marshalltown, IA 50158"]

        im = Image(logo, 2 * inch, 2 * inch)
        Story.append(im)

        styles = getSampleStyleSheet()
        styles.add(ParagraphStyle(name='Justify', alignment=TA_JUSTIFY))
        ptext = '<font size=12>%s</font>' % formatted_time

        Story.append(Paragraph(ptext, styles["Normal"]))
        Story.append(Spacer(1, 12))

        # Create return address
        ptext = '<font size=12>%s</font>' % full_name
        Story.append(Paragraph(ptext, styles["Normal"]))
        for part in address_parts:
            ptext = '<font size=12>%s</font>' % part.strip()
            Story.append(Paragraph(ptext, styles["Normal"]))

        Story.append(Spacer(1, 12))
        ptext = '<font size=12>Dear %s:</font>' % full_name.split()[0].strip()
        Story.append(Paragraph(ptext, styles["Normal"]))
        Story.append(Spacer(1, 12))

        ptext = '<font size=12>We would like to welcome you to our subscriber base for %s Magazine! \You will receive %s issues at the excellent introductory price of $%s. Please respond by\%s to start receiving your subscription and get the following free gift: %s.</font>' % (magName,issueNum,subPrice,limitedDate,freeGift)
        Story.append(Paragraph(ptext, styles["Justify"]))
        Story.append(Spacer(1, 12))

        ptext = '<font size=12>Thank you very much and we look forward to serving you.</font>'
        Story.append(Paragraph(ptext, styles["Justify"]))
        Story.append(Spacer(1, 12))
        ptext = '<font size=12>Sincerely,</font>'
        Story.append(Paragraph(ptext, styles["Normal"]))
        Story.append(Spacer(1, 48))
        ptext = '<font size=12>Ima Sucker</font>'
        Story.append(Paragraph(ptext, styles["Normal"]))
        Story.append(Spacer(1, 12))
        doc.build(Story)
        FROM_EMAIL = "admin@stratfit.in"
        print(FROM_EMAIL, "1234565434566543456765434")
        msg = EmailMultiAlternatives("nothing", "nothing", FROM_EMAIL, ["ramakotisaikumar@gmail.com"])
        attachment = open(file_name, 'rb')
        msg.attach('myfile.pdf', attachment.read(), 'application/pdf')
        # msg.attach(file_name)
        msg.send()
        return JsonResponse({"message":"Invoice Sent to your MaiId","success":True})
    except Exception as e:
        logger.error("error")
        return JsonResponse({"msg": str(e),"success":False})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def getTransactionsDetails(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    data = json.loads(request.body.decode('utf-8'))
    try:
        if username!=None:
            arr = []
            if 'rows' in request.POST and request.POST['rows'] != '':
                rows = int(request.POST['rows'])
            else:
                rows = 50

            if 'page' in request.POST and request.POST['page'] != '':
                page = int(request.POST['page'])
            else:
                page = 1
            offset = (page - 1) * rows
            tot = page * rows
            transactions = TransactionHistory.objects.select_related('User').values('paidBy_id__first_name','paidTo','purpose','amount','transation_id').order_by('-createdDate')
            total = len(transactions)
            data = transactions[offset:tot]
            for dt in data:
                dataObj = dict(dt)
                arr.append(dataObj)
            return JsonResponse({"success":True,"details":arr,"total":total})
        else:
            return JsonResponse({"success": False, "message": "User Logged Out"})
    except Exception as e:
        logger.error("error")
        return JsonResponse({"msg": str(e),"success":False})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def exportDetails(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    try:
        if username!=None:
            response = HttpResponse(content_type='text/csv')
            response['Content-Disposition'] = 'attachment; filename="transactionDetails.csv"'
            data = TransactionHistory.objects.select_related('User').values('paidBy_id__first_name','paidTo','purpose','amount','transation_id').order_by('-createdDate')
            writer = csv.writer(response)
            for row in data:
                rowData = dict(row)
                writer.writerow([rowData['paidBy_id__first_name']])
            return response
    except Exception as e:
        return JsonResponse({"msg":str(e)})


@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def revenueDetails(request):
    data = json.loads(request.body.decode('utf-8'))
    dateArr = []
    amountArr = []
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    user = username['id']
    try:
        if username != None:
            dateArr = []
            amountArr = []
            x = connection.cursor()
            query = "SELECT sum(amount) as amount,DATE_FORMAT(createdDate, '%Y-%m-%d') as  createdDate from `payment_transactionhistory`  WHERE createdDate BETWEEN ' "+data['startDate']+" ' AND ' "+data['endDate']+" ' group by DATE_FORMAT(createdDate, '%Y-%m-%d')"
            '''query = "SELECT sum(amount) as amount,DATE_FORMAT(createdDate, '%Y-%m-%d') as  createdDate from `payment_transactionhistory`  WHERE createdDate group by DATE_FORMAT(createdDate, '%Y-%m-%d')"'''
            x.execute(query)
            resultQuery = dictfetchall(x)
            print(resultQuery,"kranthi")
            for rev in resultQuery:
                revObj = dict(rev)
                dateArr.append(revObj['createdDate'])
                amountArr.append(revObj['amount'])
            return JsonResponse({"success": True, "dateArr": dateArr, "amountArr": amountArr})
        else:
            return JsonResponse({"success":False,"message":"No data"})
    except Exception as e:
        logger.exception("something wrong")
        return JsonResponse({"msg": str(e)})

def dictfetchall(cursor):
    "Return all rows from a cursor as a dict"
    columns = [col[0] for col in cursor.description]
    return [
        dict(zip(columns, row))
        for row in cursor.fetchall()
    ]

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def programdetails(request):
    stratsessionutil = StartFitSessionUtil()
    username = stratsessionutil.get_user_insession(request)
    user = username['id']
    try:
        if username != None:
            amountArr = []
            activeArr = []
            compltedArr = []
            futureArr = []
            freeArr = []
            x = connection.cursor()
            query =  "SELECT t1.amount, t3.planName, t2.status, t2.id, t2.freetrail, DATE_FORMAT(t2.startDate, '%d %b  %Y') AS startdate, DATE_FORMAT(t2.nextRenewalDate, '%d %b %Y') AS nextRenewalDate  FROM payment_transactionhistory t1 LEFT JOIN Userplan_userplan t2 ON t1.userplan_id=t2.id LEFT JOIN Plan_plan t3 ON t2.plan_id=t3.id WHERE t1.paidBy_id="+  str(user) +" ORDER BY t2.startDate ASC"
            print(query)
            x.execute(query)
            resultQuery = dictfetchall(x)
            print(resultQuery,"kranthi")
            for pgm in resultQuery:
                print(pgm,"saru")
                revObj = dict(pgm)
                if revObj['status']==1:
                    revObj['sta'] = "Active Program"
                    if revObj['freetrail']==1:
                        revObj['amount'] = "free trail"
                        activeArr.append(revObj)
                    else:
                        revObj['amount'] = round(revObj['amount'])
                        activeArr.append(revObj)
                    print(activeArr,"123")
                elif  revObj['status']==2:
                    revObj['sta'] = "Program Completed"
                    if revObj['freetrail'] == 1:
                        revObj['amount'] = "free trail"
                        compltedArr.append(revObj)
                    else:
                        revObj['amount'] = round(revObj['amount'])
                        compltedArr.append(revObj)
                    print(compltedArr,"11111")
                elif revObj['status']==3:
                     revObj['sta'] = "Future Program"
                     if revObj['freetrail'] == 1:
                         revObj['amount'] = "free trail"
                         futureArr.append(revObj)
                     else:
                        revObj['amount'] = round(revObj['amount'])
                        futureArr.append(revObj)
                     print(futureArr, "22333")
            return JsonResponse({"success": True,"active": activeArr,"complted": compltedArr,"future": futureArr})
        else:
            return JsonResponse({"success":False,"message":"No data"})
    except Exception as e:
        logger.exception("something wrong")
        return JsonResponse({"msg": str(e)})

@api_view(['GET', 'POST'])
@authentication_classes((SessionAuthentication, IsAuthenticated))
@never_cache
def PgmDataDetails(request):
    data = json.loads(request.body.decode('utf-8'))
    #user = request.session['user_id']
    stratsessionutil = StartFitSessionUtil()
    try:
        username = stratsessionutil.get_user_insession(request)
        user = username['id']
        if username !='':
            userpgmdata = UserExercise.objects.select_related('utility_exercise__id').filter(user_id= user,userplan_id=data['id']).values('exerciseWorkWeight','totalReps','id','exerciseId','exerciseId__exerciseName','exerciseDate','session_id','totalSets','intensity','exerciseId__workFormula','plan_id__planName')
            if userpgmdata.exists():
                planArr = []
                for dt in userpgmdata:
                    planObj = dict(dt)
                    planObj['exerciseDate'] = planObj['exerciseDate'].strftime("%d %B %Y")
                    print(planObj,"sss")
                    planArr.append(planObj)
                return JsonResponse({"success": True, "pragramdata": planArr})
            else:
                return JsonResponse({"success": False, "message": "No Exercise detail"})
        else:
            return JsonResponse({"success": False, "message": "No Plan"})

    except Exception as e:
        logger.exception("something wrong")
        return JsonResponse({"msg": str(e)})

def advpaypalAuthToken(request):
    data = json.loads(request.body.decode('utf-8'))
    print(data['amount'])
    params = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'METHOD':'SetExpressCheckout',
        'VERSION':95,
        'PAYMENTREQUEST_0_PAYMENTACTION':'Authorization',     # type of payment
        'PAYMENTREQUEST_0_AMT':data['amount'],#50,              # amount of transaction
        'PAYMENTREQUEST_0_CURRENCYCODE':'USD',
        'CANCELURL':"http://"+request.META['HTTP_HOST']+"/#fail",    #For use if the consumer decides not to proceed with payment
        'RETURNURL':"http://"+request.META['HTTP_HOST']+"/#advsuccess"  #For use if the consumer proceeds with payment
    }

    params_string = urllib.parse.urlencode(params).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read() #gets the response and parse it.
    response_dict = parse_qs(response)
    print(response_dict)
    response_token = response_dict["TOKEN".encode("utf-8")][0]
    rurl = settings.PAYPAL_URL+str(response_token.decode("utf-8")) #gather the response token and redirect to paypal to authorize the payment
    return JsonResponse(rurl, safe=False)

def advdoCheckout(request):
    data = json.loads(request.body.decode('utf-8'))
    exparams = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'VERSION':95,

        'METHOD':'DoExpressCheckoutPayment',
        'TOKEN':data['token'],#'EC-8B556284J2540611G', #get the token from the request that is redirected
        'PAYERID':data['payerId'],#'5N4HH3FY9D52J',      # customer's unique PayPal ID
        'PAYMENTREQUEST_0_PAYMENTACTION':'Authorization',    # payment type
        'PAYMENTREQUEST_0_AMT':data['amount'],#50,             # transaction amount
        'PAYMENTREQUEST_0_CURRENCYCODE':'USD'
    }

    params_string = urllib.parse.urlencode(exparams).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read()
    print(response,"first")
    return JsonResponse(str(response), safe=False)


def advcheckPayment(request):
    data = json.loads(request.body.decode('utf-8'))
    exparams = {
        'USER' : 'soubhik.g-facilitator_api1.stratfit.co', # Edit this to your API user name
        'PWD' : 'FBTUZ737FJCW47CY', # Edit this to your API password
        'SIGNATURE' : 'AFcWxV21C7fd0v3bYYYRCpSSRl31AixKxpaoAo3GzQM51leFyvmmUaxn',
        'VERSION':95,

        'METHOD':'DoCapture',
        'AUTHORIZATIONID':data['transactionId'],#'3H008600KT432091G', #get the token from the request that is redirected      # customer's unique PayPal ID
        'AMT':data['amount'],#50,      # transaction amount
        'CURRENCYCODE':'USD',
        'COMPLETETYPE':'Complete'
    }

    params_string = urllib.parse.urlencode(exparams).encode("utf-8")
    response = urllib.request.urlopen('https://api-3t.sandbox.paypal.com/nvp', params_string).read()
    print(response,"second")
    return JsonResponse(str(response), safe=False)



