-
Notifications
You must be signed in to change notification settings - Fork 4.8k
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
Sds api split #4231
Sds api split #4231
Conversation
Signed-off-by: JimmyCYJ <[email protected]>
Signed-off-by: JimmyCYJ <[email protected]>
source/common/ssl/ssl_socket.cc
Outdated
@@ -17,6 +17,35 @@ using Envoy::Network::PostIoAction; | |||
namespace Envoy { | |||
namespace Ssl { | |||
|
|||
namespace { | |||
// This SslSocket will be used when SSL secret is not fetched from SDS server. | |||
class NotReadySslSocket : public Network::TransportSocket, public Connection { |
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 don't think you need this to be a Ssl::Connection. just inherit TransportSocket is enough.
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.
Done. Thanks.
source/common/secret/sds_api.cc
Outdated
: local_info_(local_info), dispatcher_(dispatcher), random_(random), stats_(stats), | ||
cluster_manager_(cluster_manager), sds_config_(sds_config), sds_config_name_(sds_config_name), | ||
secret_hash_(0), unregister_secret_provider_cb_(unregister_secret_provider) { | ||
// TODO(JimmyCYJ): Implement chained_init_manager, so that multiple init_manager |
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.
Once this is resolved, do we still need NotReadySslSocket?
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.
We still need NotReadySslSocket. Chained init manager guarantees that If two listeners point to the same secret, both listeners would wait for secrets and then listen on port. A better explanation is here. NotReadySslSocket is to solve the issue that if a listener gets secret and listens on a port, but the secret is bad, we should not use the secret to handle connection, and close the connection right away.
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.
Yeah, this is much clearer. Looks good, just some RAII ideas to improve interfaces.
* @param callback callback that is executed by secret provider. | ||
*/ | ||
virtual void addUpdateCallback(SecretCallbacks& callback) PURE; | ||
/** |
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.
Nit: blank line between declaration and comment belonging to next block.
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 blank line.
* Remove secret callback from secret provider. | ||
* @param callback callback that is executed by secret provider. | ||
*/ | ||
virtual void removeUpdateCallback(SecretCallbacks& callback) PURE; |
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.
A general pattern in Envoy is to use RAII for managing removal of callbacks; it's a robust design pattern. We actually have a callback manager that models this today, see https://github.com/envoyproxy/envoy/blob/master/source/common/common/callback_impl.h
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.
Are you looking at this one as well?
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.
Yes, I am working on this one. I will push my update as soon I finish it. Thanks for asking.
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 have added CallbackManager into SdsApi and removed removeUpdateCallback().
In PR #4176, I am going to add Common::CallbackHandle* secret_update_callback_handle_ into ContextConfigImpl as a private member, and modify ContextConfigImpl::setSecretUpdateCallback() like this.
void setSecretUpdateCallback(std::function<()> callback) override {
if (secret_update_callback_handle_) {
secret_update_callback_handle_->remove();
}
secret_update_callback_handle_ = tls_certficate_provider_->addUpdateCallback(callback);
}
I will also modify ~ContextConfigImpl() like this.
ContextConfigImpl::~ContextConfigImpl() {
if (secret_update_callback_handle_) {
secret_update_callback_handle_->remove();
}
}
@@ -8,10 +8,16 @@ load( | |||
|
|||
envoy_package() | |||
|
|||
envoy_cc_library( |
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.
Thanks for splitting this PR out, this is very helpful.
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.
Glad that it helps. Will keep PR in good size.
source/common/secret/sds_api.cc
Outdated
std::function<void()> unregister_secret_provider) | ||
: local_info_(local_info), dispatcher_(dispatcher), random_(random), stats_(stats), | ||
cluster_manager_(cluster_manager), sds_config_(sds_config), sds_config_name_(sds_config_name), | ||
secret_hash_(0), unregister_secret_provider_cb_(unregister_secret_provider) { |
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'm a bit uncomfortable with the naming (and maybe even presence) of unregister_secret_provider_cb
. It should at least be a generic destructor_cb_
, but I would go further. This could be refactored to have SdsApi
completely oblivious to this callback. Instead, the places that have the SdsApi
instances, e.g. in the listener manager, have an object that wraps both SdsApi
and includes a RAII cleanup, e.g. something like https://github.com/envoyproxy/envoy/blob/master/source/common/common/cleanup.h.
I'm not sure exactly how to make this super clean in your use case, but I feel that right now, this is not the right interface. Can you try out some of the above ideas to try and get SdsApi
out of the business of dealing with object lifetimes of its owner?
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 a Cleanup member into SdsApi that holds the destructor_cb, which will be invoked by ~SdsApi(). Thanks for the advice!
test/common/secret/sds_api_test.cc
Outdated
"Unexpected SDS secrets length: 2"); | ||
} | ||
|
||
TEST_F(SdsApiTest, SecretUpdateWrongSecretName) { |
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.
Can you add one liner //
above each test case explaining in simple terms what's happening?
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.
Comments are added above each test case. Thanks.
Signed-off-by: JimmyCYJ <[email protected]>
Signed-off-by: JimmyCYJ <[email protected]>
* Remove secret callback from secret provider. | ||
* @param callback callback that is executed by secret provider. | ||
*/ | ||
virtual void removeUpdateCallback(SecretCallbacks& callback) PURE; |
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.
Are you looking at this one as well?
Runtime::RandomGenerator& random, Stats::Store& stats, | ||
Upstream::ClusterManager& cluster_manager, Init::Manager& init_manager, | ||
const envoy::api::v2::core::ConfigSource& sds_config, std::string sds_config_name, | ||
std::function<void()> destructor_cb) |
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 better than before, thanks. I still think it can be cleaner if instead of having SdsApi
owning the destructor CB, we have the owner of SdsApi
own that object. It's pretty weird threading a destructor CB into an object when the lifetime issues are really those of the owning object.
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.
Thanks for pointing this out. My concern is that SdsApi is held by a shared_ptr (ContextConfigImpland::tls_certficate_provider_) and could be owned by multiple objects (e.g. multiple listeners or clusters). The last owner needs to destroy SdsApi and ~SdsApi() invokes this cleanup function. I am not clear if there is a better place to own the Cleanup object other than SdsApi.
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 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.
Yeah, OK, I still think you could wrap SdsApi
in a SdsApiWithManagedLifetime
object to get the same effect and separate concerns here, but I guess we have precedent for doing it this way.
Signed-off-by: JimmyCYJ <[email protected]>
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.
} | ||
|
||
Common::CallbackHandle* addUpdateCallback(std::function<void()> callback) override { | ||
return update_callback_manager_.add(callback); |
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.
Non-actionable; for some reason I thought this was RAII, but it's just a callback removal handle. We can make that more robust independent of this PR.
Runtime::RandomGenerator& random, Stats::Store& stats, | ||
Upstream::ClusterManager& cluster_manager, Init::Manager& init_manager, | ||
const envoy::api::v2::core::ConfigSource& sds_config, std::string sds_config_name, | ||
std::function<void()> destructor_cb) |
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.
Yeah, OK, I still think you could wrap SdsApi
in a SdsApiWithManagedLifetime
object to get the same effect and separate concerns here, but I guess we have precedent for doing it this way.
Description: Implement SDS API and dummy socket, and they are not in use. This is split from PR #4176.
Risk Level: Low
Testing: Unit tests
Docs Changes: None
Fixes #1194
Signed-off-by: Jimmy Chen [email protected]