Skip to content

Commit

Permalink
Fix tlsTrustCertsFilePath config is not applied for OAuth2 (#364)
Browse files Browse the repository at this point in the history
### Motivation

#313 has reverted the
fix of #190, which
applies the `tlsTrustCertsFilePath` config for OAuth2 authentication.

The macOS pre-built libraries are affected most because the bundled CA
path is empty.

### Modification

Apply the `tlsTrustCertsFilePath` for OAuth2.
  • Loading branch information
BewareMyPower authored Dec 6, 2023
1 parent 24ab12c commit 27cba3e
Show file tree
Hide file tree
Showing 5 changed files with 47 additions and 5 deletions.
1 change: 1 addition & 0 deletions lib/ClientConfiguration.cc
Original file line number Diff line number Diff line change
Expand Up @@ -19,6 +19,7 @@
#include <stdexcept>

#include "ClientConfigurationImpl.h"
#include "auth/AuthOauth2.h"

namespace pulsar {

Expand Down
12 changes: 10 additions & 2 deletions lib/ClientConnection.cc
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,7 @@
#include "PulsarApi.pb.h"
#include "ResultUtils.h"
#include "Url.h"
#include "auth/AuthOauth2.h"
#include "auth/InitialAuthData.h"
#include "checksum/ChecksumProvider.h"

Expand Down Expand Up @@ -193,6 +194,14 @@ ClientConnection::ClientConnection(const std::string& logicalAddress, const std:
return;
}

auto oauth2Auth = std::dynamic_pointer_cast<AuthOauth2>(authentication_);
if (oauth2Auth) {
// Configure the TLS trust certs file for Oauth2
auto authData = std::dynamic_pointer_cast<AuthenticationDataProvider>(
std::make_shared<InitialAuthData>(clientConfiguration.getTlsTrustCertsFilePath()));
oauth2Auth->getAuthData(authData);
}

if (clientConfiguration.isUseTls()) {
#if BOOST_VERSION >= 105400
boost::asio::ssl::context ctx(boost::asio::ssl::context::tlsv12_client);
Expand Down Expand Up @@ -223,8 +232,7 @@ ClientConnection::ClientConnection(const std::string& logicalAddress, const std:
std::string tlsCertificates = clientConfiguration.getTlsCertificateFilePath();
std::string tlsPrivateKey = clientConfiguration.getTlsPrivateKeyFilePath();

auto authData = std::dynamic_pointer_cast<AuthenticationDataProvider>(
std::make_shared<InitialAuthData>(clientConfiguration.getTlsTrustCertsFilePath()));
AuthenticationDataPtr authData;
if (authentication_->getAuthData(authData) == ResultOk && authData->hasDataForTls()) {
tlsCertificates = authData->getTlsCertificates();
tlsPrivateKey = authData->getTlsPrivateKey();
Expand Down
9 changes: 7 additions & 2 deletions lib/auth/AuthOauth2.cc
Original file line number Diff line number Diff line change
Expand Up @@ -342,8 +342,13 @@ Oauth2TokenResultPtr ClientCredentialFlow::authenticate() {

CurlWrapper::Options options;
options.postFields = std::move(postData);
auto result =
curl.get(tokenEndPoint_, "Content-Type: application/x-www-form-urlencoded", options, nullptr);
std::unique_ptr<CurlWrapper::TlsContext> tlsContext;
if (!tlsTrustCertsFilePath_.empty()) {
tlsContext.reset(new CurlWrapper::TlsContext);
tlsContext->trustCertsFilePath = tlsTrustCertsFilePath_;
}
auto result = curl.get(tokenEndPoint_, "Content-Type: application/x-www-form-urlencoded", options,
tlsContext.get());
if (!result.error.empty()) {
LOG_ERROR("Failed to get the well-known configuration " << issuerUrl_ << ": " << result.error);
return resultPtr;
Expand Down
9 changes: 8 additions & 1 deletion run-unit-tests.sh
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,14 @@ docker compose -f tests/oauth2/docker-compose.yml up -d
# Wait until the namespace is created, currently there is no good way to check it
# because it's hard to configure OAuth2 authentication via CLI.
sleep 15
$CMAKE_BUILD_DIRECTORY/tests/Oauth2Test
$CMAKE_BUILD_DIRECTORY/tests/Oauth2Test --gtest_filter='-*testTlsTrustFilePath'
if [[ -f /etc/ssl/certs/ca-certificates.crt ]]; then
sudo mv /etc/ssl/certs/ca-certificates.crt /etc/ssl/certs/my-cert.crt
fi
$CMAKE_BUILD_DIRECTORY/tests/Oauth2Test --gtest_filter='*testTlsTrustFilePath'
if [[ -f /etc/ssl/certs/my-cert.crt ]]; then
sudo mv /etc/ssl/certs/my-cert.crt /etc/ssl/certs/ca-certificates.crt
fi
docker compose -f tests/oauth2/docker-compose.yml down

# Run BrokerMetadata tests
Expand Down
21 changes: 21 additions & 0 deletions tests/oauth2/Oauth2Test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@

#include <boost/property_tree/json_parser.hpp>
#include <boost/property_tree/ptree.hpp>
#include <fstream>

#include "lib/Base64Utils.h"

Expand Down Expand Up @@ -64,6 +65,26 @@ TEST(Oauth2Test, testWrongUrl) {
ASSERT_EQ(ResultAuthenticationError, testCreateProducer("my-protocol:" + gKeyPath));
}

TEST(Oauth2Test, testTlsTrustFilePath) {
const auto caPath = "/etc/ssl/certs/my-cert.crt";
std::ifstream fin{caPath};
if (!fin) { // Skip this test if the CA cert is not prepared
return;
}
fin.close();

ClientConfiguration conf;
conf.setTlsTrustCertsFilePath(caPath);
auto params = gCommonParams;
params["private_key"] = "file://" + gKeyPath;
conf.setAuth(AuthOauth2::create(params));

Client client{"pulsar://localhost:6650", conf};
Producer producer;
ASSERT_EQ(ResultOk, client.createProducer("oauth2-test", producer));
client.close();
}

int main(int argc, char* argv[]) {
std::cout << "Load Oauth2 configs from " << gKeyPath << "..." << std::endl;
boost::property_tree::ptree root;
Expand Down

0 comments on commit 27cba3e

Please sign in to comment.