annotation to ignore given list of WAF rulesets (#2314)
This commit is contained in:
parent
a6fe800a47
commit
16faf309ca
6 changed files with 59 additions and 9 deletions
|
@ -68,6 +68,7 @@ The following annotations are supported:
|
||||||
|[nginx.ingress.kubernetes.io/enable-access-log](#enable-access-log)|"true" or "false"|
|
|[nginx.ingress.kubernetes.io/enable-access-log](#enable-access-log)|"true" or "false"|
|
||||||
|[nginx.ingress.kubernetes.io/lua-resty-waf](#lua-resty-waf)|"true" or "false"|
|
|[nginx.ingress.kubernetes.io/lua-resty-waf](#lua-resty-waf)|"true" or "false"|
|
||||||
|[nginx.ingress.kubernetes.io/lua-resty-waf-debug](#lua-resty-waf)|"true" or "false"|
|
|[nginx.ingress.kubernetes.io/lua-resty-waf-debug](#lua-resty-waf)|"true" or "false"|
|
||||||
|
|[nginx.ingress.kubernetes.io/lua-resty-waf-ignore-rulesets](#lua-resty-waf)|string|
|
||||||
|
|
||||||
**Note:** all the values must be a string. In case of booleans or number it must be quoted.
|
**Note:** all the values must be a string. In case of booleans or number it must be quoted.
|
||||||
|
|
||||||
|
@ -476,3 +477,12 @@ nginx.ingress.kubernetes.io/lua-resty-waf: "true"
|
||||||
```
|
```
|
||||||
|
|
||||||
In order to run it in debugging mode you can set `nginx.ingress.kubernetes.io/lua-resty-waf-debug` to `"true"` in addition to the above configuration.
|
In order to run it in debugging mode you can set `nginx.ingress.kubernetes.io/lua-resty-waf-debug` to `"true"` in addition to the above configuration.
|
||||||
|
|
||||||
|
`lua-resty-waf` comes with predefined set of rules(https://github.com/p0pr0ck5/lua-resty-waf/tree/84b4f40362500dd0cb98b9e71b5875cb1a40f1ad/rules) that covers ModSecurity CRS.
|
||||||
|
You can use `nginx.ingress.kubernetes.io/lua-resty-waf-ignore-rulesets` to ignore subset of those rulesets. For an example:
|
||||||
|
|
||||||
|
```yaml
|
||||||
|
nginx.ingress.kubernetes.io/lua-resty-waf-ignore-rulesets: "41000_sqli, 42000_xss"
|
||||||
|
```
|
||||||
|
|
||||||
|
will ignore the two mentioned rulesets.
|
||||||
|
|
File diff suppressed because one or more lines are too long
|
@ -17,6 +17,9 @@ limitations under the License.
|
||||||
package luarestywaf
|
package luarestywaf
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"reflect"
|
||||||
|
"strings"
|
||||||
|
|
||||||
extensions "k8s.io/api/extensions/v1beta1"
|
extensions "k8s.io/api/extensions/v1beta1"
|
||||||
|
|
||||||
"k8s.io/ingress-nginx/internal/ingress/annotations/parser"
|
"k8s.io/ingress-nginx/internal/ingress/annotations/parser"
|
||||||
|
@ -27,6 +30,7 @@ import (
|
||||||
type Config struct {
|
type Config struct {
|
||||||
Enabled bool `json:"enabled"`
|
Enabled bool `json:"enabled"`
|
||||||
Debug bool `json:"debug"`
|
Debug bool `json:"debug"`
|
||||||
|
IgnoredRuleSets []string `json: "ignored-rulesets"`
|
||||||
}
|
}
|
||||||
|
|
||||||
// Equal tests for equality between two Config types
|
// Equal tests for equality between two Config types
|
||||||
|
@ -43,6 +47,9 @@ func (e1 *Config) Equal(e2 *Config) bool {
|
||||||
if e1.Debug != e2.Debug {
|
if e1.Debug != e2.Debug {
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
if !reflect.DeepEqual(e1.IgnoredRuleSets, e2.IgnoredRuleSets) {
|
||||||
|
return false
|
||||||
|
}
|
||||||
|
|
||||||
return true
|
return true
|
||||||
}
|
}
|
||||||
|
@ -67,8 +74,15 @@ func (a luarestywaf) Parse(ing *extensions.Ingress) (interface{}, error) {
|
||||||
|
|
||||||
debug, _ := parser.GetBoolAnnotation("lua-resty-waf-debug", ing)
|
debug, _ := parser.GetBoolAnnotation("lua-resty-waf-debug", ing)
|
||||||
|
|
||||||
|
ignoredRuleSetsStr, _ := parser.GetStringAnnotation("lua-resty-waf-ignore-rulesets", ing)
|
||||||
|
ignoredRuleSets := strings.FieldsFunc(ignoredRuleSetsStr, func(c rune) bool {
|
||||||
|
strC := string(c)
|
||||||
|
return strC == "," || strC == " "
|
||||||
|
})
|
||||||
|
|
||||||
return &Config{
|
return &Config{
|
||||||
Enabled: enabled,
|
Enabled: enabled,
|
||||||
Debug: debug,
|
Debug: debug,
|
||||||
|
IgnoredRuleSets: ignoredRuleSets,
|
||||||
}, nil
|
}, nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -29,6 +29,7 @@ import (
|
||||||
func TestParse(t *testing.T) {
|
func TestParse(t *testing.T) {
|
||||||
luaRestyWAFAnnotation := parser.GetAnnotationWithPrefix("lua-resty-waf")
|
luaRestyWAFAnnotation := parser.GetAnnotationWithPrefix("lua-resty-waf")
|
||||||
luaRestyWAFDebugAnnotation := parser.GetAnnotationWithPrefix("lua-resty-waf-debug")
|
luaRestyWAFDebugAnnotation := parser.GetAnnotationWithPrefix("lua-resty-waf-debug")
|
||||||
|
luaRestyWAFIgnoredRuleSetsAnnotation := parser.GetAnnotationWithPrefix("lua-resty-waf-ignore-rulesets")
|
||||||
|
|
||||||
ap := NewParser(&resolver.Mock{})
|
ap := NewParser(&resolver.Mock{})
|
||||||
if ap == nil {
|
if ap == nil {
|
||||||
|
@ -42,12 +43,18 @@ func TestParse(t *testing.T) {
|
||||||
{nil, &Config{}},
|
{nil, &Config{}},
|
||||||
{map[string]string{}, &Config{}},
|
{map[string]string{}, &Config{}},
|
||||||
|
|
||||||
{map[string]string{luaRestyWAFAnnotation: "true"}, &Config{Enabled: true, Debug: false}},
|
{map[string]string{luaRestyWAFAnnotation: "true"}, &Config{Enabled: true, Debug: false, IgnoredRuleSets: []string{}}},
|
||||||
{map[string]string{luaRestyWAFDebugAnnotation: "true"}, &Config{Enabled: false, Debug: false}},
|
{map[string]string{luaRestyWAFDebugAnnotation: "true"}, &Config{Enabled: false, Debug: false}},
|
||||||
|
|
||||||
{map[string]string{luaRestyWAFAnnotation: "true", luaRestyWAFDebugAnnotation: "true"}, &Config{Enabled: true, Debug: true}},
|
{map[string]string{luaRestyWAFAnnotation: "true", luaRestyWAFDebugAnnotation: "true"}, &Config{Enabled: true, Debug: true, IgnoredRuleSets: []string{}}},
|
||||||
{map[string]string{luaRestyWAFAnnotation: "true", luaRestyWAFDebugAnnotation: "false"}, &Config{Enabled: true, Debug: false}},
|
{map[string]string{luaRestyWAFAnnotation: "true", luaRestyWAFDebugAnnotation: "false"}, &Config{Enabled: true, Debug: false, IgnoredRuleSets: []string{}}},
|
||||||
{map[string]string{luaRestyWAFAnnotation: "false", luaRestyWAFDebugAnnotation: "true"}, &Config{Enabled: false, Debug: true}},
|
{map[string]string{luaRestyWAFAnnotation: "false", luaRestyWAFDebugAnnotation: "true"}, &Config{Enabled: false, Debug: true, IgnoredRuleSets: []string{}}},
|
||||||
|
|
||||||
|
{map[string]string{
|
||||||
|
luaRestyWAFAnnotation: "true",
|
||||||
|
luaRestyWAFDebugAnnotation: "true",
|
||||||
|
luaRestyWAFIgnoredRuleSetsAnnotation: "ruleset1, ruleset2 ruleset3, another.ruleset"},
|
||||||
|
&Config{Enabled: true, Debug: true, IgnoredRuleSets: []string{"ruleset1", "ruleset2", "ruleset3", "another.ruleset"}}},
|
||||||
}
|
}
|
||||||
|
|
||||||
ing := &extensions.Ingress{
|
ing := &extensions.Ingress{
|
||||||
|
|
|
@ -835,6 +835,10 @@ stream {
|
||||||
waf:set_option("res_tid_header", true)
|
waf:set_option("res_tid_header", true)
|
||||||
{{ end }}
|
{{ end }}
|
||||||
|
|
||||||
|
{{ range $ruleset := $location.LuaRestyWAF.IgnoredRuleSets }}
|
||||||
|
waf:set_option("ignore_ruleset", "{{ $ruleset }}")
|
||||||
|
{{ end }}
|
||||||
|
|
||||||
waf:exec()
|
waf:exec()
|
||||||
}
|
}
|
||||||
header_filter_by_lua_block {
|
header_filter_by_lua_block {
|
||||||
|
|
|
@ -53,6 +53,21 @@ var _ = framework.IngressNginxDescribe("Annotations - lua-resty-waf", func() {
|
||||||
Expect(len(errs)).Should(Equal(0))
|
Expect(len(errs)).Should(Equal(0))
|
||||||
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
|
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
|
||||||
})
|
})
|
||||||
|
It("should not apply ignored rulesets", func() {
|
||||||
|
host := "foo"
|
||||||
|
createIngress(f, host, map[string]string{
|
||||||
|
"nginx.ingress.kubernetes.io/lua-resty-waf": "true",
|
||||||
|
"nginx.ingress.kubernetes.io/lua-resty-waf-ignore-rulesets": "41000_sqli, 42000_xss"})
|
||||||
|
|
||||||
|
url := fmt.Sprintf("%s?msg=<A href=\"http://mysite.com/\">XSS</A>", f.NginxHTTPURL)
|
||||||
|
resp, _, errs := gorequest.New().
|
||||||
|
Get(url).
|
||||||
|
Set("Host", host).
|
||||||
|
End()
|
||||||
|
|
||||||
|
Expect(len(errs)).Should(Equal(0))
|
||||||
|
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
|
||||||
|
})
|
||||||
})
|
})
|
||||||
|
|
||||||
Context("when lua-resty-waf is not enabled", func() {
|
Context("when lua-resty-waf is not enabled", func() {
|
||||||
|
|
Loading…
Reference in a new issue