github.com/inazumav/sing-box@v0.0.0-20230926072359-ab51429a14f1/common/geosite/rule.go (about)

     1  package geosite
     2  
     3  import "github.com/inazumav/sing-box/option"
     4  
     5  type ItemType = uint8
     6  
     7  const (
     8  	RuleTypeDomain ItemType = iota
     9  	RuleTypeDomainSuffix
    10  	RuleTypeDomainKeyword
    11  	RuleTypeDomainRegex
    12  )
    13  
    14  type Item struct {
    15  	Type  ItemType
    16  	Value string
    17  }
    18  
    19  func Compile(code []Item) option.DefaultRule {
    20  	var domainLength int
    21  	var domainSuffixLength int
    22  	var domainKeywordLength int
    23  	var domainRegexLength int
    24  	for _, item := range code {
    25  		switch item.Type {
    26  		case RuleTypeDomain:
    27  			domainLength++
    28  		case RuleTypeDomainSuffix:
    29  			domainSuffixLength++
    30  		case RuleTypeDomainKeyword:
    31  			domainKeywordLength++
    32  		case RuleTypeDomainRegex:
    33  			domainRegexLength++
    34  		}
    35  	}
    36  	var codeRule option.DefaultRule
    37  	if domainLength > 0 {
    38  		codeRule.Domain = make([]string, 0, domainLength)
    39  	}
    40  	if domainSuffixLength > 0 {
    41  		codeRule.DomainSuffix = make([]string, 0, domainSuffixLength)
    42  	}
    43  	if domainKeywordLength > 0 {
    44  		codeRule.DomainKeyword = make([]string, 0, domainKeywordLength)
    45  	}
    46  	if domainRegexLength > 0 {
    47  		codeRule.DomainRegex = make([]string, 0, domainRegexLength)
    48  	}
    49  	for _, item := range code {
    50  		switch item.Type {
    51  		case RuleTypeDomain:
    52  			codeRule.Domain = append(codeRule.Domain, item.Value)
    53  		case RuleTypeDomainSuffix:
    54  			codeRule.DomainSuffix = append(codeRule.DomainSuffix, item.Value)
    55  		case RuleTypeDomainKeyword:
    56  			codeRule.DomainKeyword = append(codeRule.DomainKeyword, item.Value)
    57  		case RuleTypeDomainRegex:
    58  			codeRule.DomainRegex = append(codeRule.DomainRegex, item.Value)
    59  		}
    60  	}
    61  	return codeRule
    62  }
    63  
    64  func Merge(rules []option.DefaultRule) option.DefaultRule {
    65  	var domainLength int
    66  	var domainSuffixLength int
    67  	var domainKeywordLength int
    68  	var domainRegexLength int
    69  	for _, subRule := range rules {
    70  		domainLength += len(subRule.Domain)
    71  		domainSuffixLength += len(subRule.DomainSuffix)
    72  		domainKeywordLength += len(subRule.DomainKeyword)
    73  		domainRegexLength += len(subRule.DomainRegex)
    74  	}
    75  	var rule option.DefaultRule
    76  	if domainLength > 0 {
    77  		rule.Domain = make([]string, 0, domainLength)
    78  	}
    79  	if domainSuffixLength > 0 {
    80  		rule.DomainSuffix = make([]string, 0, domainSuffixLength)
    81  	}
    82  	if domainKeywordLength > 0 {
    83  		rule.DomainKeyword = make([]string, 0, domainKeywordLength)
    84  	}
    85  	if domainRegexLength > 0 {
    86  		rule.DomainRegex = make([]string, 0, domainRegexLength)
    87  	}
    88  	for _, subRule := range rules {
    89  		if len(subRule.Domain) > 0 {
    90  			rule.Domain = append(rule.Domain, subRule.Domain...)
    91  		}
    92  		if len(subRule.DomainSuffix) > 0 {
    93  			rule.DomainSuffix = append(rule.DomainSuffix, subRule.DomainSuffix...)
    94  		}
    95  		if len(subRule.DomainKeyword) > 0 {
    96  			rule.DomainKeyword = append(rule.DomainKeyword, subRule.DomainKeyword...)
    97  		}
    98  		if len(subRule.DomainRegex) > 0 {
    99  			rule.DomainRegex = append(rule.DomainRegex, subRule.DomainRegex...)
   100  		}
   101  	}
   102  	return rule
   103  }