Skip to content
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

Wire in WebhookTokenAutenticators support #18868

Merged
merged 2 commits into from
Mar 16, 2018

Conversation

simo5
Copy link
Contributor

@simo5 simo5 commented Mar 6, 2018

This allows to use an external server for Token authentication.

@openshift-ci-robot openshift-ci-robot added the size/M Denotes a PR that changes 30-99 lines, ignoring generated files. label Mar 6, 2018
@simo5 simo5 added do-not-merge/work-in-progress Indicates that a PR should not merge because it is a work in progress. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Mar 6, 2018
@simo5
Copy link
Contributor Author

simo5 commented Mar 6, 2018

@mrogers950 @enj PTAL

@@ -399,6 +399,9 @@ type MasterConfig struct {
EtcdConfig *EtcdConfig
// OAuthConfig, if present start the /oauth endpoint in this process
OAuthConfig *OAuthConfig
// WebhookTokenAuthnConfig, if present configures remote token reviewers
WebhookTokenAuthenticators []WebhookTokenAuthenticators
Copy link
Contributor

Choose a reason for hiding this comment

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

probably belongs under MasterAuthConfig

Copy link
Contributor

Choose a reason for hiding this comment

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

do we have a use case for allowing more than one, or is that just future-proofing?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Maybe seem that it is more similar to OAuthConfig than RequestHeaderAuthenticationOptions as an auth type, why do we not have OAuthConfig under MasterauthConfig ?

Copy link
Contributor

Choose a reason for hiding this comment

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

OAuth component is distinct from the master API. OAuth config is for the OAuth server. MasterAuthConfig is for the API server.

Copy link
Contributor

Choose a reason for hiding this comment

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

Maybe seem that it is more similar to OAuthConfig than RequestHeaderAuthenticationOptions as an auth type

RequestHeaderAuthenticationOptions and WebhookTokenAuthenticators both mirror upstream API authentication configuration options. We should group them under MasterAuthConfig.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Ok, makes sense.

@@ -828,6 +831,15 @@ type DNSConfig struct {
AllowRecursiveQueries bool
}

type WebhookTokenAuthenticators struct {
Copy link
Contributor

Choose a reason for hiding this comment

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

type should be singular if it describes a single authenticator

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Ack

@@ -618,6 +618,7 @@ func defaultOpenAPIConfig(config configapi.MasterConfig) *openapicommon.Config {
},
}
}
// TODO: handle WebhookTokenAuthenticators somehow ?
Copy link
Contributor

Choose a reason for hiding this comment

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

probably just as an additional condition in if len(config.ServiceAccountConfig.PublicKeyFiles) > 0 || ... token webhooks ... {

Copy link
Contributor Author

Choose a reason for hiding this comment

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

yeah I wasn't sure about that I'll do as you suggest

@openshift-ci-robot openshift-ci-robot added the size/M Denotes a PR that changes 30-99 lines, ignoring generated files. label Mar 6, 2018
@openshift-ci-robot openshift-ci-robot added size/L Denotes a PR that changes 100-499 lines, ignoring generated files. and removed size/M Denotes a PR that changes 30-99 lines, ignoring generated files. labels Mar 7, 2018
@simo5
Copy link
Contributor Author

simo5 commented Mar 7, 2018

/retest

enj
enj previously requested changes Mar 7, 2018
WebhookTokenAuthnConfigFile string `json:"webhookTokenAuthnConfigFile"`
// WebhookTokenAuthnCacheTTL indicates how long an authentication result should be cached.
// It takes a valid time duration string (e.g. "5m").
// If empty, you get the default timeout. If zero (e.g. "0m"), caching is disabled
Copy link
Contributor

Choose a reason for hiding this comment

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

Probably should state what the default timeout is (I see no code that does defaulting in this PR).

Copy link
Contributor Author

Choose a reason for hiding this comment

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

There is currently no default, you are required tio state the CacheTTL

Copy link
Contributor

Choose a reason for hiding this comment

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

Upstream defaults this to 2 minutes. @liggitt any preference?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I've added a 10s default

@@ -192,6 +192,24 @@ func ValidateMasterAuthConfig(config configapi.MasterAuthConfig, fldPath *field.
validationResults.AddErrors(field.Required(fldPath.Child("requestHeader.extraHeaderPrefixes"), "must be specified for a secure connection"))
}

for _, wta := range config.WebhookTokenAuthenticators {
Copy link
Contributor

Choose a reason for hiding this comment

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

unit test

Copy link
Contributor Author

Choose a reason for hiding this comment

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

done

@@ -108,6 +109,18 @@ func newAuthenticator(config configapi.MasterConfig, accessTokenGetter oauthclie
group.NewTokenGroupAdder(oauthTokenAuthenticator, []string{bootstrappolicy.AuthenticatedOAuthGroup}))
}

for _, wta := range config.AuthConfig.WebhookTokenAuthenticators {
Copy link
Contributor

Choose a reason for hiding this comment

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

integration test (which I know you are already working on)

@enj enj removed the request for review from csrwng March 7, 2018 17:31
@enj
Copy link
Contributor

enj commented Mar 7, 2018

do we have a use case for allowing more than one, or is that just future-proofing?

@liggitt I specifically asked for this from @simo5. I see no reason not to have it, and I really do not want to try to hack it in later. It is assumed that all such remote token authenticators are allowed to see all tokens - if you do not trust all of them at that level, then you should not put them in your config.

@enj
Copy link
Contributor

enj commented Mar 7, 2018

@openshift/api-review

t.Fatalf("unexpected error: %v", err)
}

// Ex
Copy link
Contributor

Choose a reason for hiding this comment

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

External / Example / or .. ?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

ignore, remnant of my copy/paste from the oidc test

@@ -399,6 +399,7 @@ type MasterConfig struct {
EtcdConfig *EtcdConfig
// OAuthConfig, if present start the /oauth endpoint in this process
OAuthConfig *OAuthConfig

Copy link
Contributor

Choose a reason for hiding this comment

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

unnecessary change

@@ -247,6 +247,7 @@ type MasterConfig struct {
EtcdConfig *EtcdConfig `json:"etcdConfig"`
// OAuthConfig, if present start the /oauth endpoint in this process
OAuthConfig *OAuthConfig `json:"oauthConfig"`

Copy link
Contributor

Choose a reason for hiding this comment

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

same as above

Copy link
Contributor Author

Choose a reason for hiding this comment

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

yeah remamnt of a previous incarnation, will remove, thanks for catching

@simo5 simo5 force-pushed the WebhookEnable branch 3 times, most recently from 5330e97 to b39e082 Compare March 8, 2018 18:41
@simo5 simo5 removed the do-not-merge/work-in-progress Indicates that a PR should not merge because it is a work in progress. label Mar 8, 2018
@simo5
Copy link
Contributor Author

simo5 commented Mar 8, 2018

I think we are ready for final reviews
@mrogers950 @enj @liggitt PTAL

@deads2k
Copy link
Contributor

deads2k commented Mar 9, 2018

api approved.

@simo5 simo5 force-pushed the WebhookEnable branch 2 times, most recently from 13e3e62 to f9af946 Compare March 9, 2018 21:41
enj
enj previously requested changes Mar 13, 2018
}
errors := ValidateMasterAuthConfig(config, nil)
if len(test.expectedErrors) != len(errors.Errors) {
t.Errorf("%s: expected %v errors, got %v", test.testName, test.expectedErrors, errors.Errors)
Copy link
Contributor

Choose a reason for hiding this comment

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

continue after this line or you can panic on the next loop

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Ah, true, but then, the test already failed :-)
Will fix

@@ -215,6 +215,15 @@ func fuzzInternalObject(t *testing.T, forVersion schema.GroupVersion, item runti
}
}

for i := range obj.AuthConfig.WebhookTokenAuthenticators {
if len(obj.AuthConfig.WebhookTokenAuthenticators[i].ConfigFile) == 0 {
continue
Copy link
Contributor

Choose a reason for hiding this comment

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

I don't understand this continue

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Does not default the TTL if there is no file to start with

Copy link
Contributor Author

Choose a reason for hiding this comment

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

(config is already wrong)

Copy link
Contributor

Choose a reason for hiding this comment

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

Sure, but then why do we not want to default? It will just make two errors show up and make the user think that both are required.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

ok removing both

// Set defaults Cache TTLs for external Webhook Token Reviewers
for i := range obj.AuthConfig.WebhookTokenAuthenticators {
if len(obj.AuthConfig.WebhookTokenAuthenticators[i].ConfigFile) == 0 {
continue
Copy link
Contributor

Choose a reason for hiding this comment

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

Same comment

authToken := "Anything-goes!"
authTestUser := "testuser"
authTestUID := "42"
authTestGroups := []string{"testgroup"}
Copy link
Contributor

Choose a reason for hiding this comment

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

TODO masters group

Copy link
Contributor Author

Choose a reason for hiding this comment

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

no need

Copy link
Contributor

Choose a reason for hiding this comment

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

OK

}

// Get master config
masterOptions, err := testserver.DefaultMasterOptions()
Copy link
Contributor

Choose a reason for hiding this comment

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

Move down

Copy link
Contributor Author

Choose a reason for hiding this comment

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

?

Copy link
Contributor

Choose a reason for hiding this comment

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

Just cosmetic for increasing readability since you do not need that variable until later.

// Try to authenticate with a token that can be validated only by our
// external token reviewer
userConfig := &restclient.Config{
Host: clientConfig.Host,
Copy link
Contributor

Choose a reason for hiding this comment

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

Anonymous helper

Copy link
Contributor Author

Choose a reason for hiding this comment

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

?

Copy link
Contributor

Choose a reason for hiding this comment

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

userConfig := AnonymousClientConfig(...)
userConfig.BearerToken = ...

Copy link
Contributor Author

Choose a reason for hiding this comment

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

ok

userWhoamiOptions := cmd.WhoAmIOptions{UserInterface: userClient.Users(), Out: ioutil.Discard}
retrievedUser, err := userWhoamiOptions.WhoAmI()
if err != nil {
t.Errorf("unexpected error: %v", err)
Copy link
Contributor

Choose a reason for hiding this comment

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

Fatal

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Not really needed, other tests do the same

Copy link
Contributor

Choose a reason for hiding this comment

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

Just because other people write their tests incorrectly is not a valid reason to continue doing the wrong thing.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

ooook

masterOptions.AuthConfig.WebhookTokenAuthenticators = []configapi.WebhookTokenAuthenticator{
{
ConfigFile: authConfigFile.Name(),
CacheTTL: "10s",
Copy link
Contributor

Choose a reason for hiding this comment

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

Remove to check defaulting

Copy link
Contributor Author

Choose a reason for hiding this comment

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

defaulting is already checked in uint tests, no need to check it here

Copy link
Contributor

Choose a reason for hiding this comment

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

Hm I guess serialization tests may be enough.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

DEfaulting happens before we override this part of the config anyway, so it wouldn't work :-)

t.Fatalf("unexpected error: %v", err)
}
err = oauthClient.Oauth().OAuthAccessTokens().Delete("XYZ", &metav1.DeleteOptions{})
if !kerrors.IsForbidden(err) {
Copy link
Contributor

Choose a reason for hiding this comment

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

Needs to check for scope error.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Why ?

Copy link
Contributor

Choose a reason for hiding this comment

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

Because we should know we got forbidden via scope and not "the token stopped working for random reason"

@simo5 simo5 dismissed enj’s stale review March 13, 2018 17:10

All requested changes have been addressed

@simo5
Copy link
Contributor Author

simo5 commented Mar 13, 2018

/retest

}
webhookTokenAuthenticator, err := webhooktoken.New(wta.ConfigFile, ttl)
if err != nil {
return nil, nil, fmt.Errorf("Failed to create webhook token authenticator for ConfigFile='%s'", wta.ConfigFile)
Copy link
Contributor

Choose a reason for hiding this comment

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

Include the error that caused the failure:

return nil, nil, fmt.Errorf("Failed to create webhook token authenticator for ConfigFile=%q: %v", wta.ConfigFile, err)

Also replace '%s' with %q on both messages.

@enj
Copy link
Contributor

enj commented Mar 13, 2018

/lgtm
/retest
/refresh

@openshift-ci-robot openshift-ci-robot added the lgtm Indicates that a PR is ready to be merged. label Mar 13, 2018
@openshift-ci-robot
Copy link

[APPROVALNOTIFIER] This PR is APPROVED

This pull-request has been approved by: enj, simo5

The full list of commands accepted by this bot can be found here.

The pull request process is described here

Needs approval from an approver in each of these files:

Approvers can indicate their approval by writing /approve in a comment
Approvers can cancel approval by writing /approve cancel in a comment

@openshift-ci-robot openshift-ci-robot added the approved Indicates a PR has been approved by an approver from all required OWNERS files. label Mar 13, 2018
@simo5
Copy link
Contributor Author

simo5 commented Mar 13, 2018

/refresh

@simo5
Copy link
Contributor Author

simo5 commented Mar 13, 2018

/retest

3 similar comments
@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/retest

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/retest

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/retest

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/test extended_conformance_install

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/retest

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/test extended_networking_minimal

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

/test extended_conformance_install

@simo5
Copy link
Contributor Author

simo5 commented Mar 14, 2018

Flake: #18982

@simo5
Copy link
Contributor Author

simo5 commented Mar 15, 2018

/retest

1 similar comment
@simo5
Copy link
Contributor Author

simo5 commented Mar 16, 2018

/retest

@openshift-merge-robot
Copy link
Contributor

Automatic merge from submit-queue.

@openshift-merge-robot openshift-merge-robot merged commit d78a15c into openshift:master Mar 16, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
api-approved approved Indicates a PR has been approved by an approver from all required OWNERS files. lgtm Indicates that a PR is ready to be merged. needs-api-review size/L Denotes a PR that changes 100-499 lines, ignoring generated files.
Projects
None yet
Development

Successfully merging this pull request may close these issues.

7 participants