Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
K
k3s
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Jacklull
k3s
Commits
381d0a5d
Commit
381d0a5d
authored
Aug 17, 2018
by
Patrick Barker
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
adds dynamic audit api
parent
f6b54f79
Hide whitespace changes
Inline
Side-by-side
Showing
31 changed files
with
1682 additions
and
1 deletion
+1682
-1
.golint_failures
hack/.golint_failures
+3
-1
init.sh
hack/lib/init.sh
+1
-0
update-generated-protobuf-dockerized.sh
hack/update-generated-protobuf-dockerized.sh
+1
-0
testapi.go
pkg/api/testapi/testapi.go
+8
-0
defaulting_test.go
pkg/api/testing/defaulting_test.go
+2
-0
fuzzer.go
pkg/api/testing/fuzzer.go
+2
-0
validation.go
pkg/apis/admissionregistration/validation/validation.go
+1
-0
doc.go
pkg/apis/auditregistration/doc.go
+20
-0
fuzzer.go
pkg/apis/auditregistration/fuzzer/fuzzer.go
+38
-0
install.go
pkg/apis/auditregistration/install/install.go
+38
-0
register.go
pkg/apis/auditregistration/register.go
+53
-0
types.go
pkg/apis/auditregistration/types.go
+197
-0
defaults.go
pkg/apis/auditregistration/v1alpha1/defaults.go
+56
-0
defaults_test.go
pkg/apis/auditregistration/v1alpha1/defaults_test.go
+165
-0
doc.go
pkg/apis/auditregistration/v1alpha1/doc.go
+24
-0
register.go
pkg/apis/auditregistration/v1alpha1/register.go
+46
-0
validation.go
pkg/apis/auditregistration/validation/validation.go
+200
-0
validation_test.go
pkg/apis/auditregistration/validation/validation_test.go
+324
-0
import_known_versions.go
pkg/master/import_known_versions.go
+1
-0
master.go
pkg/master/master.go
+4
-0
doc.go
pkg/registry/auditregistration/auditsink/doc.go
+17
-0
storage.go
pkg/registry/auditregistration/auditsink/storage/storage.go
+51
-0
strategy.go
pkg/registry/auditregistration/auditsink/strategy.go
+89
-0
storage_auditregistration.go
...istry/auditregistration/rest/storage_auditregistration.go
+53
-0
OWNERS
staging/src/k8s.io/api/auditregistration/OWNERS
+6
-0
doc.go
staging/src/k8s.io/api/auditregistration/v1alpha1/doc.go
+22
-0
register.go
...ing/src/k8s.io/api/auditregistration/v1alpha1/register.go
+56
-0
types.go
staging/src/k8s.io/api/auditregistration/v1alpha1/types.go
+195
-0
validation.go
.../k8s.io/apiserver/pkg/apis/audit/validation/validation.go
+1
-0
print_test.go
test/integration/apiserver/print_test.go
+3
-0
master_utils.go
test/integration/framework/master_utils.go
+5
-0
No files found.
hack/.golint_failures
View file @
381d0a5d
...
@@ -28,6 +28,7 @@ pkg/apis/apps/v1
...
@@ -28,6 +28,7 @@ pkg/apis/apps/v1
pkg/apis/apps/v1beta1
pkg/apis/apps/v1beta1
pkg/apis/apps/v1beta2
pkg/apis/apps/v1beta2
pkg/apis/apps/validation
pkg/apis/apps/validation
pkg/apis/auditregistration/v1alpha1
pkg/apis/authentication
pkg/apis/authentication
pkg/apis/authentication/v1
pkg/apis/authentication/v1
pkg/apis/authentication/v1beta1
pkg/apis/authentication/v1beta1
...
@@ -283,6 +284,7 @@ pkg/registry/apps/replicaset/storage
...
@@ -283,6 +284,7 @@ pkg/registry/apps/replicaset/storage
pkg/registry/apps/rest
pkg/registry/apps/rest
pkg/registry/apps/statefulset
pkg/registry/apps/statefulset
pkg/registry/apps/statefulset/storage
pkg/registry/apps/statefulset/storage
pkg/registry/auditregistration/rest
pkg/registry/authentication/rest
pkg/registry/authentication/rest
pkg/registry/authentication/tokenreview
pkg/registry/authentication/tokenreview
pkg/registry/authorization/localsubjectaccessreview
pkg/registry/authorization/localsubjectaccessreview
...
@@ -453,6 +455,7 @@ staging/src/k8s.io/api/admissionregistration/v1beta1
...
@@ -453,6 +455,7 @@ staging/src/k8s.io/api/admissionregistration/v1beta1
staging/src/k8s.io/api/apps/v1
staging/src/k8s.io/api/apps/v1
staging/src/k8s.io/api/apps/v1beta1
staging/src/k8s.io/api/apps/v1beta1
staging/src/k8s.io/api/apps/v1beta2
staging/src/k8s.io/api/apps/v1beta2
staging/src/k8s.io/api/auditregistration/v1alpha1
staging/src/k8s.io/api/authentication/v1
staging/src/k8s.io/api/authentication/v1
staging/src/k8s.io/api/authentication/v1beta1
staging/src/k8s.io/api/authentication/v1beta1
staging/src/k8s.io/api/authorization/v1
staging/src/k8s.io/api/authorization/v1
...
@@ -555,7 +558,6 @@ staging/src/k8s.io/apiserver/pkg/apis/audit
...
@@ -555,7 +558,6 @@ staging/src/k8s.io/apiserver/pkg/apis/audit
staging/src/k8s.io/apiserver/pkg/apis/audit/v1
staging/src/k8s.io/apiserver/pkg/apis/audit/v1
staging/src/k8s.io/apiserver/pkg/apis/audit/v1alpha1
staging/src/k8s.io/apiserver/pkg/apis/audit/v1alpha1
staging/src/k8s.io/apiserver/pkg/apis/audit/v1beta1
staging/src/k8s.io/apiserver/pkg/apis/audit/v1beta1
staging/src/k8s.io/apiserver/pkg/apis/audit/validation
staging/src/k8s.io/apiserver/pkg/apis/config/v1alpha1
staging/src/k8s.io/apiserver/pkg/apis/config/v1alpha1
staging/src/k8s.io/apiserver/pkg/apis/example
staging/src/k8s.io/apiserver/pkg/apis/example
staging/src/k8s.io/apiserver/pkg/apis/example/v1
staging/src/k8s.io/apiserver/pkg/apis/example/v1
...
...
hack/lib/init.sh
View file @
381d0a5d
...
@@ -62,6 +62,7 @@ admission.k8s.io/v1beta1 \
...
@@ -62,6 +62,7 @@ admission.k8s.io/v1beta1 \
apps/v1beta1 \
apps/v1beta1 \
apps/v1beta2 \
apps/v1beta2 \
apps/v1 \
apps/v1 \
auditregistration.k8s.io/v1alpha1 \
authentication.k8s.io/v1 \
authentication.k8s.io/v1 \
authentication.k8s.io/v1beta1 \
authentication.k8s.io/v1beta1 \
authorization.k8s.io/v1 \
authorization.k8s.io/v1 \
...
...
hack/update-generated-protobuf-dockerized.sh
View file @
381d0a5d
...
@@ -78,6 +78,7 @@ PACKAGES=(
...
@@ -78,6 +78,7 @@ PACKAGES=(
k8s.io/api/admissionregistration/v1alpha1
k8s.io/api/admissionregistration/v1alpha1
k8s.io/api/admissionregistration/v1beta1
k8s.io/api/admissionregistration/v1beta1
k8s.io/api/admission/v1beta1
k8s.io/api/admission/v1beta1
k8s.io/api/auditregistration/v1alpha1
k8s.io/api/networking/v1
k8s.io/api/networking/v1
k8s.io/metrics/pkg/apis/metrics/v1alpha1
k8s.io/metrics/pkg/apis/metrics/v1alpha1
k8s.io/metrics/pkg/apis/metrics/v1beta1
k8s.io/metrics/pkg/apis/metrics/v1beta1
...
...
pkg/api/testapi/testapi.go
View file @
381d0a5d
...
@@ -37,6 +37,7 @@ import (
...
@@ -37,6 +37,7 @@ import (
"k8s.io/kubernetes/pkg/apis/admission"
"k8s.io/kubernetes/pkg/apis/admission"
"k8s.io/kubernetes/pkg/apis/admissionregistration"
"k8s.io/kubernetes/pkg/apis/admissionregistration"
"k8s.io/kubernetes/pkg/apis/apps"
"k8s.io/kubernetes/pkg/apis/apps"
"k8s.io/kubernetes/pkg/apis/auditregistration"
"k8s.io/kubernetes/pkg/apis/authorization"
"k8s.io/kubernetes/pkg/apis/authorization"
"k8s.io/kubernetes/pkg/apis/autoscaling"
"k8s.io/kubernetes/pkg/apis/autoscaling"
"k8s.io/kubernetes/pkg/apis/batch"
"k8s.io/kubernetes/pkg/apis/batch"
...
@@ -57,6 +58,7 @@ import (
...
@@ -57,6 +58,7 @@ import (
_
"k8s.io/kubernetes/pkg/apis/admission/install"
_
"k8s.io/kubernetes/pkg/apis/admission/install"
_
"k8s.io/kubernetes/pkg/apis/admissionregistration/install"
_
"k8s.io/kubernetes/pkg/apis/admissionregistration/install"
_
"k8s.io/kubernetes/pkg/apis/apps/install"
_
"k8s.io/kubernetes/pkg/apis/apps/install"
_
"k8s.io/kubernetes/pkg/apis/auditregistration/install"
_
"k8s.io/kubernetes/pkg/apis/authentication/install"
_
"k8s.io/kubernetes/pkg/apis/authentication/install"
_
"k8s.io/kubernetes/pkg/apis/authorization/install"
_
"k8s.io/kubernetes/pkg/apis/authorization/install"
_
"k8s.io/kubernetes/pkg/apis/autoscaling/install"
_
"k8s.io/kubernetes/pkg/apis/autoscaling/install"
...
@@ -267,6 +269,12 @@ func init() {
...
@@ -267,6 +269,12 @@ func init() {
externalGroupVersion
:
externalGroupVersion
,
externalGroupVersion
:
externalGroupVersion
,
}
}
}
}
if
_
,
ok
:=
Groups
[
auditregistration
.
GroupName
];
!
ok
{
externalGroupVersion
:=
schema
.
GroupVersion
{
Group
:
auditregistration
.
GroupName
,
Version
:
legacyscheme
.
Scheme
.
PrioritizedVersionsForGroup
(
auditregistration
.
GroupName
)[
0
]
.
Version
}
Groups
[
auditregistration
.
GroupName
]
=
TestGroup
{
externalGroupVersion
:
externalGroupVersion
,
}
}
Default
=
Groups
[
api
.
GroupName
]
Default
=
Groups
[
api
.
GroupName
]
Autoscaling
=
Groups
[
autoscaling
.
GroupName
]
Autoscaling
=
Groups
[
autoscaling
.
GroupName
]
...
...
pkg/api/testing/defaulting_test.go
View file @
381d0a5d
...
@@ -136,6 +136,8 @@ func TestDefaulting(t *testing.T) {
...
@@ -136,6 +136,8 @@ func TestDefaulting(t *testing.T) {
{
Group
:
"admissionregistration.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"ValidatingWebhookConfigurationList"
}
:
{},
{
Group
:
"admissionregistration.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"ValidatingWebhookConfigurationList"
}
:
{},
{
Group
:
"admissionregistration.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"MutatingWebhookConfiguration"
}
:
{},
{
Group
:
"admissionregistration.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"MutatingWebhookConfiguration"
}
:
{},
{
Group
:
"admissionregistration.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"MutatingWebhookConfigurationList"
}
:
{},
{
Group
:
"admissionregistration.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"MutatingWebhookConfigurationList"
}
:
{},
{
Group
:
"auditregistration.k8s.io"
,
Version
:
"v1alpha1"
,
Kind
:
"AuditSink"
}
:
{},
{
Group
:
"auditregistration.k8s.io"
,
Version
:
"v1alpha1"
,
Kind
:
"AuditSinkList"
}
:
{},
{
Group
:
"networking.k8s.io"
,
Version
:
"v1"
,
Kind
:
"NetworkPolicy"
}
:
{},
{
Group
:
"networking.k8s.io"
,
Version
:
"v1"
,
Kind
:
"NetworkPolicy"
}
:
{},
{
Group
:
"networking.k8s.io"
,
Version
:
"v1"
,
Kind
:
"NetworkPolicyList"
}
:
{},
{
Group
:
"networking.k8s.io"
,
Version
:
"v1"
,
Kind
:
"NetworkPolicyList"
}
:
{},
{
Group
:
"storage.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"StorageClass"
}
:
{},
{
Group
:
"storage.k8s.io"
,
Version
:
"v1beta1"
,
Kind
:
"StorageClass"
}
:
{},
...
...
pkg/api/testing/fuzzer.go
View file @
381d0a5d
...
@@ -29,6 +29,7 @@ import (
...
@@ -29,6 +29,7 @@ import (
runtimeserializer
"k8s.io/apimachinery/pkg/runtime/serializer"
runtimeserializer
"k8s.io/apimachinery/pkg/runtime/serializer"
admissionregistrationfuzzer
"k8s.io/kubernetes/pkg/apis/admissionregistration/fuzzer"
admissionregistrationfuzzer
"k8s.io/kubernetes/pkg/apis/admissionregistration/fuzzer"
appsfuzzer
"k8s.io/kubernetes/pkg/apis/apps/fuzzer"
appsfuzzer
"k8s.io/kubernetes/pkg/apis/apps/fuzzer"
auditregistrationfuzzer
"k8s.io/kubernetes/pkg/apis/auditregistration/fuzzer"
autoscalingfuzzer
"k8s.io/kubernetes/pkg/apis/autoscaling/fuzzer"
autoscalingfuzzer
"k8s.io/kubernetes/pkg/apis/autoscaling/fuzzer"
batchfuzzer
"k8s.io/kubernetes/pkg/apis/batch/fuzzer"
batchfuzzer
"k8s.io/kubernetes/pkg/apis/batch/fuzzer"
certificatesfuzzer
"k8s.io/kubernetes/pkg/apis/certificates/fuzzer"
certificatesfuzzer
"k8s.io/kubernetes/pkg/apis/certificates/fuzzer"
...
@@ -101,6 +102,7 @@ var FuzzerFuncs = fuzzer.MergeFuzzerFuncs(
...
@@ -101,6 +102,7 @@ var FuzzerFuncs = fuzzer.MergeFuzzerFuncs(
policyfuzzer
.
Funcs
,
policyfuzzer
.
Funcs
,
certificatesfuzzer
.
Funcs
,
certificatesfuzzer
.
Funcs
,
admissionregistrationfuzzer
.
Funcs
,
admissionregistrationfuzzer
.
Funcs
,
auditregistrationfuzzer
.
Funcs
,
storagefuzzer
.
Funcs
,
storagefuzzer
.
Funcs
,
networkingfuzzer
.
Funcs
,
networkingfuzzer
.
Funcs
,
)
)
pkg/apis/admissionregistration/validation/validation.go
View file @
381d0a5d
...
@@ -240,6 +240,7 @@ func validateWebhookClientConfig(fldPath *field.Path, cc *admissionregistration.
...
@@ -240,6 +240,7 @@ func validateWebhookClientConfig(fldPath *field.Path, cc *admissionregistration.
return
allErrors
return
allErrors
}
}
// note: this has copy/paste inheritance in auditregistration
func
validateWebhookService
(
fldPath
*
field
.
Path
,
svc
*
admissionregistration
.
ServiceReference
)
field
.
ErrorList
{
func
validateWebhookService
(
fldPath
*
field
.
Path
,
svc
*
admissionregistration
.
ServiceReference
)
field
.
ErrorList
{
var
allErrors
field
.
ErrorList
var
allErrors
field
.
ErrorList
...
...
pkg/apis/auditregistration/doc.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// +k8s:deepcopy-gen=package
// +groupName=auditregistration.k8s.io
package
auditregistration
// import "k8s.io/kubernetes/pkg/apis/auditregistration"
pkg/apis/auditregistration/fuzzer/fuzzer.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
fuzzer
import
(
fuzz
"github.com/google/gofuzz"
runtimeserializer
"k8s.io/apimachinery/pkg/runtime/serializer"
"k8s.io/kubernetes/pkg/apis/auditregistration"
)
// Funcs returns the fuzzer functions for the auditregistration api group.
var
Funcs
=
func
(
codecs
runtimeserializer
.
CodecFactory
)
[]
interface
{}
{
return
[]
interface
{}{
func
(
obj
*
auditregistration
.
AuditSink
,
c
fuzz
.
Continue
)
{
c
.
FuzzNoCustom
(
obj
)
v
:=
int64
(
1
)
obj
.
Spec
.
Webhook
.
Throttle
=
&
auditregistration
.
WebhookThrottleConfig
{
QPS
:
&
v
,
Burst
:
&
v
,
}
},
}
}
pkg/apis/auditregistration/install/install.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// Package install adds the experimental API group, making it available as
// an option to all of the API encoding/decoding machinery.
package
install
import
(
"k8s.io/apimachinery/pkg/runtime"
utilruntime
"k8s.io/apimachinery/pkg/util/runtime"
"k8s.io/kubernetes/pkg/api/legacyscheme"
"k8s.io/kubernetes/pkg/apis/auditregistration"
"k8s.io/kubernetes/pkg/apis/auditregistration/v1alpha1"
)
func
init
()
{
Install
(
legacyscheme
.
Scheme
)
}
// Install registers the API group and adds types to a scheme
func
Install
(
scheme
*
runtime
.
Scheme
)
{
utilruntime
.
Must
(
auditregistration
.
AddToScheme
(
scheme
))
utilruntime
.
Must
(
v1alpha1
.
AddToScheme
(
scheme
))
utilruntime
.
Must
(
scheme
.
SetVersionPriority
(
v1alpha1
.
SchemeGroupVersion
))
}
pkg/apis/auditregistration/register.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
auditregistration
import
(
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/runtime/schema"
)
// GroupName is the group name use in this package
const
GroupName
=
"auditregistration.k8s.io"
// SchemeGroupVersion is group version used to register these objects
var
SchemeGroupVersion
=
schema
.
GroupVersion
{
Group
:
GroupName
,
Version
:
runtime
.
APIVersionInternal
}
// Kind takes an unqualified kind and returns a Group qualified GroupKind
func
Kind
(
kind
string
)
schema
.
GroupKind
{
return
SchemeGroupVersion
.
WithKind
(
kind
)
.
GroupKind
()
}
// Resource takes an unqualified resource and returns a Group qualified GroupResource
func
Resource
(
resource
string
)
schema
.
GroupResource
{
return
SchemeGroupVersion
.
WithResource
(
resource
)
.
GroupResource
()
}
var
(
// SchemeBuilder for audit registration
SchemeBuilder
=
runtime
.
NewSchemeBuilder
(
addKnownTypes
)
// AddToScheme audit registration
AddToScheme
=
SchemeBuilder
.
AddToScheme
)
func
addKnownTypes
(
scheme
*
runtime
.
Scheme
)
error
{
scheme
.
AddKnownTypes
(
SchemeGroupVersion
,
&
AuditSink
{},
&
AuditSinkList
{},
)
return
nil
}
pkg/apis/auditregistration/types.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// +k8s:openapi-gen=true
package
auditregistration
import
(
metav1
"k8s.io/apimachinery/pkg/apis/meta/v1"
)
// Level defines the amount of information logged during auditing
type
Level
string
// Valid audit levels
const
(
// LevelNone disables auditing
LevelNone
Level
=
"None"
// LevelMetadata provides the basic level of auditing.
LevelMetadata
Level
=
"Metadata"
// LevelRequest provides Metadata level of auditing, and additionally
// logs the request object (does not apply for non-resource requests).
LevelRequest
Level
=
"Request"
// LevelRequestResponse provides Request level of auditing, and additionally
// logs the response object (does not apply for non-resource requests and watches).
LevelRequestResponse
Level
=
"RequestResponse"
)
// Stage defines the stages in request handling during which audit events may be generated.
type
Stage
string
// Valid audit stages.
const
(
// The stage for events generated after the audit handler receives the request, but before it
// is delegated down the handler chain.
StageRequestReceived
=
"RequestReceived"
// The stage for events generated after the response headers are sent, but before the response body
// is sent. This stage is only generated for long-running requests (e.g. watch).
StageResponseStarted
=
"ResponseStarted"
// The stage for events generated after the response body has been completed, and no more bytes
// will be sent.
StageResponseComplete
=
"ResponseComplete"
// The stage for events generated when a panic occurred.
StagePanic
=
"Panic"
)
// +genclient
// +genclient:nonNamespaced
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// AuditSink represents a cluster level sink for audit data
type
AuditSink
struct
{
metav1
.
TypeMeta
// +optional
metav1
.
ObjectMeta
// Spec defines the audit sink spec
Spec
AuditSinkSpec
}
// AuditSinkSpec is the spec for the audit sink object
type
AuditSinkSpec
struct
{
// Policy defines the policy for selecting which events should be sent to the backend
// required
Policy
Policy
// Webhook to send events
// required
Webhook
Webhook
}
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// AuditSinkList is a list of a audit sink items.
type
AuditSinkList
struct
{
metav1
.
TypeMeta
// +optional
metav1
.
ListMeta
// List of audit configurations.
Items
[]
AuditSink
}
// Policy defines the configuration of how audit events are logged
type
Policy
struct
{
// The Level that all requests are recorded at.
// available options: None, Metadata, Request, RequestResponse
// required
Level
Level
// Stages is a list of stages for which events are created.
// +optional
Stages
[]
Stage
}
// Webhook holds the configuration of the webhooks
type
Webhook
struct
{
// Throttle holds the options for throttling the webhook
// +optional
Throttle
*
WebhookThrottleConfig
// ClientConfig holds the connection parameters for the webhook
// required
ClientConfig
WebhookClientConfig
}
// WebhookThrottleConfig holds the configuration for throttling
type
WebhookThrottleConfig
struct
{
// QPS maximum number of batches per second
// default 10 QPS
// +optional
QPS
*
int64
// Burst is the maximum number of events sent at the same moment
// default 15 QPS
// +optional
Burst
*
int64
}
// WebhookClientConfig contains the information to make a connection with the webhook
type
WebhookClientConfig
struct
{
// `url` gives the location of the webhook, in standard URL form
// (`[scheme://]host:port/path`). Exactly one of `url` or `service`
// must be specified.
//
// The `host` should not refer to a service running in the cluster; use
// the `service` field instead. The host might be resolved via external
// DNS in some apiservers (e.g., `kube-apiserver` cannot resolve
// in-cluster DNS as that would be a layering violation). `host` may
// also be an IP address.
//
// Please note that using `localhost` or `127.0.0.1` as a `host` is
// risky unless you take great care to run this webhook on all hosts
// which run an apiserver which might need to make calls to this
// webhook. Such installs are likely to be non-portable, i.e., not easy
// to turn up in a new cluster.
//
// The scheme must be "https"; the URL must begin with "https://".
//
// A path is optional, and if present may be any string permissible in
// a URL. You may use the path to pass an arbitrary string to the
// webhook, for example, a cluster identifier.
//
// Attempting to use a user or basic auth e.g. "user:password@" is not
// allowed. Fragments ("#...") and query parameters ("?...") are not
// allowed, either.
//
// +optional
URL
*
string
// `service` is a reference to the service for this webhook. Either
// `service` or `url` must be specified.
//
// If the webhook is running within the cluster, then you should use `service`.
//
// Port 443 will be used if it is open, otherwise it is an error.
//
// +optional
Service
*
ServiceReference
// `caBundle` is a PEM encoded CA bundle which will be used to validate
// the webhook's server certificate.
// defaults to the apiservers CA bundle for the endpoint type
// +optional
CABundle
[]
byte
}
// ServiceReference holds a reference to Service.legacy.k8s.io
type
ServiceReference
struct
{
// `namespace` is the namespace of the service.
// Required
Namespace
string
// `name` is the name of the service.
// Required
Name
string
// `path` is an optional URL path which will be sent in any request to
// this service.
// +optional
Path
*
string
}
pkg/apis/auditregistration/v1alpha1/defaults.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
v1alpha1
import
(
auditregistrationv1alpha1
"k8s.io/api/auditregistration/v1alpha1"
"k8s.io/apimachinery/pkg/runtime"
utilpointer
"k8s.io/utils/pointer"
)
const
(
// DefaultQPS is the default QPS value
DefaultQPS
=
int64
(
10
)
// DefaultBurst is the default burst value
DefaultBurst
=
int64
(
15
)
)
// DefaultThrottle is a default throttle config
func
DefaultThrottle
()
*
auditregistrationv1alpha1
.
WebhookThrottleConfig
{
return
&
auditregistrationv1alpha1
.
WebhookThrottleConfig
{
QPS
:
utilpointer
.
Int64Ptr
(
DefaultQPS
),
Burst
:
utilpointer
.
Int64Ptr
(
DefaultBurst
),
}
}
func
addDefaultingFuncs
(
scheme
*
runtime
.
Scheme
)
error
{
return
RegisterDefaults
(
scheme
)
}
// SetDefaults_AuditSink sets defaults if the audit sink isn't present
func
SetDefaults_AuditSink
(
obj
*
auditregistrationv1alpha1
.
AuditSink
)
{
if
obj
.
Spec
.
Webhook
.
Throttle
!=
nil
{
if
obj
.
Spec
.
Webhook
.
Throttle
.
QPS
==
nil
{
obj
.
Spec
.
Webhook
.
Throttle
.
QPS
=
utilpointer
.
Int64Ptr
(
DefaultQPS
)
}
if
obj
.
Spec
.
Webhook
.
Throttle
.
Burst
==
nil
{
obj
.
Spec
.
Webhook
.
Throttle
.
Burst
=
utilpointer
.
Int64Ptr
(
DefaultBurst
)
}
}
else
{
obj
.
Spec
.
Webhook
.
Throttle
=
DefaultThrottle
()
}
}
pkg/apis/auditregistration/v1alpha1/defaults_test.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
v1alpha1_test
import
(
"reflect"
"testing"
auditregistrationv1alpha1
"k8s.io/api/auditregistration/v1alpha1"
apiequality
"k8s.io/apimachinery/pkg/api/equality"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/kubernetes/pkg/api/legacyscheme"
_
"k8s.io/kubernetes/pkg/apis/auditregistration/install"
.
"k8s.io/kubernetes/pkg/apis/auditregistration/v1alpha1"
utilpointer
"k8s.io/utils/pointer"
)
func
TestSetDefaultAuditSink
(
t
*
testing
.
T
)
{
defaultURL
:=
"http://test"
tests
:=
[]
struct
{
original
*
auditregistrationv1alpha1
.
AuditSink
expected
*
auditregistrationv1alpha1
.
AuditSink
}{
{
// Missing Throttle
original
:
&
auditregistrationv1alpha1
.
AuditSink
{
Spec
:
auditregistrationv1alpha1
.
AuditSinkSpec
{
Policy
:
auditregistrationv1alpha1
.
Policy
{
Level
:
auditregistrationv1alpha1
.
LevelMetadata
,
},
Webhook
:
auditregistrationv1alpha1
.
Webhook
{
ClientConfig
:
auditregistrationv1alpha1
.
WebhookClientConfig
{
URL
:
&
defaultURL
,
},
},
},
},
expected
:
&
auditregistrationv1alpha1
.
AuditSink
{
Spec
:
auditregistrationv1alpha1
.
AuditSinkSpec
{
Policy
:
auditregistrationv1alpha1
.
Policy
{
Level
:
auditregistrationv1alpha1
.
LevelMetadata
,
},
Webhook
:
auditregistrationv1alpha1
.
Webhook
{
Throttle
:
DefaultThrottle
(),
ClientConfig
:
auditregistrationv1alpha1
.
WebhookClientConfig
{
URL
:
&
defaultURL
,
},
},
},
},
},
{
// Missing QPS
original
:
&
auditregistrationv1alpha1
.
AuditSink
{
Spec
:
auditregistrationv1alpha1
.
AuditSinkSpec
{
Policy
:
auditregistrationv1alpha1
.
Policy
{
Level
:
auditregistrationv1alpha1
.
LevelMetadata
,
},
Webhook
:
auditregistrationv1alpha1
.
Webhook
{
Throttle
:
&
auditregistrationv1alpha1
.
WebhookThrottleConfig
{
Burst
:
utilpointer
.
Int64Ptr
(
1
),
},
ClientConfig
:
auditregistrationv1alpha1
.
WebhookClientConfig
{
URL
:
&
defaultURL
,
},
},
},
},
expected
:
&
auditregistrationv1alpha1
.
AuditSink
{
Spec
:
auditregistrationv1alpha1
.
AuditSinkSpec
{
Policy
:
auditregistrationv1alpha1
.
Policy
{
Level
:
auditregistrationv1alpha1
.
LevelMetadata
,
},
Webhook
:
auditregistrationv1alpha1
.
Webhook
{
Throttle
:
&
auditregistrationv1alpha1
.
WebhookThrottleConfig
{
QPS
:
DefaultThrottle
()
.
QPS
,
Burst
:
utilpointer
.
Int64Ptr
(
1
),
},
ClientConfig
:
auditregistrationv1alpha1
.
WebhookClientConfig
{
URL
:
&
defaultURL
,
},
},
},
},
},
{
// Missing Burst
original
:
&
auditregistrationv1alpha1
.
AuditSink
{
Spec
:
auditregistrationv1alpha1
.
AuditSinkSpec
{
Policy
:
auditregistrationv1alpha1
.
Policy
{
Level
:
auditregistrationv1alpha1
.
LevelMetadata
,
},
Webhook
:
auditregistrationv1alpha1
.
Webhook
{
Throttle
:
&
auditregistrationv1alpha1
.
WebhookThrottleConfig
{
QPS
:
utilpointer
.
Int64Ptr
(
1
),
},
ClientConfig
:
auditregistrationv1alpha1
.
WebhookClientConfig
{
URL
:
&
defaultURL
,
},
},
},
},
expected
:
&
auditregistrationv1alpha1
.
AuditSink
{
Spec
:
auditregistrationv1alpha1
.
AuditSinkSpec
{
Policy
:
auditregistrationv1alpha1
.
Policy
{
Level
:
auditregistrationv1alpha1
.
LevelMetadata
,
},
Webhook
:
auditregistrationv1alpha1
.
Webhook
{
Throttle
:
&
auditregistrationv1alpha1
.
WebhookThrottleConfig
{
QPS
:
utilpointer
.
Int64Ptr
(
1
),
Burst
:
DefaultThrottle
()
.
Burst
,
},
ClientConfig
:
auditregistrationv1alpha1
.
WebhookClientConfig
{
URL
:
&
defaultURL
,
},
},
},
},
},
}
for
i
,
test
:=
range
tests
{
original
:=
test
.
original
expected
:=
test
.
expected
obj2
:=
roundTrip
(
t
,
runtime
.
Object
(
original
))
got
,
ok
:=
obj2
.
(
*
auditregistrationv1alpha1
.
AuditSink
)
if
!
ok
{
t
.
Fatalf
(
"(%d) unexpected object: %v"
,
i
,
obj2
)
}
if
!
apiequality
.
Semantic
.
DeepEqual
(
got
.
Spec
,
expected
.
Spec
)
{
t
.
Errorf
(
"(%d) got different than expected
\n
got:
\n\t
%+v
\n
expected:
\n\t
%+v"
,
i
,
got
.
Spec
,
expected
.
Spec
)
}
}
}
func
roundTrip
(
t
*
testing
.
T
,
obj
runtime
.
Object
)
runtime
.
Object
{
data
,
err
:=
runtime
.
Encode
(
legacyscheme
.
Codecs
.
LegacyCodec
(
SchemeGroupVersion
),
obj
)
if
err
!=
nil
{
t
.
Errorf
(
"%v
\n
%#v"
,
err
,
obj
)
return
nil
}
obj2
,
err
:=
runtime
.
Decode
(
legacyscheme
.
Codecs
.
UniversalDecoder
(),
data
)
if
err
!=
nil
{
t
.
Errorf
(
"%v
\n
Data: %s
\n
Source: %#v"
,
err
,
string
(
data
),
obj
)
return
nil
}
obj3
:=
reflect
.
New
(
reflect
.
TypeOf
(
obj
)
.
Elem
())
.
Interface
()
.
(
runtime
.
Object
)
err
=
legacyscheme
.
Scheme
.
Convert
(
obj2
,
obj3
,
nil
)
if
err
!=
nil
{
t
.
Errorf
(
"%v
\n
Source: %#v"
,
err
,
obj2
)
return
nil
}
return
obj3
}
pkg/apis/auditregistration/v1alpha1/doc.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// +k8s:conversion-gen=k8s.io/kubernetes/pkg/apis/auditregistration
// +k8s:conversion-gen-external-types=k8s.io/api/auditregistration/v1alpha1
// +k8s:defaulter-gen=TypeMeta
// +k8s:defaulter-gen-input=../../../../vendor/k8s.io/api/auditregistration/v1alpha1
// +groupName=auditregistration.k8s.io
package
v1alpha1
// import "k8s.io/kubernetes/pkg/apis/auditregistration/v1alpha1"
pkg/apis/auditregistration/v1alpha1/register.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
v1alpha1
import
(
auditregistrationv1alpha1
"k8s.io/api/auditregistration/v1alpha1"
"k8s.io/apimachinery/pkg/runtime/schema"
)
// GroupName for audit registration
const
GroupName
=
"auditregistration.k8s.io"
// SchemeGroupVersion is group version used to register these objects
var
SchemeGroupVersion
=
schema
.
GroupVersion
{
Group
:
GroupName
,
Version
:
"v1alpha1"
}
// Resource takes an unqualified resource and returns a Group qualified GroupResource
func
Resource
(
resource
string
)
schema
.
GroupResource
{
return
SchemeGroupVersion
.
WithResource
(
resource
)
.
GroupResource
()
}
var
(
localSchemeBuilder
=
&
auditregistrationv1alpha1
.
SchemeBuilder
// AddToScheme audit registration
AddToScheme
=
localSchemeBuilder
.
AddToScheme
)
func
init
()
{
// We only register manually written functions here. The registration of the
// generated functions takes place in the generated files. The separation
// makes the code compile even when the generated files are missing.
localSchemeBuilder
.
Register
(
addDefaultingFuncs
)
}
pkg/apis/auditregistration/validation/validation.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
validation
import
(
"fmt"
"net/url"
"strings"
genericvalidation
"k8s.io/apimachinery/pkg/api/validation"
"k8s.io/apimachinery/pkg/util/sets"
"k8s.io/apimachinery/pkg/util/validation"
"k8s.io/apimachinery/pkg/util/validation/field"
"k8s.io/kubernetes/pkg/apis/auditregistration"
)
// ValidateAuditSink validates the AuditSinks
func
ValidateAuditSink
(
as
*
auditregistration
.
AuditSink
)
field
.
ErrorList
{
allErrs
:=
genericvalidation
.
ValidateObjectMeta
(
&
as
.
ObjectMeta
,
false
,
genericvalidation
.
NameIsDNSSubdomain
,
field
.
NewPath
(
"metadata"
))
allErrs
=
append
(
allErrs
,
ValidateAuditSinkSpec
(
as
.
Spec
,
field
.
NewPath
(
"spec"
))
...
)
return
allErrs
}
// ValidateAuditSinkSpec validates the sink spec for audit
func
ValidateAuditSinkSpec
(
s
auditregistration
.
AuditSinkSpec
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrs
field
.
ErrorList
allErrs
=
append
(
allErrs
,
ValidatePolicy
(
s
.
Policy
,
field
.
NewPath
(
"policy"
))
...
)
allErrs
=
append
(
allErrs
,
ValidateWebhook
(
s
.
Webhook
,
field
.
NewPath
(
"webhook"
))
...
)
return
allErrs
}
// ValidateWebhook validates the webhook
func
ValidateWebhook
(
w
auditregistration
.
Webhook
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrs
field
.
ErrorList
if
w
.
Throttle
!=
nil
{
allErrs
=
append
(
allErrs
,
ValidateWebhookThrottleConfig
(
w
.
Throttle
,
fldPath
.
Child
(
"throttle"
))
...
)
}
allErrs
=
append
(
allErrs
,
ValidateWebhookClientConfig
(
&
w
.
ClientConfig
,
fldPath
.
Child
(
"clientConfig"
))
...
)
return
allErrs
}
// ValidateWebhookThrottleConfig validates the throttle config
func
ValidateWebhookThrottleConfig
(
c
*
auditregistration
.
WebhookThrottleConfig
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrs
field
.
ErrorList
if
c
.
QPS
!=
nil
&&
*
c
.
QPS
<=
0
{
allErrs
=
append
(
allErrs
,
field
.
Invalid
(
fldPath
.
Child
(
"qps"
),
c
.
QPS
,
"qps must be a positive number"
))
}
if
c
.
Burst
!=
nil
&&
*
c
.
Burst
<=
0
{
allErrs
=
append
(
allErrs
,
field
.
Invalid
(
fldPath
.
Child
(
"burst"
),
c
.
Burst
,
"burst must be a positive number"
))
}
return
allErrs
}
// ValidateWebhookClientConfig validates the WebhookClientConfig
// note: this is largely copy/paste inheritance from admissionregistration with subtle changes
func
ValidateWebhookClientConfig
(
cc
*
auditregistration
.
WebhookClientConfig
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrors
field
.
ErrorList
if
(
cc
.
URL
==
nil
)
==
(
cc
.
Service
==
nil
)
{
allErrors
=
append
(
allErrors
,
field
.
Required
(
fldPath
.
Child
(
"url"
),
"exactly one of url or service is required"
))
}
if
cc
.
URL
!=
nil
{
const
form
=
"; desired format: https://host[/path]"
if
u
,
err
:=
url
.
Parse
(
*
cc
.
URL
);
err
!=
nil
{
allErrors
=
append
(
allErrors
,
field
.
Required
(
fldPath
.
Child
(
"url"
),
"url must be a valid URL: "
+
err
.
Error
()
+
form
))
}
else
{
if
len
(
u
.
Host
)
==
0
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"url"
),
u
.
Host
,
"host must be provided"
+
form
))
}
if
u
.
User
!=
nil
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"url"
),
u
.
User
.
String
(),
"user information is not permitted in the URL"
))
}
if
len
(
u
.
Fragment
)
!=
0
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"url"
),
u
.
Fragment
,
"fragments are not permitted in the URL"
))
}
if
len
(
u
.
RawQuery
)
!=
0
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"url"
),
u
.
RawQuery
,
"query parameters are not permitted in the URL"
))
}
}
}
if
cc
.
Service
!=
nil
{
allErrors
=
append
(
allErrors
,
validateWebhookService
(
cc
.
Service
,
fldPath
.
Child
(
"service"
))
...
)
}
return
allErrors
}
// note: this is copy/paste inheritance from admissionregistration
func
validateWebhookService
(
svc
*
auditregistration
.
ServiceReference
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrors
field
.
ErrorList
if
len
(
svc
.
Name
)
==
0
{
allErrors
=
append
(
allErrors
,
field
.
Required
(
fldPath
.
Child
(
"name"
),
"service name is required"
))
}
if
len
(
svc
.
Namespace
)
==
0
{
allErrors
=
append
(
allErrors
,
field
.
Required
(
fldPath
.
Child
(
"namespace"
),
"service namespace is required"
))
}
if
svc
.
Path
==
nil
{
return
allErrors
}
// TODO: replace below with url.Parse + verifying that host is empty?
urlPath
:=
*
svc
.
Path
if
urlPath
==
"/"
||
len
(
urlPath
)
==
0
{
return
allErrors
}
if
urlPath
==
"//"
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"path"
),
urlPath
,
"segment[0] may not be empty"
))
return
allErrors
}
if
!
strings
.
HasPrefix
(
urlPath
,
"/"
)
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"path"
),
urlPath
,
"must start with a '/'"
))
}
urlPathToCheck
:=
urlPath
[
1
:
]
if
strings
.
HasSuffix
(
urlPathToCheck
,
"/"
)
{
urlPathToCheck
=
urlPathToCheck
[
:
len
(
urlPathToCheck
)
-
1
]
}
steps
:=
strings
.
Split
(
urlPathToCheck
,
"/"
)
for
i
,
step
:=
range
steps
{
if
len
(
step
)
==
0
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"path"
),
urlPath
,
fmt
.
Sprintf
(
"segment[%d] may not be empty"
,
i
)))
continue
}
failures
:=
validation
.
IsDNS1123Subdomain
(
step
)
for
_
,
failure
:=
range
failures
{
allErrors
=
append
(
allErrors
,
field
.
Invalid
(
fldPath
.
Child
(
"path"
),
urlPath
,
fmt
.
Sprintf
(
"segment[%d]: %v"
,
i
,
failure
)))
}
}
return
allErrors
}
// ValidatePolicy validates the audit policy
func
ValidatePolicy
(
policy
auditregistration
.
Policy
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrs
field
.
ErrorList
allErrs
=
append
(
allErrs
,
validateStages
(
policy
.
Stages
,
fldPath
.
Child
(
"stages"
))
...
)
allErrs
=
append
(
allErrs
,
validateLevel
(
policy
.
Level
,
fldPath
.
Child
(
"level"
))
...
)
if
policy
.
Level
!=
auditregistration
.
LevelNone
&&
len
(
policy
.
Stages
)
==
0
{
return
field
.
ErrorList
{
field
.
Required
(
fldPath
.
Child
(
"stages"
),
""
)}
}
return
allErrs
}
var
validLevels
=
sets
.
NewString
(
string
(
auditregistration
.
LevelNone
),
string
(
auditregistration
.
LevelMetadata
),
string
(
auditregistration
.
LevelRequest
),
string
(
auditregistration
.
LevelRequestResponse
),
)
var
validStages
=
sets
.
NewString
(
string
(
auditregistration
.
StageRequestReceived
),
string
(
auditregistration
.
StageResponseStarted
),
string
(
auditregistration
.
StageResponseComplete
),
string
(
auditregistration
.
StagePanic
),
)
func
validateLevel
(
level
auditregistration
.
Level
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
if
string
(
level
)
==
""
{
return
field
.
ErrorList
{
field
.
Required
(
fldPath
,
""
)}
}
if
!
validLevels
.
Has
(
string
(
level
))
{
return
field
.
ErrorList
{
field
.
NotSupported
(
fldPath
,
level
,
validLevels
.
List
())}
}
return
nil
}
func
validateStages
(
stages
[]
auditregistration
.
Stage
,
fldPath
*
field
.
Path
)
field
.
ErrorList
{
var
allErrs
field
.
ErrorList
for
i
,
stage
:=
range
stages
{
if
!
validStages
.
Has
(
string
(
stage
))
{
allErrs
=
append
(
allErrs
,
field
.
Invalid
(
fldPath
.
Index
(
i
),
string
(
stage
),
"allowed stages are "
+
strings
.
Join
(
validStages
.
List
(),
","
)))
}
}
return
allErrs
}
// ValidateAuditSinkUpdate validates an update to the object
func
ValidateAuditSinkUpdate
(
newC
,
oldC
*
auditregistration
.
AuditSink
)
field
.
ErrorList
{
return
ValidateAuditSink
(
newC
)
}
pkg/apis/auditregistration/validation/validation_test.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
validation
import
(
"strings"
"testing"
"github.com/stretchr/testify/require"
metav1
"k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/util/validation/field"
"k8s.io/kubernetes/pkg/apis/auditregistration"
)
func
TestValidateAuditSink
(
t
*
testing
.
T
)
{
testQPS
:=
int64
(
10
)
testURL
:=
"http://localhost"
testCases
:=
[]
struct
{
name
string
conf
auditregistration
.
AuditSink
numErr
int
}{
{
name
:
"should pass full config"
,
conf
:
auditregistration
.
AuditSink
{
ObjectMeta
:
metav1
.
ObjectMeta
{
Name
:
"myconf"
,
},
Spec
:
auditregistration
.
AuditSinkSpec
{
Policy
:
auditregistration
.
Policy
{
Level
:
auditregistration
.
LevelRequest
,
Stages
:
[]
auditregistration
.
Stage
{
auditregistration
.
StageRequestReceived
,
},
},
Webhook
:
auditregistration
.
Webhook
{
Throttle
:
&
auditregistration
.
WebhookThrottleConfig
{
QPS
:
&
testQPS
,
},
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
&
testURL
,
},
},
},
},
numErr
:
0
,
},
{
name
:
"should fail no policy"
,
conf
:
auditregistration
.
AuditSink
{
ObjectMeta
:
metav1
.
ObjectMeta
{
Name
:
"myconf"
,
},
Spec
:
auditregistration
.
AuditSinkSpec
{
Webhook
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
&
testURL
,
},
},
},
},
numErr
:
1
,
},
{
name
:
"should fail no webhook"
,
conf
:
auditregistration
.
AuditSink
{
ObjectMeta
:
metav1
.
ObjectMeta
{
Name
:
"myconf"
,
},
Spec
:
auditregistration
.
AuditSinkSpec
{
Policy
:
auditregistration
.
Policy
{
Level
:
auditregistration
.
LevelMetadata
,
Stages
:
[]
auditregistration
.
Stage
{
auditregistration
.
StageRequestReceived
,
},
},
},
},
numErr
:
1
,
},
}
for
_
,
test
:=
range
testCases
{
t
.
Run
(
test
.
name
,
func
(
t
*
testing
.
T
)
{
errs
:=
ValidateAuditSink
(
&
test
.
conf
)
require
.
Len
(
t
,
errs
,
test
.
numErr
)
})
}
}
func
TestValidatePolicy
(
t
*
testing
.
T
)
{
successCases
:=
[]
auditregistration
.
Policy
{}
successCases
=
append
(
successCases
,
auditregistration
.
Policy
{
// Policy with omitStages and level
Level
:
auditregistration
.
LevelRequest
,
Stages
:
[]
auditregistration
.
Stage
{
auditregistration
.
Stage
(
"RequestReceived"
),
auditregistration
.
Stage
(
"ResponseStarted"
),
},
})
successCases
=
append
(
successCases
,
auditregistration
.
Policy
{
Level
:
auditregistration
.
LevelNone
})
// Policy with none level only
for
i
,
policy
:=
range
successCases
{
if
errs
:=
ValidatePolicy
(
policy
,
field
.
NewPath
(
"policy"
));
len
(
errs
)
!=
0
{
t
.
Errorf
(
"[%d] Expected policy %#v to be valid: %v"
,
i
,
policy
,
errs
)
}
}
errorCases
:=
[]
auditregistration
.
Policy
{}
errorCases
=
append
(
errorCases
,
auditregistration
.
Policy
{})
// Empty policy // Policy with missing level
errorCases
=
append
(
errorCases
,
auditregistration
.
Policy
{
Stages
:
[]
auditregistration
.
Stage
{
// Policy with invalid stages
auditregistration
.
Stage
(
"Bad"
)}})
errorCases
=
append
(
errorCases
,
auditregistration
.
Policy
{
Level
:
auditregistration
.
Level
(
"invalid"
)})
// Policy with bad level
errorCases
=
append
(
errorCases
,
auditregistration
.
Policy
{
Level
:
auditregistration
.
LevelMetadata
})
// Policy without stages
for
i
,
policy
:=
range
errorCases
{
if
errs
:=
ValidatePolicy
(
policy
,
field
.
NewPath
(
"policy"
));
len
(
errs
)
==
0
{
t
.
Errorf
(
"[%d] Expected policy %#v to be invalid!"
,
i
,
policy
)
}
}
}
func
strPtr
(
s
string
)
*
string
{
return
&
s
}
func
TestValidateWebhookConfiguration
(
t
*
testing
.
T
)
{
tests
:=
[]
struct
{
name
string
config
auditregistration
.
Webhook
expectedError
string
}{
{
name
:
"both service and URL missing"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{},
},
expectedError
:
`exactly one of`
,
},
{
name
:
"both service and URL provided"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
},
URL
:
strPtr
(
"example.com/k8s/webhook"
),
},
},
expectedError
:
`webhook.clientConfig.url: Required value: exactly one of url or service is required`
,
},
{
name
:
"blank URL"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
strPtr
(
""
),
},
},
expectedError
:
`webhook.clientConfig.url: Invalid value: "": host must be provided`
,
},
{
name
:
"missing host"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
strPtr
(
"https:///fancy/webhook"
),
},
},
expectedError
:
`host must be provided`
,
},
{
name
:
"fragment"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
strPtr
(
"https://example.com/#bookmark"
),
},
},
expectedError
:
`"bookmark": fragments are not permitted`
,
},
{
name
:
"query"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
strPtr
(
"https://example.com?arg=value"
),
},
},
expectedError
:
`"arg=value": query parameters are not permitted`
,
},
{
name
:
"user"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
strPtr
(
"https://harry.potter@example.com/"
),
},
},
expectedError
:
`"harry.potter": user information is not permitted`
,
},
{
name
:
"just totally wrong"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
URL
:
strPtr
(
"arg#backwards=thisis?html.index/port:host//:https"
),
},
},
expectedError
:
`host must be provided`
,
},
{
name
:
"path must start with slash"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"foo/"
),
},
},
},
expectedError
:
`clientConfig.service.path: Invalid value: "foo/": must start with a '/'`
,
},
{
name
:
"path accepts slash"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"/"
),
},
},
},
expectedError
:
``
,
},
{
name
:
"path accepts no trailing slash"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"/foo"
),
},
},
},
expectedError
:
``
,
},
{
name
:
"path fails //"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"//"
),
},
},
},
expectedError
:
`clientConfig.service.path: Invalid value: "//": segment[0] may not be empty`
,
},
{
name
:
"path no empty step"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"/foo//bar/"
),
},
},
},
expectedError
:
`clientConfig.service.path: Invalid value: "/foo//bar/": segment[1] may not be empty`
,
},
{
name
:
"path no empty step 2"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"/foo/bar//"
),
},
},
},
expectedError
:
`clientConfig.service.path: Invalid value: "/foo/bar//": segment[2] may not be empty`
,
},
{
name
:
"path no non-subdomain"
,
config
:
auditregistration
.
Webhook
{
ClientConfig
:
auditregistration
.
WebhookClientConfig
{
Service
:
&
auditregistration
.
ServiceReference
{
Namespace
:
"ns"
,
Name
:
"n"
,
Path
:
strPtr
(
"/apis/foo.bar/v1alpha1/--bad"
),
},
},
},
expectedError
:
`clientConfig.service.path: Invalid value: "/apis/foo.bar/v1alpha1/--bad": segment[3]: a DNS-1123 subdomain`
,
},
}
for
_
,
test
:=
range
tests
{
t
.
Run
(
test
.
name
,
func
(
t
*
testing
.
T
)
{
errs
:=
ValidateWebhook
(
test
.
config
,
field
.
NewPath
(
"webhook"
))
err
:=
errs
.
ToAggregate
()
if
err
!=
nil
{
if
e
,
a
:=
test
.
expectedError
,
err
.
Error
();
!
strings
.
Contains
(
a
,
e
)
||
e
==
""
{
t
.
Errorf
(
"expected to contain
\n
err: %s
\n
got: %s"
,
e
,
a
)
}
}
else
{
if
test
.
expectedError
!=
""
{
t
.
Errorf
(
"unexpected no error, expected to contain %s"
,
test
.
expectedError
)
}
}
})
}
}
pkg/master/import_known_versions.go
View file @
381d0a5d
...
@@ -21,6 +21,7 @@ import (
...
@@ -21,6 +21,7 @@ import (
_
"k8s.io/kubernetes/pkg/apis/admission/install"
_
"k8s.io/kubernetes/pkg/apis/admission/install"
_
"k8s.io/kubernetes/pkg/apis/admissionregistration/install"
_
"k8s.io/kubernetes/pkg/apis/admissionregistration/install"
_
"k8s.io/kubernetes/pkg/apis/apps/install"
_
"k8s.io/kubernetes/pkg/apis/apps/install"
_
"k8s.io/kubernetes/pkg/apis/auditregistration/install"
_
"k8s.io/kubernetes/pkg/apis/authentication/install"
_
"k8s.io/kubernetes/pkg/apis/authentication/install"
_
"k8s.io/kubernetes/pkg/apis/authorization/install"
_
"k8s.io/kubernetes/pkg/apis/authorization/install"
_
"k8s.io/kubernetes/pkg/apis/autoscaling/install"
_
"k8s.io/kubernetes/pkg/apis/autoscaling/install"
...
...
pkg/master/master.go
View file @
381d0a5d
...
@@ -29,6 +29,7 @@ import (
...
@@ -29,6 +29,7 @@ import (
appsv1
"k8s.io/api/apps/v1"
appsv1
"k8s.io/api/apps/v1"
appsv1beta1
"k8s.io/api/apps/v1beta1"
appsv1beta1
"k8s.io/api/apps/v1beta1"
appsv1beta2
"k8s.io/api/apps/v1beta2"
appsv1beta2
"k8s.io/api/apps/v1beta2"
auditregistrationv1alpha1
"k8s.io/api/auditregistration/v1alpha1"
authenticationv1
"k8s.io/api/authentication/v1"
authenticationv1
"k8s.io/api/authentication/v1"
authenticationv1beta1
"k8s.io/api/authentication/v1beta1"
authenticationv1beta1
"k8s.io/api/authentication/v1beta1"
authorizationapiv1
"k8s.io/api/authorization/v1"
authorizationapiv1
"k8s.io/api/authorization/v1"
...
@@ -83,6 +84,7 @@ import (
...
@@ -83,6 +84,7 @@ import (
// RESTStorage installers
// RESTStorage installers
admissionregistrationrest
"k8s.io/kubernetes/pkg/registry/admissionregistration/rest"
admissionregistrationrest
"k8s.io/kubernetes/pkg/registry/admissionregistration/rest"
appsrest
"k8s.io/kubernetes/pkg/registry/apps/rest"
appsrest
"k8s.io/kubernetes/pkg/registry/apps/rest"
auditregistrationrest
"k8s.io/kubernetes/pkg/registry/auditregistration/rest"
authenticationrest
"k8s.io/kubernetes/pkg/registry/authentication/rest"
authenticationrest
"k8s.io/kubernetes/pkg/registry/authentication/rest"
authorizationrest
"k8s.io/kubernetes/pkg/registry/authorization/rest"
authorizationrest
"k8s.io/kubernetes/pkg/registry/authorization/rest"
autoscalingrest
"k8s.io/kubernetes/pkg/registry/autoscaling/rest"
autoscalingrest
"k8s.io/kubernetes/pkg/registry/autoscaling/rest"
...
@@ -346,6 +348,7 @@ func (c completedConfig) New(delegationTarget genericapiserver.DelegationTarget)
...
@@ -346,6 +348,7 @@ func (c completedConfig) New(delegationTarget genericapiserver.DelegationTarget)
// TODO: describe the priority all the way down in the RESTStorageProviders and plumb it back through the various discovery
// TODO: describe the priority all the way down in the RESTStorageProviders and plumb it back through the various discovery
// handlers that we have.
// handlers that we have.
restStorageProviders
:=
[]
RESTStorageProvider
{
restStorageProviders
:=
[]
RESTStorageProvider
{
auditregistrationrest
.
RESTStorageProvider
{},
authenticationrest
.
RESTStorageProvider
{
Authenticator
:
c
.
GenericConfig
.
Authentication
.
Authenticator
},
authenticationrest
.
RESTStorageProvider
{
Authenticator
:
c
.
GenericConfig
.
Authentication
.
Authenticator
},
authorizationrest
.
RESTStorageProvider
{
Authorizer
:
c
.
GenericConfig
.
Authorization
.
Authorizer
,
RuleResolver
:
c
.
GenericConfig
.
RuleResolver
},
authorizationrest
.
RESTStorageProvider
{
Authorizer
:
c
.
GenericConfig
.
Authorization
.
Authorizer
,
RuleResolver
:
c
.
GenericConfig
.
RuleResolver
},
autoscalingrest
.
RESTStorageProvider
{},
autoscalingrest
.
RESTStorageProvider
{},
...
@@ -505,6 +508,7 @@ func DefaultAPIResourceConfigSource() *serverstorage.ResourceConfig {
...
@@ -505,6 +508,7 @@ func DefaultAPIResourceConfigSource() *serverstorage.ResourceConfig {
)
)
// disable alpha versions explicitly so we have a full list of what's possible to serve
// disable alpha versions explicitly so we have a full list of what's possible to serve
ret
.
DisableVersions
(
ret
.
DisableVersions
(
auditregistrationv1alpha1
.
SchemeGroupVersion
,
admissionregistrationv1alpha1
.
SchemeGroupVersion
,
admissionregistrationv1alpha1
.
SchemeGroupVersion
,
batchapiv2alpha1
.
SchemeGroupVersion
,
batchapiv2alpha1
.
SchemeGroupVersion
,
rbacv1alpha1
.
SchemeGroupVersion
,
rbacv1alpha1
.
SchemeGroupVersion
,
...
...
pkg/registry/auditregistration/auditsink/doc.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
auditsink
// import "k8s.io/kubernetes/pkg/registry/auditregistration/auditsink"
pkg/registry/auditregistration/auditsink/storage/storage.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
storage
import
(
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apiserver/pkg/registry/generic"
genericregistry
"k8s.io/apiserver/pkg/registry/generic/registry"
"k8s.io/kubernetes/pkg/apis/auditregistration"
auditstrategy
"k8s.io/kubernetes/pkg/registry/auditregistration/auditsink"
)
// REST implements a RESTStorage for audit sink against etcd
type
REST
struct
{
*
genericregistry
.
Store
}
// NewREST returns a RESTStorage object that will work against audit sinks
func
NewREST
(
optsGetter
generic
.
RESTOptionsGetter
)
*
REST
{
store
:=
&
genericregistry
.
Store
{
NewFunc
:
func
()
runtime
.
Object
{
return
&
auditregistration
.
AuditSink
{}
},
NewListFunc
:
func
()
runtime
.
Object
{
return
&
auditregistration
.
AuditSinkList
{}
},
ObjectNameFunc
:
func
(
obj
runtime
.
Object
)
(
string
,
error
)
{
return
obj
.
(
*
auditregistration
.
AuditSink
)
.
Name
,
nil
},
DefaultQualifiedResource
:
auditregistration
.
Resource
(
"auditsinks"
),
CreateStrategy
:
auditstrategy
.
Strategy
,
UpdateStrategy
:
auditstrategy
.
Strategy
,
DeleteStrategy
:
auditstrategy
.
Strategy
,
}
options
:=
&
generic
.
StoreOptions
{
RESTOptions
:
optsGetter
}
if
err
:=
store
.
CompleteWithOptions
(
options
);
err
!=
nil
{
panic
(
err
)
// TODO: Propagate error up
}
return
&
REST
{
store
}
}
pkg/registry/auditregistration/auditsink/strategy.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
auditsink
import
(
"context"
"reflect"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/util/validation/field"
"k8s.io/apiserver/pkg/storage/names"
"k8s.io/kubernetes/pkg/api/legacyscheme"
audit
"k8s.io/kubernetes/pkg/apis/auditregistration"
"k8s.io/kubernetes/pkg/apis/auditregistration/validation"
)
// auditSinkStrategy implements verification logic for AuditSink.
type
auditSinkStrategy
struct
{
runtime
.
ObjectTyper
names
.
NameGenerator
}
// Strategy is the default logic that applies when creating and updating AuditSink objects.
var
Strategy
=
auditSinkStrategy
{
legacyscheme
.
Scheme
,
names
.
SimpleNameGenerator
}
// NamespaceScoped returns false because all AuditSink's need to be cluster scoped
func
(
auditSinkStrategy
)
NamespaceScoped
()
bool
{
return
false
}
// PrepareForCreate clears the status of an AuditSink before creation.
func
(
auditSinkStrategy
)
PrepareForCreate
(
ctx
context
.
Context
,
obj
runtime
.
Object
)
{
ic
:=
obj
.
(
*
audit
.
AuditSink
)
ic
.
Generation
=
1
}
// PrepareForUpdate clears fields that are not allowed to be set by end users on update.
func
(
auditSinkStrategy
)
PrepareForUpdate
(
ctx
context
.
Context
,
obj
,
old
runtime
.
Object
)
{
newIC
:=
obj
.
(
*
audit
.
AuditSink
)
oldIC
:=
old
.
(
*
audit
.
AuditSink
)
// Any changes to the policy or backend increment the generation number
// See metav1.ObjectMeta description for more information on Generation.
if
!
reflect
.
DeepEqual
(
oldIC
.
Spec
,
newIC
.
Spec
)
{
newIC
.
Generation
=
oldIC
.
Generation
+
1
}
}
// Validate validates a new auditSink.
func
(
auditSinkStrategy
)
Validate
(
ctx
context
.
Context
,
obj
runtime
.
Object
)
field
.
ErrorList
{
ic
:=
obj
.
(
*
audit
.
AuditSink
)
return
validation
.
ValidateAuditSink
(
ic
)
}
// Canonicalize normalizes the object after validation.
func
(
auditSinkStrategy
)
Canonicalize
(
obj
runtime
.
Object
)
{
}
// AllowCreateOnUpdate is true for auditSink; this means you may create one with a PUT request.
func
(
auditSinkStrategy
)
AllowCreateOnUpdate
()
bool
{
return
false
}
// ValidateUpdate is the default update validation for an end user.
func
(
auditSinkStrategy
)
ValidateUpdate
(
ctx
context
.
Context
,
obj
,
old
runtime
.
Object
)
field
.
ErrorList
{
validationErrorList
:=
validation
.
ValidateAuditSink
(
obj
.
(
*
audit
.
AuditSink
))
updateErrorList
:=
validation
.
ValidateAuditSinkUpdate
(
obj
.
(
*
audit
.
AuditSink
),
old
.
(
*
audit
.
AuditSink
))
return
append
(
validationErrorList
,
updateErrorList
...
)
}
// AllowUnconditionalUpdate is the default update policy for auditSink objects. Status update should
// only be allowed if version match.
func
(
auditSinkStrategy
)
AllowUnconditionalUpdate
()
bool
{
return
false
}
pkg/registry/auditregistration/rest/storage_auditregistration.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
rest
import
(
auditv1alpha1
"k8s.io/api/auditregistration/v1alpha1"
"k8s.io/apiserver/pkg/registry/generic"
"k8s.io/apiserver/pkg/registry/rest"
genericapiserver
"k8s.io/apiserver/pkg/server"
serverstorage
"k8s.io/apiserver/pkg/server/storage"
"k8s.io/kubernetes/pkg/api/legacyscheme"
auditstorage
"k8s.io/kubernetes/pkg/registry/auditregistration/auditsink/storage"
)
// RESTStorageProvider is a REST storage provider for audit.k8s.io
type
RESTStorageProvider
struct
{}
// NewRESTStorage returns a RESTStorageProvider
func
(
p
RESTStorageProvider
)
NewRESTStorage
(
apiResourceConfigSource
serverstorage
.
APIResourceConfigSource
,
restOptionsGetter
generic
.
RESTOptionsGetter
)
(
genericapiserver
.
APIGroupInfo
,
bool
)
{
apiGroupInfo
:=
genericapiserver
.
NewDefaultAPIGroupInfo
(
auditv1alpha1
.
GroupName
,
legacyscheme
.
Scheme
,
legacyscheme
.
ParameterCodec
,
legacyscheme
.
Codecs
)
if
apiResourceConfigSource
.
VersionEnabled
(
auditv1alpha1
.
SchemeGroupVersion
)
{
apiGroupInfo
.
VersionedResourcesStorageMap
[
auditv1alpha1
.
SchemeGroupVersion
.
Version
]
=
p
.
v1alpha1Storage
(
apiResourceConfigSource
,
restOptionsGetter
)
}
return
apiGroupInfo
,
true
}
func
(
p
RESTStorageProvider
)
v1alpha1Storage
(
apiResourceConfigSource
serverstorage
.
APIResourceConfigSource
,
restOptionsGetter
generic
.
RESTOptionsGetter
)
map
[
string
]
rest
.
Storage
{
storage
:=
map
[
string
]
rest
.
Storage
{}
s
:=
auditstorage
.
NewREST
(
restOptionsGetter
)
storage
[
"auditsinks"
]
=
s
return
storage
}
// GroupName is the group name for the storage provider
func
(
p
RESTStorageProvider
)
GroupName
()
string
{
return
auditv1alpha1
.
GroupName
}
staging/src/k8s.io/api/auditregistration/OWNERS
0 → 100644
View file @
381d0a5d
reviewers:
- lavalamp
- sttts
- tallclair
- pbarker
\ No newline at end of file
staging/src/k8s.io/api/auditregistration/v1alpha1/doc.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// +k8s:deepcopy-gen=package
// +k8s:openapi-gen=true
// +groupName=auditregistration.k8s.io
package
v1alpha1
// import "k8s.io/api/auditregistration/v1alpha1"
staging/src/k8s.io/api/auditregistration/v1alpha1/register.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
package
v1alpha1
import
(
metav1
"k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/runtime"
"k8s.io/apimachinery/pkg/runtime/schema"
)
// GroupName is the group name use in this package
const
GroupName
=
"auditregistration.k8s.io"
// SchemeGroupVersion is group version used to register these objects
var
SchemeGroupVersion
=
schema
.
GroupVersion
{
Group
:
GroupName
,
Version
:
"v1alpha1"
}
// Resource takes an unqualified resource and returns a Group qualified GroupResource
func
Resource
(
resource
string
)
schema
.
GroupResource
{
return
SchemeGroupVersion
.
WithResource
(
resource
)
.
GroupResource
()
}
var
(
SchemeBuilder
runtime
.
SchemeBuilder
localSchemeBuilder
=
&
SchemeBuilder
AddToScheme
=
localSchemeBuilder
.
AddToScheme
)
func
init
()
{
// We only register manually written functions here. The registration of the
// generated functions takes place in the generated files. The separation
// makes the code compile even when the generated files are missing.
localSchemeBuilder
.
Register
(
addKnownTypes
)
}
func
addKnownTypes
(
scheme
*
runtime
.
Scheme
)
error
{
scheme
.
AddKnownTypes
(
SchemeGroupVersion
,
&
AuditSink
{},
&
AuditSinkList
{},
)
metav1
.
AddToGroupVersion
(
scheme
,
SchemeGroupVersion
)
return
nil
}
staging/src/k8s.io/api/auditregistration/v1alpha1/types.go
0 → 100644
View file @
381d0a5d
/*
Copyright 2018 The Kubernetes Authors.
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at
http://www.apache.org/licenses/LICENSE-2.0
Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/
// +k8s:openapi-gen=true
package
v1alpha1
import
(
metav1
"k8s.io/apimachinery/pkg/apis/meta/v1"
)
// Level defines the amount of information logged during auditing
type
Level
string
// Valid audit levels
const
(
// LevelNone disables auditing
LevelNone
Level
=
"None"
// LevelMetadata provides the basic level of auditing.
LevelMetadata
Level
=
"Metadata"
// LevelRequest provides Metadata level of auditing, and additionally
// logs the request object (does not apply for non-resource requests).
LevelRequest
Level
=
"Request"
// LevelRequestResponse provides Request level of auditing, and additionally
// logs the response object (does not apply for non-resource requests and watches).
LevelRequestResponse
Level
=
"RequestResponse"
)
// Stage defines the stages in request handling during which audit events may be generated.
type
Stage
string
// Valid audit stages.
const
(
// The stage for events generated after the audit handler receives the request, but before it
// is delegated down the handler chain.
StageRequestReceived
=
"RequestReceived"
// The stage for events generated after the response headers are sent, but before the response body
// is sent. This stage is only generated for long-running requests (e.g. watch).
StageResponseStarted
=
"ResponseStarted"
// The stage for events generated after the response body has been completed, and no more bytes
// will be sent.
StageResponseComplete
=
"ResponseComplete"
// The stage for events generated when a panic occurred.
StagePanic
=
"Panic"
)
// +genclient
// +genclient:nonNamespaced
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// AuditSink represents a cluster level audit sink
type
AuditSink
struct
{
metav1
.
TypeMeta
`json:",inline"`
// +optional
metav1
.
ObjectMeta
`json:"metadata,omitempty" protobuf:"bytes,1,opt,name=metadata"`
// Spec defines the audit configuration spec
Spec
AuditSinkSpec
`json:"spec,omitempty" protobuf:"bytes,2,opt,name=spec"`
}
// AuditSinkSpec holds the spec for the audit sink
type
AuditSinkSpec
struct
{
// Policy defines the policy for selecting which events should be sent to the webhook
// required
Policy
Policy
`json:"policy" protobuf:"bytes,1,opt,name=policy"`
// Webhook to send events
// required
Webhook
Webhook
`json:"webhook" protobuf:"bytes,2,opt,name=webhook"`
}
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// AuditSinkList is a list of AuditSink items.
type
AuditSinkList
struct
{
metav1
.
TypeMeta
`json:",inline"`
// +optional
metav1
.
ListMeta
`json:"metadata,omitempty" protobuf:"bytes,1,opt,name=metadata"`
// List of audit configurations.
Items
[]
AuditSink
`json:"items" protobuf:"bytes,2,rep,name=items"`
}
// Policy defines the configuration of how audit events are logged
type
Policy
struct
{
// The Level that all requests are recorded at.
// available options: None, Metadata, Request, RequestResponse
// required
Level
Level
`json:"level" protobuf:"bytes,1,opt,name=level"`
// Stages is a list of stages for which events are created.
// +optional
Stages
[]
Stage
`json:"stages" protobuf:"bytes,2,opt,name=stages"`
}
// Webhook holds the configuration of the webhook
type
Webhook
struct
{
// Throttle holds the options for throttling the webhook
// +optional
Throttle
*
WebhookThrottleConfig
`json:"throttle,omitempty" protobuf:"bytes,1,opt,name=throttle"`
// ClientConfig holds the connection parameters for the webhook
// required
ClientConfig
WebhookClientConfig
`json:"clientConfig" protobuf:"bytes,2,opt,name=clientConfig"`
}
// WebhookThrottleConfig holds the configuration for throttling events
type
WebhookThrottleConfig
struct
{
// ThrottleQPS maximum number of batches per second
// default 10 QPS
// +optional
QPS
*
int64
`json:"qps,omitempty" protobuf:"bytes,1,opt,name=qps"`
// ThrottleBurst is the maximum number of events sent at the same moment
// default 15 QPS
// +optional
Burst
*
int64
`json:"burst,omitempty" protobuf:"bytes,2,opt,name=burst"`
}
// WebhookClientConfig contains the information to make a connection with the webhook
type
WebhookClientConfig
struct
{
// `url` gives the location of the webhook, in standard URL form
// (`[scheme://]host:port/path`). Exactly one of `url` or `service`
// must be specified.
//
// The `host` should not refer to a service running in the cluster; use
// the `service` field instead. The host might be resolved via external
// DNS in some apiservers (e.g., `kube-apiserver` cannot resolve
// in-cluster DNS as that would be a layering violation). `host` may
// also be an IP address.
//
// Please note that using `localhost` or `127.0.0.1` as a `host` is
// risky unless you take great care to run this webhook on all hosts
// which run an apiserver which might need to make calls to this
// webhook. Such installs are likely to be non-portable, i.e., not easy
// to turn up in a new cluster.
//
// The scheme must be "https"; the URL must begin with "https://".
//
// A path is optional, and if present may be any string permissible in
// a URL. You may use the path to pass an arbitrary string to the
// webhook, for example, a cluster identifier.
//
// Attempting to use a user or basic auth e.g. "user:password@" is not
// allowed. Fragments ("#...") and query parameters ("?...") are not
// allowed, either.
//
// +optional
URL
*
string
`json:"url,omitempty" protobuf:"bytes,1,opt,name=url"`
// `service` is a reference to the service for this webhook. Either
// `service` or `url` must be specified.
//
// If the webhook is running within the cluster, then you should use `service`.
//
// Port 443 will be used if it is open, otherwise it is an error.
//
// +optional
Service
*
ServiceReference
`json:"service" protobuf:"bytes,2,opt,name=service"`
// `caBundle` is a PEM encoded CA bundle which will be used to validate
// the webhook's server certificate.
// defaults to the apiservers CA bundle for the endpoint type
// +optional
CABundle
[]
byte
`json:"caBundle" protobuf:"bytes,3,opt,name=caBundle"`
}
// ServiceReference holds a reference to Service.legacy.k8s.io
type
ServiceReference
struct
{
// `namespace` is the namespace of the service.
// Required
Namespace
string
`json:"namespace" protobuf:"bytes,1,opt,name=namespace"`
// `name` is the name of the service.
// Required
Name
string
`json:"name" protobuf:"bytes,2,opt,name=name"`
// `path` is an optional URL path which will be sent in any request to
// this service.
// +optional
Path
*
string
`json:"path,omitempty" protobuf:"bytes,3,opt,name=path"`
}
staging/src/k8s.io/apiserver/pkg/apis/audit/validation/validation.go
View file @
381d0a5d
...
@@ -24,6 +24,7 @@ import (
...
@@ -24,6 +24,7 @@ import (
"k8s.io/apiserver/pkg/apis/audit"
"k8s.io/apiserver/pkg/apis/audit"
)
)
// ValidatePolicy validates the audit policy
func
ValidatePolicy
(
policy
*
audit
.
Policy
)
field
.
ErrorList
{
func
ValidatePolicy
(
policy
*
audit
.
Policy
)
field
.
ErrorList
{
var
allErrs
field
.
ErrorList
var
allErrs
field
.
ErrorList
allErrs
=
append
(
allErrs
,
validateOmitStages
(
policy
.
OmitStages
,
field
.
NewPath
(
"omitStages"
))
...
)
allErrs
=
append
(
allErrs
,
validateOmitStages
(
policy
.
OmitStages
,
field
.
NewPath
(
"omitStages"
))
...
)
...
...
test/integration/apiserver/print_test.go
View file @
381d0a5d
...
@@ -26,6 +26,7 @@ import (
...
@@ -26,6 +26,7 @@ import (
"testing"
"testing"
"time"
"time"
auditregv1alpha1
"k8s.io/api/auditregistration/v1alpha1"
batchv2alpha1
"k8s.io/api/batch/v2alpha1"
batchv2alpha1
"k8s.io/api/batch/v2alpha1"
rbacv1alpha1
"k8s.io/api/rbac/v1alpha1"
rbacv1alpha1
"k8s.io/api/rbac/v1alpha1"
schedulerapi
"k8s.io/api/scheduling/v1beta1"
schedulerapi
"k8s.io/api/scheduling/v1beta1"
...
@@ -130,11 +131,13 @@ var missingHanlders = sets.NewString(
...
@@ -130,11 +131,13 @@ var missingHanlders = sets.NewString(
"VolumeAttachment"
,
"VolumeAttachment"
,
"PriorityClass"
,
"PriorityClass"
,
"PodPreset"
,
"PodPreset"
,
"AuditSink"
,
)
)
func
TestServerSidePrint
(
t
*
testing
.
T
)
{
func
TestServerSidePrint
(
t
*
testing
.
T
)
{
s
,
_
,
closeFn
:=
setup
(
t
,
s
,
_
,
closeFn
:=
setup
(
t
,
// additional groupversions needed for the test to run
// additional groupversions needed for the test to run
auditregv1alpha1
.
SchemeGroupVersion
,
batchv2alpha1
.
SchemeGroupVersion
,
batchv2alpha1
.
SchemeGroupVersion
,
rbacv1alpha1
.
SchemeGroupVersion
,
rbacv1alpha1
.
SchemeGroupVersion
,
settingsv1alpha1
.
SchemeGroupVersion
,
settingsv1alpha1
.
SchemeGroupVersion
,
...
...
test/integration/framework/master_utils.go
View file @
381d0a5d
...
@@ -28,6 +28,7 @@ import (
...
@@ -28,6 +28,7 @@ import (
"github.com/pborman/uuid"
"github.com/pborman/uuid"
apps
"k8s.io/api/apps/v1beta1"
apps
"k8s.io/api/apps/v1beta1"
auditreg
"k8s.io/api/auditregistration/v1alpha1"
autoscaling
"k8s.io/api/autoscaling/v1"
autoscaling
"k8s.io/api/autoscaling/v1"
certificates
"k8s.io/api/certificates/v1beta1"
certificates
"k8s.io/api/certificates/v1beta1"
"k8s.io/api/core/v1"
"k8s.io/api/core/v1"
...
@@ -290,6 +291,10 @@ func NewMasterConfig() *master.Config {
...
@@ -290,6 +291,10 @@ func NewMasterConfig() *master.Config {
schema
.
GroupResource
{
Group
:
storage
.
GroupName
,
Resource
:
serverstorage
.
AllResources
},
schema
.
GroupResource
{
Group
:
storage
.
GroupName
,
Resource
:
serverstorage
.
AllResources
},
""
,
""
,
ns
)
ns
)
storageFactory
.
SetSerializer
(
schema
.
GroupResource
{
Group
:
auditreg
.
GroupName
,
Resource
:
serverstorage
.
AllResources
},
""
,
ns
)
genericConfig
:=
genericapiserver
.
NewConfig
(
legacyscheme
.
Codecs
)
genericConfig
:=
genericapiserver
.
NewConfig
(
legacyscheme
.
Codecs
)
kubeVersion
:=
version
.
Get
()
kubeVersion
:=
version
.
Get
()
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment