Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions cmd/controller/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ import (
"github.com/knative/eventing/pkg/controller/bind"
"github.com/knative/eventing/pkg/controller/bus"
"github.com/knative/eventing/pkg/controller/channel"
"github.com/knative/eventing/pkg/controller/clusterbus"
"github.com/knative/eventing/pkg/signals"

"github.com/prometheus/client_golang/prometheus/promhttp"
Expand Down Expand Up @@ -88,6 +89,7 @@ func main() {
ctors := []controller.Constructor{
bind.NewController,
bus.NewController,
clusterbus.NewController,
channel.NewController,
}

Expand Down
25 changes: 25 additions & 0 deletions config/clusterbus.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
# Copyright 2018 The Knative 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.
apiVersion: apiextensions.k8s.io/v1beta1
kind: CustomResourceDefinition
metadata:
name: clusterbuses.channels.knative.dev
spec:
scope: Cluster
group: channels.knative.dev
version: v1alpha1
names:
kind: ClusterBus
plural: clusterbuses
singular: clusterbus
2 changes: 1 addition & 1 deletion config/clusterrole.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ metadata:
name: knative-channels-bus
rules:
- apiGroups: ["channels.knative.dev"]
resources: ["buses", "channels", "subscriptions"]
resources: ["buses", "clusterbuses", "channels", "subscriptions"]
verbs: ["get", "watch", "list"]
- apiGroups: [""]
resources: ["events"]
Expand Down
14 changes: 14 additions & 0 deletions config/clusterrolebinding.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -23,3 +23,17 @@ roleRef:
kind: ClusterRole
name: cluster-admin
apiGroup: rbac.authorization.k8s.io

---
apiVersion: rbac.authorization.k8s.io/v1beta1
kind: ClusterRoleBinding
metadata:
name: clusterbus-controller-manage
subjects:
- kind: ServiceAccount
name: clusterbus-controller
namespace: knative-eventing
roleRef:
kind: ClusterRole
name: knative-channels-bus
apiGroup: rbac.authorization.k8s.io
7 changes: 7 additions & 0 deletions config/serviceaccount.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -16,3 +16,10 @@ kind: ServiceAccount
metadata:
name: bind-controller
namespace: knative-eventing

---
apiVersion: v1
kind: ServiceAccount
metadata:
name: clusterbus-controller
namespace: knative-eventing
21 changes: 19 additions & 2 deletions pkg/apis/channels/v1alpha1/bus_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ import (

kapi "k8s.io/api/core/v1"
meta_v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
runtime "k8s.io/apimachinery/pkg/runtime"
)

// +genclient
Expand All @@ -32,8 +33,8 @@ import (
type Bus struct {
meta_v1.TypeMeta `json:",inline"`
meta_v1.ObjectMeta `json:"metadata"`
Spec BusSpec `json:"spec"`
Status *BusStatus `json:"status,omitempty"`
Spec BusSpec `json:"spec"`
Status BusStatus `json:"status,omitempty"`
}

// BusSpec (what the user wants) for a bus
Expand Down Expand Up @@ -66,6 +67,14 @@ type BusParameters struct {
type BusStatus struct {
}

func (b *Bus) BacksChannel(channel *Channel) bool {
return b.Namespace == channel.Namespace && b.Name == channel.Spec.Bus
}

func (b *Bus) GetSpec() *BusSpec {
return &b.Spec
}

func (b *Bus) GetSpecJSON() ([]byte, error) {
return json.Marshal(b.Spec)
}
Expand All @@ -78,3 +87,11 @@ type BusList struct {
meta_v1.ListMeta `json:"metadata"`
Items []Bus `json:"items"`
}

// GenericBus may be backed by Bus or ClusterBus
type GenericBus interface {
Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@pmorie do you have a better pattern for working with cluster and namespaced resources in a similar way?

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

If their specs are going to be the exact same, this seems better than what I've had to do in the past :)

runtime.Object
meta_v1.ObjectMetaAccessor
BacksChannel(channel *Channel) bool
GetSpec() *BusSpec
}
11 changes: 7 additions & 4 deletions pkg/apis/channels/v1alpha1/channel_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,15 +31,18 @@ import (
type Channel struct {
meta_v1.TypeMeta `json:",inline"`
meta_v1.ObjectMeta `json:"metadata"`
Spec ChannelSpec `json:"spec"`
Status *ChannelStatus `json:"status,omitempty"`
Spec ChannelSpec `json:"spec"`
Status ChannelStatus `json:"status,omitempty"`
}

// ChannelSpec (what the user wants) for a channel
type ChannelSpec struct {

// Name of the bus backing this channel (optional)
Bus string `json:"bus`
// Bus name of the bus backing this channel (mutually exclusive with ClusterBus)
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wonder if it would be cleaner to always include the namespace for the bus in the channel and remove clusterBus here.

Or add a busNamespace property to signal which namespace we are referring to.

I have seen this clusterFoo and Foo pattern before and I have always felt like it complicates the understanding of the object over the wire...

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

In my understanding, a ClusterBus is not the same thing as a (namespaced) Bus in a namespace different from the channel namespace. At least in usage intention.

It is a Bus that is widely available for anyone to use

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't think there's a good way to use the lack of an explicit namespace to mean cluster scoped. Users are not used to having to explicitly state the namespace - this will complicate templates/charts/etc. I would expect a name with no explicit namespace to mean 'my namespace', not cluster scope.

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I agree with @pmorie here.

The alternative implementation would be to do something like:

spec:
  bus:
    type: cluster
    name: pubsub

The trade off is a single field in config that is set, and the user has to know which field to use, or two nested fields that both must be set. I don't have a strong opinion as to which model is best.

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

oh nice, I like this idea ^, it gets us closer to label selector style syntax.

I could be alone, but it bothers me when there are mutually exclusive fields

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

should type be scope? could it be a boolean (cluster-scoped), and should it have a default value?

Copy link
Copy Markdown
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

scope is better than type. Not crazy about using a boolean, but we could certainly make either namespace or cluster the default.

I'm willing to go with the group consensus here.

Bus string `json:"bus"`

// ClusterBus name of the clusterbus backing this channel (mutually exclusive with Bus)
ClusterBus string `json:"clusterBus"`

// Arguments configuration arguments for the channel
Arguments *[]Argument `json:"arguments,omitempty"`
Expand Down
65 changes: 65 additions & 0 deletions pkg/apis/channels/v1alpha1/clusterbus_types.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
/*
* Copyright 2018 The Knative 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 (
"encoding/json"

meta_v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
)

// +genclient
// +genclient:noStatus
// +genclient:nonNamespaced
// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object
// +k8s:defaulter-gen=true

// ClusterBus represents the clusterbuses.channels.knative.dev CRD
type ClusterBus struct {
meta_v1.TypeMeta `json:",inline"`
meta_v1.ObjectMeta `json:"metadata"`
Spec ClusterBusSpec `json:"spec"`
Status ClusterBusStatus `json:"status,omitempty"`
}

// ClusterBusSpec (what the user wants) for a clusterbus
type ClusterBusSpec = BusSpec

// ClusterBusStatus (computed) for a clusterbus
type ClusterBusStatus struct {
}

func (b *ClusterBus) BacksChannel(channel *Channel) bool {
return len(b.Namespace) == 0 && b.Name == channel.Spec.ClusterBus
}

func (b *ClusterBus) GetSpec() *BusSpec {
return &b.Spec
}

func (b *ClusterBus) GetSpecJSON() ([]byte, error) {
return json.Marshal(b.Spec)
}

// +k8s:deepcopy-gen:interfaces=k8s.io/apimachinery/pkg/runtime.Object

// ClusterBusList returned in list operations
type ClusterBusList struct {
meta_v1.TypeMeta `json:",inline"`
meta_v1.ListMeta `json:"metadata"`
Items []ClusterBus `json:"items"`
}
2 changes: 2 additions & 0 deletions pkg/apis/channels/v1alpha1/register.go
Original file line number Diff line number Diff line change
Expand Up @@ -47,6 +47,8 @@ func addKnownTypes(scheme *runtime.Scheme) error {
scheme.AddKnownTypes(SchemeGroupVersion,
&Bus{},
&BusList{},
&ClusterBus{},
&ClusterBusList{},
&Channel{},
&ChannelList{},
&Subscription{},
Expand Down
4 changes: 2 additions & 2 deletions pkg/apis/channels/v1alpha1/subscription_types.go
Original file line number Diff line number Diff line change
Expand Up @@ -31,8 +31,8 @@ import (
type Subscription struct {
meta_v1.TypeMeta `json:",inline"`
meta_v1.ObjectMeta `json:"metadata"`
Spec SubscriptionSpec `json:"spec"`
Status *SubscriptionStatus `json:"status,omitempty"`
Spec SubscriptionSpec `json:"spec"`
Status SubscriptionStatus `json:"status,omitempty"`
}

// SubscriptionSpec (what the user wants) for a subscription
Expand Down
107 changes: 80 additions & 27 deletions pkg/apis/channels/v1alpha1/zz_generated.deepcopy.go

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

Loading