-
Notifications
You must be signed in to change notification settings - Fork 11
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
Add startup logic to enable Push-to-File #377
Conversation
c314d85
to
ed71869
Compare
168e04b
to
d6719a8
Compare
if _, err := os.Stat(annotationsFile); err == nil { | ||
annotationsMap, err = annotations.NewAnnotationsFromFile(annotationsFile) | ||
// Only attempt to populate from annotations if the annotations file exists | ||
// TODO: Figure out strategy for dealing with explicit annotation file path |
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.
Why would the annotation file path be anything other than /conjur/podinfo
? I don't think it makes sense that the file path would be user configurable...
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 comment is actually from #367 by @doodlesbykumbi. GH did a weird auto-rebase on my branch, but I've corrected it since.
I think I would agree with you here, though. The location of the annotations file seems like an internal detail rather than something the user should be concerned with. I feel differently about a configurable secrets file base path, though.
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.
Both of the fixed paths /conjur/podinfo
and the /conjur/secrets
are from the perspective of the Secrets Provider container only. For the application container, the user can mount the corresponding volumes at any arbitrary mountPath
s (though they might not care about the podinfo volume).
We intentionally left out "config knobs" for these SP mountPaths
to simplify the user experience and so that we have two less things that can get misconfigured.
With that in mind, we can probably change defaultAnnotationsFile
back to annotationsFile
, and defaultSecretBasePath
to secretBasePath
.
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.
My motivation for making these values configurable is for
- For testing purposes we should be able to specify arbitrary mouth paths.
- Potentially supporting dry run capabilities. I acknowledge this as a nice-to-have, and something that might require a separate dedicated discussion.
We don't have to expose these as config knobs to the user, but I think the hardcoded value should only be present in ./main.go
.
I opted for defaultAnnotationsFile
vs annotationsFile
to specifically call out the fact that this is the default, but perhaps that causes some confusion due to the word "default" implying that there are other options. Perhaps a better name would be fixedAnnotationsFilePath
.
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.
Changed to annotationsFilePath
and secretBasePath
. When they're made "configurable" in the context of testing/dry run, then we can change it to something more suitable.
ed71869
to
ff3e2bf
Compare
provideConjurSecretFunc = k8s_secrets_storage.ProvideConjurSecretsToK8sSecrets | ||
// NewProviderForType returns a ProviderFunc responsible for retrieving and providing secrets in a given StoreType mode. | ||
func NewProviderForType( | ||
retrievek8sSecret k8s.RetrieveK8sSecretFunc, |
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.
Function NewProviderForType
has 7 arguments (exceeds 4 allowed). Consider refactoring.
|
||
// NewProvider creates a new secret provider for K8s Secrets mode. | ||
func NewProvider( | ||
retrievek8sSecret k8s.RetrieveK8sSecretFunc, |
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.
Function NewProvider
has 5 arguments (exceeds 4 allowed). Consider refactoring.
ff3e2bf
to
3c577a7
Compare
8ec6f5b
to
de875b2
Compare
} | ||
|
||
// Provide implements a ProviderFunc to retrieve and push secrets to K8s secrets. | ||
func (p k8sProvider) Provide() error { |
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.
Method k8sProvider.Provide
has 6 return statements (exceeds 4 allowed).
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.
Looks good!!! Nice work on the provider retry wrapper, and on adding testability for the retry mechanism!
if _, err := os.Stat(annotationsFile); err == nil { | ||
annotationsMap, err = annotations.NewAnnotationsFromFile(annotationsFile) | ||
// Only attempt to populate from annotations if the annotations file exists | ||
// TODO: Figure out strategy for dealing with explicit annotation file path |
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.
Both of the fixed paths /conjur/podinfo
and the /conjur/secrets
are from the perspective of the Secrets Provider container only. For the application container, the user can mount the corresponding volumes at any arbitrary mountPath
s (though they might not care about the podinfo volume).
We intentionally left out "config knobs" for these SP mountPaths
to simplify the user experience and so that we have two less things that can get misconfigured.
With that in mind, we can probably change defaultAnnotationsFile
back to annotationsFile
, and defaultSecretBasePath
to secretBasePath
.
cmd/secrets-provider/main.go
Outdated
secretsConfig := setupSecretsConfig() | ||
|
||
provideConjurSecrets, err := secrets.GetProvideConjurSecretFunc(secretsConfig.StoreType) | ||
// Initialize a Conjur Secret Fetcher | ||
secretRetriver, err := conjur.NewConjurSecretRetriever(*authnConfig) |
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.
Typo: secretRetriver
should be secretRetriever
.
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.
Fixed
) | ||
logErrorsAndConditionalExit(errs, nil, messages.CSPFK053E) | ||
|
||
provideSecrets = secrets.RetryableSecretProvider( |
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.
Nice, I like the RetryableSecretProvider(...)
wrapper!
return nil, log.RecordedError(messages.CSPFK010E) | ||
} | ||
|
||
// NOTE: the token is cleanup up by whoever created it! |
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.
Should be "the token is cleaned up"?
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.
Removed this comment entirely - seems repetitive given the comment a few lines later:
// Always delete the access token. The deletion is idempotent and never fails
defer authn.AccessToken.Delete()
if err != nil { | ||
return nil, log.RecordedError(messages.CSPFK002E) | ||
} | ||
// Always delete the access token. The deletion idempotent and never fails |
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.
Should be "The deletion is idempotent"?
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.
Fixed
@@ -74,3 +74,6 @@ const CSPFK049E string = "CSPFK049E Failed to validate Pod annotations" | |||
const CSPFK050E string = "CSPFK050E Failed to unmarshal Push-to-File secrets. Reason: %s" | |||
const CSPFK051E string = "CSPFK051E Unknown file format '%s'" | |||
const CSPFK052E string = "CSPFK052E Failed to retrieve secrets. Reason: %s" | |||
|
|||
const CSPFK053E string = "CSPFK053E Unable to initialize Secrets Provider: unable to create secret group collection" |
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.
Oh-oh, I used the same CSPFK053E
error code. Looks like we're going to need to arm wrestle for it.
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.
Branching thought off of this...
This file has all error messages numbered sequentially, but it also has them loosely grouped by area of concern, separated by comments, ie. // General
, // Push to File
, etc.
I've added CSPFK054E
, which arises when SP fails for a bad StoreType
- which is more of a // General
failure. Moving this error to the // General
section would require changing the identifiers for every error message declared afterwords. Updating the numbering style might help the error messages to be more extensible and static through future changes.
I think if the messages here are to be grouped by area of concern, then maybe they should be numbered within their area of concern:
const CSPFK-A001E string = "first message concerned with aspect A"
const CSPFK-A002E string = "second message concerned with aspect A"
const CSPFK-B001E string = "first message concerned with aspect B"
This also might help to avoid collisions like this one! (EDIT: not this one exactly, because we're both adding to the same concern group w/ 053E
, but similar cases)
|
||
for _, tc := range TestCases { | ||
var logBuffer bytes.Buffer | ||
logger.InfoLogger = log.New(&logBuffer, "", 0) |
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.
logger.InfoLogger
is a global, exported variable for the authn-k8s-client log package. So if we ever run tests in parallel, I think we could have multiple tests contending for this global setting?
At some point, we'll probably want to revisit how this is done in the conjur-authn-client log package... maybe have it return the info logger to the entity that's using the log package, rather than storing the info logger is as a global, exported variable?
ProviderFunc will represent ambiguously present a func which is responsible for prividing secrets, either to K8s Secrets or to Files depending on configuration.
015eb46
to
f2d66a1
Compare
f2d66a1
to
bc9fffa
Compare
Code Climate has analyzed commit bc9fffa and detected 3 issues on this pull request. Here's the issue category breakdown:
The test coverage on the diff in this pull request is 63.1% (50% is the threshold). This pull request will bring the total coverage in the repository to 87.6% (-1.6% change). View more on Code Climate. |
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.
LGTM!
Thanks for the final push in getting us across the E2E goal line!
I think we should merge this as is, and handle these with separate, smaller PRs:
- Issue with having to specify full secret file path
- Code Climate issues
I can work on the CC issues if you'd like... your choice.
What does this PR do?
type ProviderFunc func() error
func NewProviderForType(...) (ProviderFunc, []error)
ProviderFunc
given SP configurationfunc RetryableSecretProvider(...) ProviderFunc
ProviderFunc
in alimitedBackOff
regulated Retry loopProviderFunc
typek8s_secrets_storage
andpushtofile
packagesNewProvider(...)
defines dependencies required by each processProvide()
method which Implements theProviderFunc
typeconjur
packagemain.go
What ticket does this PR close?
ONYX-12537
Checklists
Change log
Test coverage
Documentation
README
s) were updated in this PR, and/or there is a follow-on issue to update docs, or