mirror of
https://github.com/zalando/postgres-operator.git
synced 2026-10-09 23:00:18 +02:00
PostgresTeam CRD for advanced team management (#1165)
* PostgresTeamCRD for advanced team management * rework internal structure to be closer to CRD * superusers instead of admin * add more util functions and unit tests * fix initHumanUsers * check for superusers when creating normal teams * polishing and fixes * adding the essential missing pieces * add documentation and update rbac * reflect some feedback * reflect more feedback * fixing debug logs and raise QueueResyncPeriodTPR * add two more flags to disable CRD and its superuser support * fix chart * update go modules * move to client 1.19.3 and update codegen
This commit is contained in:
@@ -169,6 +169,8 @@ type Config struct {
|
||||
EnableTeamSuperuser bool `name:"enable_team_superuser" default:"false"`
|
||||
TeamAdminRole string `name:"team_admin_role" default:"admin"`
|
||||
EnableAdminRoleForUsers bool `name:"enable_admin_role_for_users" default:"true"`
|
||||
EnablePostgresTeamCRD *bool `name:"enable_postgres_team_crd" default:"true"`
|
||||
EnablePostgresTeamCRDSuperusers bool `name:"enable_postgres_team_crd_superusers" default:"false"`
|
||||
EnableMasterLoadBalancer bool `name:"enable_master_load_balancer" default:"true"`
|
||||
EnableReplicaLoadBalancer bool `name:"enable_replica_load_balancer" default:"false"`
|
||||
CustomServiceAnnotations map[string]string `name:"custom_service_annotations"`
|
||||
|
||||
@@ -10,7 +10,9 @@ import (
|
||||
"fmt"
|
||||
"math/big"
|
||||
"math/rand"
|
||||
"reflect"
|
||||
"regexp"
|
||||
"sort"
|
||||
"strings"
|
||||
"time"
|
||||
|
||||
@@ -134,6 +136,21 @@ func PrettyDiff(a, b interface{}) string {
|
||||
return strings.Join(Diff(a, b), "\n")
|
||||
}
|
||||
|
||||
// Compare two string slices while ignoring the order of elements
|
||||
func IsEqualIgnoreOrder(a, b []string) bool {
|
||||
if len(a) != len(b) {
|
||||
return false
|
||||
}
|
||||
a_copy := make([]string, len(a))
|
||||
b_copy := make([]string, len(b))
|
||||
copy(a_copy, a)
|
||||
copy(b_copy, b)
|
||||
sort.Strings(a_copy)
|
||||
sort.Strings(b_copy)
|
||||
|
||||
return reflect.DeepEqual(a_copy, b_copy)
|
||||
}
|
||||
|
||||
// SubstractStringSlices finds elements in a that are not in b and return them as a result slice.
|
||||
func SubstractStringSlices(a []string, b []string) (result []string, equal bool) {
|
||||
// Slices are assumed to contain unique elements only
|
||||
@@ -176,6 +193,20 @@ func FindNamedStringSubmatch(r *regexp.Regexp, s string) map[string]string {
|
||||
return res
|
||||
}
|
||||
|
||||
// SliceContains
|
||||
func SliceContains(slice interface{}, item interface{}) bool {
|
||||
s := reflect.ValueOf(slice)
|
||||
if s.Kind() != reflect.Slice {
|
||||
panic("Invalid data-type")
|
||||
}
|
||||
for i := 0; i < s.Len(); i++ {
|
||||
if s.Index(i).Interface() == item {
|
||||
return true
|
||||
}
|
||||
}
|
||||
return false
|
||||
}
|
||||
|
||||
// MapContains returns true if and only if haystack contains all the keys from the needle with matching corresponding values
|
||||
func MapContains(haystack, needle map[string]string) bool {
|
||||
if len(haystack) < len(needle) {
|
||||
|
||||
@@ -43,6 +43,17 @@ var prettyDiffTest = []struct {
|
||||
{[]int{1, 2, 3, 4}, []int{1, 2, 3, 4}, ""},
|
||||
}
|
||||
|
||||
var isEqualIgnoreOrderTest = []struct {
|
||||
inA []string
|
||||
inB []string
|
||||
outEqual bool
|
||||
}{
|
||||
{[]string{"a", "b", "c"}, []string{"a", "b", "c"}, true},
|
||||
{[]string{"a", "b", "c"}, []string{"a", "c", "b"}, true},
|
||||
{[]string{"a", "b"}, []string{"a", "c", "b"}, false},
|
||||
{[]string{"a", "b", "c"}, []string{"a", "d", "c"}, false},
|
||||
}
|
||||
|
||||
var substractTest = []struct {
|
||||
inA []string
|
||||
inB []string
|
||||
@@ -53,6 +64,16 @@ var substractTest = []struct {
|
||||
{[]string{"a", "b", "c", "d"}, []string{"a", "bb", "c", "d"}, []string{"b"}, false},
|
||||
}
|
||||
|
||||
var sliceContaintsTest = []struct {
|
||||
slice []string
|
||||
item string
|
||||
out bool
|
||||
}{
|
||||
{[]string{"a", "b", "c"}, "a", true},
|
||||
{[]string{"a", "b", "c"}, "d", false},
|
||||
{[]string{}, "d", false},
|
||||
}
|
||||
|
||||
var mapContaintsTest = []struct {
|
||||
inA map[string]string
|
||||
inB map[string]string
|
||||
@@ -136,6 +157,15 @@ func TestPrettyDiff(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestIsEqualIgnoreOrder(t *testing.T) {
|
||||
for _, tt := range isEqualIgnoreOrderTest {
|
||||
actualEqual := IsEqualIgnoreOrder(tt.inA, tt.inB)
|
||||
if actualEqual != tt.outEqual {
|
||||
t.Errorf("IsEqualIgnoreOrder expected: %t, got: %t", tt.outEqual, actualEqual)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestSubstractSlices(t *testing.T) {
|
||||
for _, tt := range substractTest {
|
||||
actualRes, actualEqual := SubstractStringSlices(tt.inA, tt.inB)
|
||||
@@ -160,6 +190,15 @@ func TestFindNamedStringSubmatch(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestSliceContains(t *testing.T) {
|
||||
for _, tt := range sliceContaintsTest {
|
||||
res := SliceContains(tt.slice, tt.item)
|
||||
if res != tt.out {
|
||||
t.Errorf("SliceContains expected: %#v, got: %#v", tt.out, res)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
func TestMapContains(t *testing.T) {
|
||||
for _, tt := range mapContaintsTest {
|
||||
res := MapContains(tt.inA, tt.inB)
|
||||
|
||||
Reference in New Issue
Block a user