-
Notifications
You must be signed in to change notification settings - Fork 4.8k
refactor build interfaces #760
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
d56638c to
c2a804b
Compare
|
[test] |
c14eeb6 to
fda1363
Compare
pkg/build/builder/util.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
godoc? (same for interface below)
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
added
|
The builder package seems like an odd place to put the interfaces, maybe they should go in their own client package? |
pkg/build/builder/util.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So we don't do this for a reason - to make local testability easier. This is kind of going against the conventions we're using in both Kubernetes and Origin.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
having seen what that has wrought, i really disagree with that convention. it has created a nightmare of interfaces that make it really hard to follow what is being implemented, not to mention redundant logic all over the place.
I also don't really see that this reduces local testability, as you can see in the PR i've retained all the existing tests.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Actually Ben's refactor matches upstream conventions, see https://github.com/GoogleCloudPlatform/kubernetes/blob/master/pkg/controller/replication_controller.go#L46-L51. The only problem I can see here, there's too much create build methods we're using.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This interface purpose is to provide external services to the controller. I'd propose moving CreateBuildFromConfig and CreateBuildWithImmutableId methods to the controller, because they contain logic that should be part of the controller. The only interaction with other parts of the system I see there is CreateBuild which is part of that interface and all the rest should happen inside controller IMHO.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Looking more into it, I haven't noticed this interface landed in util.go, sorry. I see a BuildInterface here which should contain create and update methods and the other two methods (CreateBuildFromConfig, CreateBuildWithImmutableId) are just plain util methods, that should not be part of that interface.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@soltysh +1 i think the interfaces should be 'clean'
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
CreateBuildFromConfig and CreateBuildWithImmutableId need to be interfaces somewhere so they can be mocked... I might be inclined to agree that the methods that "just" create the object w/ no other logic should be separated from the more sophisticated paths, though.
|
I'm not in favor of this change given our existing conventions. |
test/integration/buildclient_test.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It would be more effective to implement a "real" implementation of ClientWebhookInterface that wraps a client in webhook.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There's no good reason for "ClientWebhookInterface" to exist, all it did was provide CreateBuild methods, there's nothing unique about that that demands the webhook component have its own version of the interface. Which is why i've removed it and replaced it with the more generic BuildClient interface to be used by things that want to create/manipulate Builds and BuildConfigClient interface for things that want to create/manipulate BuildConfigs
|
I'm leaning towards @smarterclayton idea of not changing what we have here. What I'd propose is to come up with reasonable naming scheme for case such as here. In there we have 3 different interfaces serving similar purpose, they differ only in the resource type they serve. I'd suggest renaming all of them to |
pkg/build/builder/util.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
godoc does not match
594757b to
0c2e8ed
Compare
|
@smarterclayton let me add my next commit reworking the interface definitions before we continue this discussion, i think it will alleviate at least some of your concerns. |
8da4d9b to
520251f
Compare
|
The refactor has been refactored.
|
e74721b to
72e217c
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Again, buildclient.BuilderUpdater would make me feel like you want me to be happy.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
i find it helpful when things are clearly spelled out as being interfaces w/o having to dig into them. it tells me immediately that the implementation might be flexible and i need to consider why and how it changes, and tells me i can potentially change it if needed. Having to jump to the definition to determine that is an extra step.
but again, i'll change it, i'm not that hung up on it, but i do think there are multiple valid schools of thought here.
|
I like this version much better, a few name things and the client stuff left. |
ae42450 to
2beb1ff
Compare
|
Made the final changes in a separate commit, will squash if you're content. |
|
continuous-integration/openshift-jenkins/test SUCCESS (https://ci.openshift.redhat.com/jenkins/job/test_pull_requests_openshift3/898/) |
pkg/cmd/server/origin/master.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Was this change intentional?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
no, global search/replace error.
0fb103a to
cfb5343
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'd propose renaming the file to clients.go, similar to what we have in pkg/client/client.go.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
since there are multiple clients in this file, i think i prefer it as is.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is more of a convention thing. If you have one file in a package, and you want to call the package a certain something, you generally call the only file in the package the same as the package. That's usually the stronger convention.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
so as soon as we add a second file to this package, the name would be ok, right?
|
LGTM 👍 |
|
One small nit, other than that LGTM 🎱 |
cfb5343 to
71c523d
Compare
|
---->squashed<---- |
|
@smarterclayton merge at will. |
pkg/cmd/server/origin/master.go
Outdated
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
If you have BuildControllerClients, why do you need BuildControllerClient?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
because I don't want both and in the interest of your implied pending abstraction of these methods, I didn't think using the method that returned both and then assuming one of the two return values would always be the one i wanted, was the right thing to do.
71c523d to
87233e7
Compare
|
@smarterclayton removed the BuildControllerClient method. |
|
LGTM [merge] |
|
Evaluated for origin up to 87233e7 |
|
continuous-integration/openshift-jenkins/merge SUCCESS (https://ci.openshift.redhat.com/jenkins/job/merge_pull_requests_openshift3/730/) (Image: devenv-fedora_624) |
Merged by openshift-bot
Merged by openshift-bot
Attempting to bring some structure to the build interfaces we had scattered about the code... the intent is to define all the interfaces and the "standard" implementation in the util.go file, define the mock impls in the test cases that use them, and reduce the number of interfaces (rather than having an interface per build operation, have an interface that aggregates all the build operations).
this makes it slightly harder to mock the interface since you have to provide more dummy implementations, but it makes it much easier (imho) to understand the set of interfaces involved in the build process and where they're implemented.