1
0
mirror of https://github.com/rancher/steve.git synced 2025-09-13 13:59:40 +00:00

#47483 - Adding NonResourceURLs support to AccessStore (#299)

* adding NonResourceURLs support to access_store

* added tests to AccessSet NonResourceURLs handling

* change on test script suggested by @tomleb + go mod tidy

* added nonresource to ext api authorization

* added NonResourceURLs implementation in Authorizes + test

* removed non-resource-url tests from the main test

* added new tests for non-resource-urls

* removed unused test data

* changed nonResourceKey to point to struct{}

* addressed comments from @tomleb

* addressed more comments

* fixing typo

* check for empty accessSet
This commit is contained in:
Felipe Gehrke
2024-11-04 23:47:48 -03:00
committed by GitHub
parent 2175e090fe
commit 6ee8201c8d
10 changed files with 588 additions and 39 deletions

View File

@@ -3,15 +3,19 @@ package accesscontrol
import (
"sort"
"github.com/rancher/apiserver/pkg/types"
"github.com/rancher/steve/pkg/attributes"
v1 "k8s.io/api/rbac/v1"
"k8s.io/apimachinery/pkg/runtime/schema"
"k8s.io/apimachinery/pkg/util/sets"
rbacv1 "k8s.io/kubernetes/pkg/apis/rbac/v1"
"github.com/rancher/apiserver/pkg/types"
"github.com/rancher/steve/pkg/attributes"
)
type AccessSet struct {
ID string
set map[key]resourceAccessSet
ID string
set map[key]resourceAccessSet
nonResourceSet map[nonResourceKey]struct{}
}
type resourceAccessSet map[Access]bool
@@ -21,6 +25,11 @@ type key struct {
gr schema.GroupResource
}
type nonResourceKey struct {
verb string
url string
}
func (a *AccessSet) Namespaces() (result []string) {
set := map[string]bool{}
for k, as := range a.set {
@@ -56,6 +65,17 @@ func (a *AccessSet) Merge(right *AccessSet) {
m[k] = v
}
}
if a.nonResourceSet == nil {
a.nonResourceSet = map[nonResourceKey]struct{}{}
}
for k, v := range right.nonResourceSet {
_, ok := a.nonResourceSet[k]
if !ok {
a.nonResourceSet[k] = v
}
}
}
func (a AccessSet) Grants(verb string, gr schema.GroupResource, namespace, name string) bool {
@@ -80,6 +100,26 @@ func (a AccessSet) Grants(verb string, gr schema.GroupResource, namespace, name
return false
}
func (a *AccessSet) GrantsNonResource(verb, url string) bool {
if a.nonResourceSet == nil {
return false
}
if _, ok := a.nonResourceSet[nonResourceKey{url: url, verb: verb}]; ok {
rule := &v1.PolicyRule{NonResourceURLs: []string{url}, Verbs: []string{verb}}
return rbacv1.NonResourceURLMatches(rule, url) && rbacv1.VerbMatches(rule, verb)
}
for key := range a.nonResourceSet {
rule := &v1.PolicyRule{NonResourceURLs: []string{key.url}, Verbs: []string{key.verb}}
if rbacv1.NonResourceURLMatches(rule, url) && rbacv1.VerbMatches(rule, verb) {
return true
}
}
return false
}
func (a AccessSet) AccessListFor(verb string, gr schema.GroupResource) (result AccessList) {
dedup := map[Access]bool{}
for _, v := range []string{All, verb} {
@@ -120,6 +160,25 @@ func (a *AccessSet) Add(verb string, gr schema.GroupResource, access Access) {
}
}
func (a *AccessSet) AddNonResourceURLs(verbs, urls []string) {
if len(verbs) == 0 || len(urls) == 0 {
return
}
if a.nonResourceSet == nil {
a.nonResourceSet = map[nonResourceKey]struct{}{}
}
for _, verb := range verbs {
for _, url := range urls {
a.nonResourceSet[nonResourceKey{
verb: verb,
url: url,
}] = struct{}{}
}
}
}
type AccessListByVerb map[string]AccessList
func (a AccessListByVerb) Grants(verb, namespace, name string) bool {