var track = {},
    common = require('./../../utils/common.js'),
    logger = require('../../../logger'),
    semusiConfig = require('./../../config'),
    AWS = require('aws-sdk'),
    unirest = require('unirest'),
    apsalar = require('./../../ref_plugins/apsalar_callback.js'),
    appsFlyer = require('./../../ref_plugins/appsflyer_callback.js'),
    gAdwords = require('./../../ref_plugins/gadwords_callback.js'),
    cacheApi = require('./../../utils/semusi.cache.js'),
    mattune = require('./../../ref_plugins/mattune_callback.js');
    semusiConfig = require('../../config');
    
(function (track) {

	// track.recordClick = function (params){
  //
  //       var argProps = {
  //           'clickId':     { 'required': true, 'type': 'String' },
  //           'campaignId':     { 'required': true, 'type': 'String' },
  //           'promoterId':{'required':true,'type':'String'},
  //           'userAgent':{'required':false,'type':'String'},
  //           'isConfirmed':{'required':false,'type':'Boolean'},
  //       },
  //       clickDetail = {};
  //   	if (!(clickDetail = common.validateArgs(params.qstring.args, argProps))) {
  //           common.returnMessage(params, 400, 'Not enough args');
  //           return false;
  //       }
  //
  //       clickDetail.createdOn = parseInt(common.getCurrentEpochTime());
  //   	clickDetail.ip = params.ip_address;
  //
  //       common.db.collection('promoter_campaigns').findOne({"_id":common.db.ObjectID(clickDetail.campaignId)},function(err,campaign){
  //       	if(campaign){
  //               clickDetail['createdAt'] = common.getCurrentEpochTime();
  //       		common.db.collection('campaignconversions_'+ params.qstring.appId).insert(clickDetail, function(err, clickRecord) {
  //                   if(clickRecord && clickRecord.result && clickRecord.result.ok){
	//         			//Get promoter details
	//         			common.db.collection('promoters').findOne({"_id":common.db.ObjectID(campaign.promoterId)},function(err,promoter){
	//         				if(promoter){
	//         					//Construct redirect url
	// 		        			var referrer = encodeURIComponent("utm_source="+promoter.promoterName+"&utm_medium="+campaign.type+"&utm_content=affiliatedLink&utm_campaign="+campaign.campaignName+"&trackId="+clickRecord["ops"][0]._id+"&clickId="+clickDetail.clickId);
	// 		        			var url = campaign.trackingUrl + "&referrer="+referrer;
	// 	        				clickDetail.url = url;
	// 		        			common.returnOutput(params, clickDetail);
	//         				}
	//         				else{
	//         					common.returnMessage(params, 400, 'System was not able to find promoter record.');
	//         				}
  //
	//         			});
  //
	//         		}
	//         		else{
	//         			common.returnMessage(params, 400, 'System was not able to create click record.');
	//         		}
	//         	});
  //       	}
  //       	else{
  //       		common.returnMessage(params, 400, 'This campaign does not exist in our system.');
  //       	}
  //
  //       });
  //
	// };

  track.recordClick = function (params){

        var argProps = {
            'clickId':     { 'required': true, 'type': 'String' },
            'campaignId':     { 'required': true, 'type': 'String' },
            'promoterId':{'required':true,'type':'String'},
            'userAgent':{'required':false,'type':'String'},
            'referrer':{'required':false,'type':'String'},
            'utm_content':{'required':false,'type':'String'},
            'utm_term':{'required':false,'type':'String'},
            'isConfirmed':{'required':false,'type':'Boolean'},
        },
        clickDetail = {};
    	if (!(clickDetail = common.validateArgs(params.qstring.args, argProps))) {
            common.returnMessage(params, 400, 'Not enough args');
            return false;
        }

        clickDetail.createdOn = parseInt(common.getCurrentEpochTime());
    	clickDetail.ip = params.ip_address;

         
        // get device model
        common.db.collection('promoter_campaigns').findOne({"_id":common.db.ObjectID(clickDetail.campaignId)},function(err,campaign){
        	if(campaign){
                clickDetail['createdAt'] = common.getCurrentEpochTime();

                unirest.post("https://neutrinoapi-user-agent-info.p.mashape.com/user-agent-info")
                .header("X-Mashape-Key", "9UMbe97HZfmshOPSF8E5Del17606p1V1Wu0jsnw7ATBk96mb8C")
                .header("Content-Type", "application/x-www-form-urlencoded")
                .header("Accept", "application/json")
                .send("user-agent="+clickDetail.userAgent)
                .end(function (result) {
                    // dump device information
                    if(result && result.body && result.body['mobile-brand']){
                        clickDetail.device = result.body['mobile-brand'];
                    }
                    // dump device brand information
                    if(result && result.body && result.body['mobile-brand']){
                        clickDetail.model = result.body['mobile-model'];
                    }

                    // get request headers
                    clickDetail.headersInfo = params.req.headers;

                    // dump click record
                    common.db.collection('campaignconversions_'+ params.qstring.appId).insert(clickDetail, function(err, clickRecord) {
                        if(clickRecord && clickRecord.result && clickRecord.result.ok){
                            //Get promoter details
                            common.db.collection('promoters').findOne({"_id":common.db.ObjectID(campaign.promoterId)},function(err,promoter){
                                if(promoter){
                                    //Construct redirect url
                                    var utm_content = (clickDetail.utm_content != '')? clickDetail.utm_content : 'affiliatedLink';
                                    var utm_term = (clickDetail.utm_term != '')? clickDetail.utm_term : '';
                                    var referrer = encodeURIComponent("utm_source="+promoter.promoterName+"&utm_medium="+campaign.type+"&utm_content="+utm_content+"&utm_term="+utm_term+"&utm_campaign="+campaign.campaignName+"&trackId="+clickRecord["ops"][0]._id+"&clickId="+clickDetail.clickId);
                                    var url = campaign.trackingUrl + "&referrer="+referrer;
                                    clickDetail.url = url;

                                    // set refferrer into cache
                                    var headerVal = params.qstring.appId;
                                    /*
                                    Object.keys(params.req.headers).forEach(function(key){
                                        headerVal += params.req.headers[key];
                                    });*/
                                    if(params.req.headers['x-forwarded-for']){
                                       headerVal += params.req.headers['x-forwarded-for'];
                                    }
                                    if(params.req.headers['x-real-ip']){
                                       headerVal += params.req.headers['x-real-ip'];
                                    }
                                    if(params.req.headers['host']){
                                       headerVal += params.req.headers['host'];
                                    }

                                     
                                    var haderHash = common.crypto.createHash(semusiConfig.shaV1Hash).update( headerVal + "").digest('hex');
                                     
                                    cacheApi.setKey("referrer_" + haderHash, JSON.stringify({ _ref : referrer, headers : params.req.headers }));

                                    common.returnOutput(params, clickDetail);
                                }
                                else{
                                    common.returnMessage(params, 400, 'System was not able to find promoter record.');
                                }

                            });

                        }
                        else{
                            common.returnMessage(params, 400, 'System was not able to create click record.');
                        }
                    });
                });
        	}
        	else{
        		common.returnMessage(params, 400, 'This campaign does not exist in our system.');
        	}

        });

	};

	track.addPromoter = function(params){
        var argProps = {
			'promoterMemberId': { 'required': true, 'type': 'String' },
			'promoterName': { 'required': true, 'type': 'String' },
			'promoterCompany': { 'required': false, 'type': 'String' },
			'promoterAddress': { 'required': false, 'type': 'String' },
			'promoterEmail': { 'required': false, 'type': 'String' },
			'promoterPhone': { 'required': false, 'type': 'String' },
			'promoterContactPerson': { 'required': false, 'type': 'String' }
        },
        promoter = {};

        if (!(promoter = common.validateArgs(params.qstring.args, argProps))) {
            common.returnMessage(params, 400, 'Not enough args');
            return false;
        }
        promoter.createdOn = parseInt(common.getCurrentEpochTime());

        promoter['createdAt'] = common.getCurrentEpochTime();
        common.db.collection('promoters').insert(promoter, function(err, result) {
            common.returnOutput(params, result);
        });

	};

    track.updatePromoter = function(params){
        var argProps = {
            'promoterMemberId': { 'required': true, 'type': 'String' },
            'promoterName': { 'required': true, 'type': 'String' },
            'promoterCompany': { 'required': false, 'type': 'String' },
            'promoterAddress': { 'required': false, 'type': 'String' },
            'promoterEmail': { 'required': false, 'type': 'String' },
            'promoterPhone': { 'required': false, 'type': 'String' },
            'promoterContactPerson': { 'required': false, 'type': 'String' }
        },
        promoter = {};

        if (!(promoter = common.validateArgs(params.qstring.args, argProps))) {
            common.returnMessage(params, 400, 'Not enough args');
            return false;
        }
        promoter.modifiedOn = parseInt(common.getCurrentEpochTime());

        promoter['updatedAt'] = common.getCurrentEpochTime();
        common.db.collection('promoters').update({"_id":common.db.ObjectID(params.qstring.promoterId)},{'$set':promoter},{safe:true}, function(err, result) {
            common.returnOutput(params, result);
        });

    };

    track.getPromotersByMember = function(params){
        //{"promoterMemberId": params.qstring.promoterMemberId}
        common.db.collection('promoters').find().toArray(function(err, result) {
            common.returnOutput(params, result);
        });
    };

    track.getPromotersById = function(params){
        common.db.collection('promoters').findOne({"_id":common.db.ObjectID(params.qstring.promoterId)},function(err, result) {
            common.returnOutput(params, result);
        });
    };

    track.getMemberApps = function(params){
        common.db.collection('members').findOne({"_id":common.db.ObjectID(params.qstring.memberId)},function(err,member){
            if(member){
                var adminOfAppIds = [],
                    userOfAppIds = [];
                if(member.global_admin){
                    common.db.collection('apps').find({"isAppDeleted":"false"}).toArray(function(err,apps){
                        common.returnOutput(params, apps);
                    });
                }
                else{
                    if (member.admin_of) {
                        for (var i = 0; i < member.admin_of.length ;i++) {
                            if (member.admin_of[i] == "") {
                                continue;
                            }

                            adminOfAppIds[adminOfAppIds.length] = common.db.ObjectID(member.admin_of[i]);
                        }
                    }

                    if (member.user_of) {
                        for (var i = 0; i < member.user_of.length ;i++) {
                            userOfAppIds[userOfAppIds.length] = common.db.ObjectID(member.user_of[i]);
                        }
                    }
                    common.db.collection('apps').find({ _id : { '$in': userOfAppIds },"isAppDeleted":"false" }).toArray(function(err, apps) {
                        common.returnOutput(params, apps);
                    });
                }
            }
        });
    };


	track.addPromoterCampaign = function(params){
        var argProps = {
			'promoterId': { 'required': true, 'type': 'String' },
			'campaignName': { 'required': true, 'type': 'String' },
			'type': { 'required': false, 'type': 'String' },
			'appid': { 'required': false, 'type': 'String' },
			'callbackurl': { 'required': false, 'type': 'String' },
			'param': { 'required': false, 'type': 'String' },
			'costPerInstall': { 'required': false, 'type': 'String' },
			'trackingUrl': { 'required': false, 'type': 'String' },
        },
        promoterCampaign = {};

        if (!(promoterCampaign  = common.validateArgs(params.qstring.args, argProps))) {
            common.returnMessage(params, 400, 'Not enough args');
            return false;
        }
        promoterCampaign.createdOn = parseInt(common.getCurrentEpochTime());

        promoterCampaign['createdAt'] = common.getCurrentEpochTime();
        common.db.collection('promoter_campaigns').insert(promoterCampaign, function(err, result) {
            common.returnOutput(params, result);
        });

	};

    track.updatePromoterCampaign = function(params){
        var argProps = {
            'promoterId': { 'required': true, 'type': 'String' },
            'campaignName': { 'required': true, 'type': 'String' },
            'type': { 'required': false, 'type': 'String' },
            'appid': { 'required': false, 'type': 'String' },
            'callbackUrl': { 'required': false, 'type': 'String' },
            'param': { 'required': false, 'type': 'String' },
            'costPerInstall': { 'required': false, 'type': 'String' },
            'trackingUrl': { 'required': false, 'type': 'String' },
        },
        promoterCampaign = {};

        if (!(promoterCampaign  = common.validateArgs(params.qstring.args, argProps))) {
            common.returnMessage(params, 400, 'Not enough args');
            return false;
        }
        promoterCampaign.modifiedOn = parseInt(common.getCurrentEpochTime());

        promoterCampaign['updatedAt'] = common.getCurrentEpochTime();
        common.db.collection('promoter_campaigns').update({"_id":common.db.ObjectID(params.qstring.campaignId)},{'$set':promoterCampaign},{safe:true}, function(err, result) {
            if(err){
                logger.error(`error => ${err}`);  
            }
            common.returnOutput(params, result);
        });

    };

    track.getPromoterCampaigns = function(params){
        common.db.collection('promoter_campaigns').find().toArray(function(err, result) {
            common.returnOutput(params, result);
        });
    };

    track.getPromoterCampaignById = function(params){
        common.db.collection('promoter_campaigns').findOne({"_id":common.db.ObjectID(params.qstring.campaignId)},function(err, result) {
            if(result){
                result.appIceUrl= semusiConfig.appIceUrl +"appId="+result.appid+"&campaignId="+result._id +"&promoterId="+result.promoterId+"&clickId={CLICK_ID}";
            }
            common.returnOutput(params, result);
        });
    };

    track.getClickRecords = function(params){
        var argProps = {
            'appid': { 'required': true, 'type': 'String' },
            'promoterId': { 'required': false, 'type': 'String' },
            'campaignId': { 'required': true, 'type': 'String' },
            'confirmed': { 'required': false, 'type': 'String' },
            'statusCode': { 'required': false, 'type': 'Number' },
            'clickFromDate': { 'required': false, 'type': 'Number' },
            'clickToDate': { 'required': false, 'type': 'Number' },
            'confirmFromDate': { 'required': false, 'type': 'Number' },
            'confirmToDate': { 'required': false, 'type': 'Number' },
        },
        clickRecordParams = {};
        if (!(clickRecordParams  = common.validateArgs(params.qstring.args, argProps))) {
            common.returnMessage(params, 400, 'Not enough args');
            return false;
        }

        var matchParams={$match:{}};

        if(clickRecordParams.promoterId!=="zzz"){
            matchParams.$match.promoterId = clickRecordParams.promoterId;
        }
        if(clickRecordParams.campaignId!=="zzz"){
            matchParams.$match.campaignId = clickRecordParams.campaignId;
        }
        if(clickRecordParams.confirmed!=="zzz"){
            matchParams.$match.isConfirmed = (clickRecordParams.confirmed=="true") ? true : false;
        }
        if(clickRecordParams.statusCode!=0){
            matchParams.$match.statusCode = clickRecordParams.statusCode;
        }
        if(clickRecordParams.clickFromDate!=0 && clickRecordParams.clickToDate!=0){
            matchParams.$match.createdOn = {$gte:clickRecordParams.clickFromDate,$lte:clickRecordParams.clickToDate};
        }

        if(clickRecordParams.confirmFromDate!=0 && clickRecordParams.confirmToDate!=0){
            matchParams.$match.confirmedOn = {$gte:clickRecordParams.confirmFromDate,$lte:clickRecordParams.confirmToDate};
        }
        logger.info(`matchParams=> ${matchParams}`);
        common.db.collection('campaignconversions_'+clickRecordParams.appid).aggregate([
            matchParams,
            { $project:{clickId:1,createdOn:1,confirmedOn:1,did:1,statusCode:1}}
        ],function(err,result){
            common.returnOutput(params, result);
        });


    };

    track.callbackConfirmed = function(params,channel,postData){
        awsRegion = semusiConfig.AWS_REGION;

         if(channel == 'appsflyer'){
            var data = appsFlyer.createAppUserObject(postData);
            if(data!=undefined){
                registerInstall(data);
            }
            common.returnMessage(params, 200, true);
            return true;

        }
        else if(channel == 'apsalar'){
            var data = apsalar.createAppUserObject(postData);

	     
            var data = apsalar.createAppUserObject(postData);
            if(data!=undefined){
                registerInstall(data);
            }
            common.returnMessage(params, 200, true);
            return true;
        }
        else if(channel == 'tune' || channel == 'mat')
        {
            //get the app info for the given app
            common.db.collection('apps').findOne({'_id':common.db.ObjectID(params.qstring.app_id)}, function (err, app) {
                if (!app) {
                    //validation error
                    common.returnMessage(params, 404, 'App not found');
                    return true;
                }
                else{
                    var newparams = {
                        'app_id':app['_id'],
                        'app_cc':app['country'],
                        "appTimezone":app['timezone'],
                        "time":'',
                        'ip_address':'',
                        'user':{
                            'country':'',
                            'city':''
                        },
                        'qstring':{
                            'app_key':app['key'],
                            'device_id':'',
                            'metrics':{},
                            'events':{},
                            'session_duration':'',
                            'begin_session':1,
                            'end_session':'',
                            'timestamp':''
                        }
                    };
                    newparams = mattune.getParamsObj(newparams,postData);

                    AWS.config.update({
                        accessKeyId: semusiConfig.AWS_ACCESS_KEY_ID,
                        secretAccessKey: semusiConfig.AWS_SECRET_KEY,
                        region: awsRegion
                      });

                    sqs = new AWS.SQS();

                    var queueUrl = '';
                    if(semusiConfig.IsProduction == true)
                    {
                        queueUrl = semusiConfig.ProductionQueueDeviceImportUrl;
                    }
                    else
                    {
                        queueUrl = semusiConfig.StagingQueueDeviceImportUrl;
                    }

                    //send the object to Queue
                    var queueObj = {};
                    queueObj.newparamsObj = newparams;
                   // queueObj.params = params;

                    var boxParams = {
                        MessageBody: JSON.stringify(queueObj),
                        QueueUrl: queueUrl,
                        DelaySeconds: 0
                    };


                    sqs.sendMessage(boxParams, function (err, data) {
                        if (err) {
                            logger.error(`error sending msg to SQS ${err}`);
                            logger.error(`error.stack ${err.stack}`); 
                           
                        } // an error occurred
                        else {
                           
                        }
                        ;
                      });

                    common.returnMessage(params, 200, true);
                    return true;
                }
            });
        }
        else
        {
            common.returnMessage(params, 404, 'Channel plugin not found');
            return true;
        }
    };

    function registerInstall(data){

        AWS.config.update({
            accessKeyId: semusiConfig.AWS_ACCESS_KEY_ID,
            secretAccessKey: semusiConfig.AWS_SECRET_KEY,
            region: awsRegion
        });

        sqs = new AWS.SQS();

        var queueUrl = '';
        if(semusiConfig.IsProduction == true){
            queueUrl = semusiConfig.ProductionQueueDeviceImportUrl;
        }
        else{
            queueUrl = semusiConfig.StagingQueueDeviceImportUrl;
        }

        // add buffer time for update postback information
        data.timestamp = parseInt(data.timestamp+semusiConfig.postbackInstallBufferSec);
        data.inittime = parseInt(data.inittime+semusiConfig.postbackInstallBufferSec);

        // queueObj.params = params;
        var boxParams = {
            MessageBody: JSON.stringify(data),
            QueueUrl: queueUrl,
            DelaySeconds: 0
        };
        sqs.sendMessage(boxParams, function (err, data) {
            if (err) {
                logger.error(`error sending msg to SQS ${err}`);
               
            } // an error occurred
            else {
                logger.info(`message sent`); 
            }
        });
    }

    function packApps(apps) {
        var appsObj = {};

        for (var i = 0; i < apps.length ;i++) {
            appsObj[apps[i]._id] = {
                '_id': apps[i]._id,
                'name' : apps[i].name
            };
        }

        return appsObj;
    }

}(track));

module.exports = track;
