package deliveryLimitation
import "net/http"
import "regexp"
import "strings"
import "reflect"
import "alpha/adDelivery/structure"
import "alpha/adDelivery/globalvariables"
import "alpha/adDelivery/deliveryLimitation/client"
import "alpha/adDelivery/deliveryLimitation/geo"
import "alpha/adDelivery/deliveryLimitation/site"
import "alpha/adDelivery/deliveryLimitation/timePack"
import config "alpha/configuration"




type DeliverLimitStruct struct {
	
	R *http.Request
	Ip_address string
	Latitude string
	Longitude string
	Country_code string
	Country_name string
	Subdivision_one string
	Subdivision_two string
	Continent string
	City string
	Postal_code string
	UsMetro string
	Organisation string
	ConnectionType string
	Useragent string
	Os string
	Osv string
	OsShort string
	Language string
	Domain string
	Browser string
	BrowserVersion string
	BrowserShort string
	
	Hostname string
	PageURL string
	RefURL string
	DomainName string
	Source string
		
	}
	
	
	
	
	



func CheckAcls(Compiledlimitation string, zoneinfo structure.ZoneDetails, r *http.Request) bool {
	
	
	globalValues  := globalvariables.SetAllGrobalVariables(r)
	
	DeliveryVariables  := DeliverLimitStruct {
		R : globalValues.R,
		Ip_address : globalValues.Ip_address,
		Latitude : globalValues.Latitude,
		Longitude : globalValues.Longitude,
		Country_code : globalValues.Country_code,
		Country_name : globalValues.Country_name,
		Subdivision_one : globalValues.Subdivision_one,
		Continent : globalValues.Continent,
		City : globalValues.City,
		Useragent : globalValues.Useragent,
		Os : globalValues.Os,
		Osv : globalValues.Osv,
		OsShort : globalValues.OsShort,
		Language : globalValues.Language,
		Domain : globalValues.Domain,
		Browser : globalValues.Browser,
		BrowserVersion : globalValues.BrowserVersion,
		BrowserShort : globalValues.BrowserShort,
		Hostname : globalValues.Hostname,
		PageURL : globalValues.PageURL,
		RefURL : globalValues.RefURL,
		DomainName : globalValues.DomainName,
		Source : globalValues.Source } 
	
 

	
    CmLimit := Compiledlimitation
    colsole := true
    
    if CmLimit != "" && CmLimit != "true" {
		
        s := strings.Split(CmLimit, " and ")
        
        for _,
        element := range s {
			
            or_constant := false
            
            if element != "" {
				
                stringer := strings.Split(element, " or ")
                
                for _,
                e := range stringer {
                    if e != "" {
                        if (CheckAclsIndividual(e,DeliveryVariables) == true) {
                            or_constant = true;
                            break;
                        }
                    }
                }
          
            }
            
             if or_constant == false {
                    colsole = false;
                    break; 
                }
        }
        
    }
    
        return colsole
        
}




func CheckAclsIndividual(str string, DeliveryVariables DeliverLimitStruct ) bool {
	
    var argunments[] string
    part := strings.Split(str, "(")
    submatchall := regexp.MustCompile(`'([^']*)'`).FindAllString(part[1], -1)
    
    for _, element := range submatchall {
        element = strings.Trim(element, "'")
        argunments = append(argunments, element)
    }
    
    return Invokefunction(part[0], argunments,DeliveryVariables)
}


func Invokefunction(name string, argunments[] string , DeliveryVariables DeliverLimitStruct ) bool {
	
    inputs := make([] reflect.Value, len(argunments))
    for i,
    _ := range argunments {
        inputs[i] = reflect.ValueOf(argunments[i])
    }
    
    
    re := reflect.ValueOf(DeliveryVariables).MethodByName(name).Call(inputs)
    return re[0].Interface().(bool)
}


 



/* Start Client Limitation */


func(y DeliverLimitStruct) MAX_checkClient_Browser(limitation string, op string) bool {
	
	browser_name  := client.SetBrowserName(y.Browser) 
	return client.Browser(limitation,op,browser_name)
}




func(y DeliverLimitStruct) MAX_checkClient_BrowserVersion(limitation string, op string) bool {
	
	browser_name  := client.SetBrowserFullName(y.Browser)
	browser_version  := y.BrowserVersion 
	return client.BrowserVersion(limitation,op,browser_name,browser_version)
}


func(y DeliverLimitStruct) MAX_checkClient_Domain(limitation string, op string) bool {
   
	domain_name  := y.Domain

    return client.Domain(limitation,op,domain_name)
    
}

func(y DeliverLimitStruct) MAX_checkClient_Ip(limitation string, op string) bool {
	
	   	ip := y.Ip_address
	    return client.Ip(limitation,op,ip)

} 

func(y DeliverLimitStruct) MAX_checkClient_Language(limitation string, op string) bool {
    
    language := y.Language
    return client.Language(limitation,op,language)
}


func(y DeliverLimitStruct) MAX_checkClient_Os(limitation string, op string) bool {
     os := client.SetOsName(y.Os)
  
    return client.Os(limitation,op,os)
}


func(y DeliverLimitStruct) MAX_checkClient_OsVersion(limitation string, op string) bool {
	
	os_name  := client.SetOsFullName(y.Os)
	os_version  := y.Osv
	return client.OsVersion(limitation,op,os_name,os_version)
}


func(y DeliverLimitStruct) MAX_checkClient_Useragent(limitation string, op string) bool {
	
	ua := y.Useragent
	return client.Ua(limitation,op,ua)
}

/* End Client Limitation */


/* Start Geo Limitation */


func(y DeliverLimitStruct) MAX_checkGeo_City(limitation string, op string) bool {
	
	country_code := y.Country_code
	city_name :=  y.City
	return geo.City(limitation,op,country_code,city_name)
}

func(y DeliverLimitStruct) MAX_checkGeo_ConnectionType(limitation string, op string) bool {
	
	connection_type := y.ConnectionType
	return geo.ConnectionType(limitation,op,connection_type)
}

func(y DeliverLimitStruct) MAX_checkGeo_Continent(limitation string, op string) bool {
	
	continent := y.Continent


	return geo.Continent(limitation,op,continent)
}

func(y DeliverLimitStruct) MAX_checkGeo_Country(limitation string, op string) bool {
	
	country := y.Country_code


	return geo.Country(limitation,op,country)
}

func(y DeliverLimitStruct) MAX_checkGeo_Latlong(limitation string, op string) bool {
	
	lat := y.Latitude
	long := y.Longitude

	return geo.Latlong(limitation,op,lat,long)
}

func(y DeliverLimitStruct) MAX_checkGeo_Organisation(limitation string, op string) bool {
	
	organisation := y.Organisation
	
	return geo.Organisation(limitation,op,organisation)
}

func(y DeliverLimitStruct) MAX_checkGeo_Postalcode(limitation string, op string) bool {
	
	country := y.Country_code
	postalcode :=y.Postal_code
	

	return geo.Postalcode(limitation,op,country,postalcode)
}


func(y DeliverLimitStruct) MAX_checkGeo_Subdivision1(limitation string, op string) bool {
	
	subdivision1 := y.Country_code+"|"+y.Subdivision_one
	
 
	return geo.Subdivision1(limitation,op,subdivision1)
}

func(y DeliverLimitStruct) MAX_checkGeo_Subdivision2(limitation string, op string) bool {
	
	subdivision2 :=  y.Country_code+"|"+y.Subdivision_two 
	

	return geo.Subdivision2(limitation,op,subdivision2)
}


func(y DeliverLimitStruct) MAX_checkGeo_UsMetro(limitation string, op string) bool {
	
	usMetro := y.UsMetro
	

	return geo.UsMetro(limitation,op,usMetro)
}

/* End Geo Limitation */


/* Start Site Limitation */


func(y DeliverLimitStruct) MAX_checkSite_Hostnamelist(limitation string, op string) bool {
	
	hostname := y.Hostname
	return site.Hostnamelist(limitation,op,hostname)
}

func(y DeliverLimitStruct) MAX_checkSite_Pageurl(limitation string, op string) bool {
	
	page_url := y.PageURL
	return site.Pageurl(limitation,op,page_url)
}
func(y DeliverLimitStruct) MAX_checkSite_Referingpage(limitation string, op string) bool {
	
	referingpage := y.RefURL
	return site.Referingpage(limitation,op,referingpage)
} 


func(y DeliverLimitStruct) MAX_checkSite_Registerabledomainlist(limitation string, op string) bool {
	
	domain := y.DomainName
	return site.Registerabledomainlist(limitation,op,domain)
}

func(y DeliverLimitStruct) MAX_checkSite_Source(limitation string, op string) bool {
	
	source := y.Source
	return site.Source(limitation,op,source)
}

func(y DeliverLimitStruct) MAX_checkSite_Variable(limitation string, op string) bool {
	
	l := strings.Split(limitation, "|") ; value := y.R.URL.Query()[l[0]] ; variable :=""
	if len(value) != 0 {	variable = value[0]; } 
	
	return site.Variable(limitation,op,variable)
		
} 


/* Start Date Limitation */

func(y DeliverLimitStruct) MAX_checkTime_Date(limitation string, op string) bool {
	
	return timePack.Date(limitation,op)
}

func(y DeliverLimitStruct) MAX_checkTime_Day(limitation string, op string) bool {
	
	return timePack.Day(limitation,op)
}

func(y DeliverLimitStruct) MAX_checkTime_Hour(limitation string, op string) bool {
	
	return timePack.Hour(limitation,op)
}

/* End Date Limitation */



/* Start Custom Limitation */


func(y DeliverLimitStruct) MAX_checkClient_Adstxt(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_AppCategory(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_AppPubDomain(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_AppStoreUrl(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_AppVersion(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Appid(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_BlockedAdvertiser(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_BlockedApps(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_BlockedCategory(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Buyeruid(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_ConnectionType(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Dataname(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_DeviceType(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Displaymanager(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_DoohID(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_DoohPubCat(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Exchange(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Gender(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Ifa(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Ipv6(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Macaddress(limitation string, op string) bool {
return true
}	

func(y DeliverLimitStruct) MAX_checkClient_Manufacture(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Martialstatus(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_MobileLanguage(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Mobilebrandwithmodel(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Mobileos(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Mobileoswithversion(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Mobileuseragent(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Network(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Profile(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_PubDomain(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Pxratio(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Regcoppa(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SSP(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Segmentname(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Segmentvalue(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SiteAmp(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SiteCategory(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SiteMobile(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SitePageCategory(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SiteSectionCategory(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_SourceTid(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Timezone(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Udid(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Vendor(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Vlan(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_Wlan(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkClient_useryob(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkGeo_Areacode(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkGeo_Dma(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkGeo_Netspeed(limitation string, op string) bool {
return true
}

func(y DeliverLimitStruct) MAX_checkGeo_Region(limitation string, op string) bool {
return true
}



func(y DeliverLimitStruct) MAX_checkClient_Segment(limitation string, op string) bool {
	
	dmp_id := CookieValue(y.R,config.GetConfig("cookiename","dmp"))
	return client.Segment(limitation,op,dmp_id)
}


func CookieValue(r *http.Request , str string) string {
	
	cookie, err := r.Cookie(str)
        if err != nil {
                  return ""
 
          
        }
          return cookie.Value

	
}



/* End Custom Limitation */




