{"record":{"id":"e909864ec55784ce","repo":"projectdiscovery/nuclei","slug":"both-follow-host-redirects-and-follow-redirects-sp","errorCode":null,"errorMessage":"both follow host redirects and follow redirects specified","messagePattern":"both follow host redirects and follow redirects specified","errorType":"validation","errorClass":null,"httpStatus":null,"severity":"error","filePath":"internal/runner/options.go","lineNumber":164,"sourceCode":"\t\tif _, ok := err.(*validator.InvalidValidationError); ok {\n\t\t\treturn err\n\t\t}\n\t\terrs := []string{}\n\t\tfor _, err := range err.(validator.ValidationErrors) {\n\t\t\terrs = append(errs, err.Namespace()+\": \"+err.Tag())\n\t\t}\n\t\treturn errors.Wrap(errors.New(strings.Join(errs, \", \")), \"validation failed for these fields\")\n\t}\n\tif options.Verbose && options.Silent {\n\t\treturn errors.New(\"both verbose and silent mode specified\")\n\t}\n\n\tif (options.HeadlessOptionalArguments != nil || options.ShowBrowser || options.UseInstalledChrome) && !options.Headless {\n\t\treturn errors.New(\"headless mode (-headless) is required if -ho, -sb, -sc or -lha are set\")\n\t}\n\n\tif options.FollowHostRedirects && options.FollowRedirects {\n\t\treturn errors.New(\"both follow host redirects and follow redirects specified\")\n\t}\n\tif options.ShouldFollowHTTPRedirects() && options.DisableRedirects {\n\t\treturn errors.New(\"both follow redirects and disable redirects specified\")\n\t}\n\t// loading the proxy server list from file or cli and test the connectivity\n\tif err := loadProxyServers(options); err != nil {\n\t\treturn err\n\t}\n\tif options.Validate {\n\t\tvalidateTemplatePaths(options.Logger, config.DefaultConfig.TemplatesDirectory, options.Templates, options.Workflows)\n\t}\n\tif options.DAST {\n\t\tif err := validateDASTOptions(options); err != nil {\n\t\t\treturn err\n\t\t}\n\t}\n\n\t// Verify if any of the client certificate options were set since it requires all three to work properly","sourceCodeStart":146,"sourceCodeEnd":182,"githubUrl":"https://github.com/projectdiscovery/nuclei/blob/265b3a3dec374741614e342f813c10f8b38d2bb7/internal/runner/options.go#L146-L182","documentation":"Variant of the source-IP check when only -source-ip is provided: nuclei verifies the address against every interface ('any'); if none owns it, startup aborts. Typical when the address is stale, belongs to another machine, or is a public/NAT address rather than one assigned locally.","triggerScenarios":"nuclei -source-ip 203.0.113.7 on a host whose interfaces only hold 192.168.x.x; an address from a previous DHCP lease; a typo in the flag.","commonSituations":"Laptops roaming between networks; scripts hard-coding an old IP; users passing the target's public IP instead of a local source address.","solutions":["List local addresses with ip addr (or ifconfig) and pass one of them","On multi-homed hosts pick the address of the egress interface","Remove -source-ip to let the OS choose the source address"],"exampleFix":"# before\nnuclei -source-ip 203.0.113.7 -t tpl.yaml\n# after\nnuclei -source-ip 192.168.1.20 -t tpl.yaml","handlingStrategy":"validation","validationCode":"import \"net\"\n\nfunc ipAnywhere(ip string) bool {\n    addrs, err := net.InterfaceAddrs()\n    if err != nil {\n        return false\n    }\n    for _, a := range addrs {\n        if ipnet, ok := a.(*net.IPNet); ok && ipnet.IP.String() == ip {\n            return true\n        }\n    }\n    return false\n}","typeGuard":null,"tryCatchPattern":null,"preventionTips":["Refresh source IPs after network changes","Never use public or NAT addresses as -source-ip","Let the OS choose by omitting -source-ip"],"tags":["network","cli","configuration","startup"],"backgroundTag":null,"analyzedSha":"265b3a3dec374741614e342f813c10f8b38d2bb7","analyzedAt":"2026-08-15T20:05:51.855Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}