XTLS/Xray-core · error

empty code

Error message

empty code

What it means

After splitting on ':' and stripping '!' reverse prefixes from the code segment, the code is empty. The rule names a file but no country code, e.g. "ext:geoip.dat:" or "geoip:!".

Source

Thrown at common/geodata/rule_parser.go:72

		reverse = !reverse
	}
	return s, reverse
}

func parseGeoIPRule(rule string, reverse bool) (*IPRule_Geoip, error) {
	file, code, ok := strings.Cut(rule, ":")
	if !ok {
		return nil, errors.New("syntax error")
	}

	if file == "" {
		return nil, errors.New("empty file")
	}

	code, codeReverse := cutReversePrefix(code)
	reverse = reverse != codeReverse
	if code == "" {
		return nil, errors.New("empty code")
	}
	code = strings.ToUpper(code)

	if err := checkFile(file, code); err != nil {
		return nil, err
	}

	return &IPRule_Geoip{
		Geoip: &GeoIPRule{
			File:         file,
			Code:         code,
			ReverseMatch: reverse,
		},
	}, nil
}

func parseCustomIPRule(rule string, reverse bool) (*IPRule_Custom, error) {
	cidr, err := parseCIDR(rule)

View on GitHub (pinned to 7d214f8b09)

Solutions

  1. Append a valid country code: "geoip:cn", "ext:geoip.dat:us".
  2. For reverse matching keep the code: "geoip:!cn" (the '!' goes before the code, not instead of it).

Example fix

// before
"ip": ["ext:geoip.dat:"]

// after
"ip": ["ext:geoip.dat:cn"]
Defensive patterns

Strategy: validation

Validate before calling

func validGeoIP(r string) bool {
    parts := strings.Split(strings.Trim(r, "!"), ":")
    return len(parts) == 2 && parts[0] != "" && strings.Trim(parts[1], "!") != ""
}

Prevention

When it happens

Trigger: Rule strings "geoip:", "ext:custom.dat:", "geoip:!"; also "geoip:!:cn" is fine but "geoip:!" alone is not.

Common situations: Config typos where the country code was omitted or deleted after the last colon.

Related errors


AI-assisted analysis of XTLS/Xray-core@7d214f8b09 (2026-08-15). Data as JSON: /api/errors/431e09e705198170. Report an issue: GitHub.