Skip to content
This repository was archived by the owner on Aug 30, 2022. It is now read-only.

Commit 567c23b

Browse files
rnburnisaachier
authored andcommitted
Add support for dynamic loading. (#64)
1 parent 30f7796 commit 567c23b

File tree

8 files changed

+362
-9
lines changed

8 files changed

+362
-9
lines changed

CMakeLists.txt

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -142,6 +142,8 @@ set(SRC
142142
src/jaegertracing/Tag.cpp
143143
src/jaegertracing/TraceID.cpp
144144
src/jaegertracing/Tracer.cpp
145+
src/jaegertracing/TracerFactory.cpp
146+
src/jaegertracing/DynamicLoad.cpp
145147
src/jaegertracing/Transport.cpp
146148
src/jaegertracing/UDPTransport.cpp
147149
src/jaegertracing/baggage/BaggageSetter.cpp
@@ -259,6 +261,8 @@ if(BUILD_TESTING)
259261
src/jaegertracing/TagTest.cpp
260262
src/jaegertracing/TraceIDTest.cpp
261263
src/jaegertracing/TracerTest.cpp
264+
src/jaegertracing/TracerFactoryTest.cpp
265+
src/jaegertracing/DynamicLoadTest.cpp
262266
src/jaegertracing/UDPTransportTest.cpp
263267
src/jaegertracing/baggage/BaggageTest.cpp
264268
src/jaegertracing/metrics/MetricsTest.cpp
@@ -283,8 +287,14 @@ if(BUILD_TESTING)
283287
GTEST_HAS_TR1_TUPLE=0
284288
GTEST_USE_OWN_TR1_TUPLE=0)
285289
target_link_libraries(
286-
UnitTest testutils GTest::main jaegertracing-static ${LIBS})
290+
UnitTest testutils GTest::main jaegertracing ${LIBS})
287291
add_test(NAME UnitTest COMMAND UnitTest)
292+
293+
add_executable(DynamicallyLoadTracerTest src/jaegertracing/DynamicallyLoadTracerTest.cpp)
294+
target_link_libraries(
295+
DynamicallyLoadTracerTest OpenTracing::opentracing-static)
296+
add_test(NAME DynamicallyLoadTracerTest COMMAND DynamicallyLoadTracerTest
297+
${CMAKE_CURRENT_BINARY_DIR}/${CMAKE_SHARED_LIBRARY_PREFIX}jaegertracing${CMAKE_SHARED_LIBRARY_SUFFIX})
288298
if(JAEGERTRACING_COVERAGE)
289299
setup_target_for_coverage(NAME UnitTestCoverage
290300
EXECUTABLE UnitTest

src/jaegertracing/DynamicLoad.cpp

Lines changed: 49 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,49 @@
1+
/*
2+
* Copyright (c) 2018 Uber Technologies, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
#include <cassert>
17+
#include <cstring>
18+
#include <system_error>
19+
20+
#include <opentracing/dynamic_load.h>
21+
22+
#include "TracerFactory.h"
23+
#include "jaegertracing/Tracer.h"
24+
25+
int OpenTracingMakeTracerFactory(const char* opentracingVersion,
26+
const void** errorCategory,
27+
void** tracerFactory)
28+
{
29+
assert(errorCategory != nullptr);
30+
assert(tracerFactory != nullptr);
31+
#ifndef JAEGERTRACING_WITH_YAML_CPP
32+
*errorCategory =
33+
static_cast<const void*>(&opentracing::dynamic_load_error_category());
34+
return opentracing::dynamic_load_not_supported_error.value();
35+
#endif
36+
if (std::strcmp(opentracingVersion, OPENTRACING_VERSION) != 0) {
37+
*errorCategory = static_cast<const void*>(
38+
&opentracing::dynamic_load_error_category());
39+
return opentracing::incompatible_library_versions_error.value();
40+
}
41+
42+
*tracerFactory = new (std::nothrow) jaegertracing::TracerFactory{};
43+
if (*tracerFactory == nullptr) {
44+
*errorCategory = static_cast<const void*>(&std::generic_category());
45+
return static_cast<int>(std::errc::not_enough_memory);
46+
}
47+
48+
return 0;
49+
}
Lines changed: 59 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,59 @@
1+
/*
2+
* Copyright (c) 2018 Uber Technologies, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
#include <iostream>
17+
#include <string>
18+
19+
#include "jaegertracing/Constants.h"
20+
#include <gtest/gtest.h>
21+
#include <opentracing/dynamic_load.h>
22+
23+
namespace jaegertracing {
24+
#ifdef JAEGERTRACING_WITH_YAML_CPP
25+
TEST(DynamicLoad, invalidVersion)
26+
{
27+
const void* errorCategory = nullptr;
28+
void* tracerFactory = nullptr;
29+
const auto rcode = OpenTracingMakeTracerFactory(
30+
"1.0.0" /*invalid version*/, &errorCategory, &tracerFactory);
31+
ASSERT_EQ(rcode, opentracing::incompatible_library_versions_error.value());
32+
ASSERT_EQ(
33+
errorCategory,
34+
static_cast<const void*>(&opentracing::dynamic_load_error_category()));
35+
ASSERT_EQ(tracerFactory, nullptr);
36+
}
37+
38+
TEST(DynamicLoad, validVersion)
39+
{
40+
const void* errorCategory = nullptr;
41+
void* tracerFactory = nullptr;
42+
const auto rcode = OpenTracingMakeTracerFactory(
43+
OPENTRACING_VERSION, &errorCategory, &tracerFactory);
44+
ASSERT_EQ(rcode, 0);
45+
ASSERT_EQ(errorCategory, nullptr);
46+
ASSERT_NE(tracerFactory, nullptr);
47+
delete static_cast<opentracing::TracerFactory*>(tracerFactory);
48+
}
49+
#else
50+
TEST(DynamicLoad, noYAML)
51+
{
52+
const void* errorCategory = nullptr;
53+
void* tracerFactory = nullptr;
54+
const auto rcode = OpenTracingMakeTracerFactory(
55+
OPENTRACING_VERSION, &errorCategory, &tracerFactory);
56+
ASSERT_NE(rcode, 0);
57+
}
58+
#endif // JAEGERTRACING_WITH_YAML_CPP
59+
} // namespace jaegertracing
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/*
2+
* Copyright (c) 2018 Uber Technologies, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
#include <iostream>
17+
#include <string>
18+
19+
#include <opentracing/dynamic_load.h>
20+
21+
// Verify that Jaeger's shared library can be dynamically loaded and used
22+
// as a plugin.
23+
int main(int argc, char* argv[])
24+
{
25+
if (argc != 2) {
26+
std::cerr << "DynamicLoadTest <tracer-library>\n";
27+
return -1;
28+
}
29+
const char* library = argv[1];
30+
std::string errorMessage;
31+
auto tracerFactoryMaybe =
32+
opentracing::DynamicallyLoadTracingLibrary(library, errorMessage);
33+
#ifdef JAEGERTRACING_WITH_YAML_CPP
34+
if (!errorMessage.empty()) {
35+
std::cerr << "Failed to load tracing tracer: " << errorMessage << "\n";
36+
return -1;
37+
}
38+
if (!tracerFactoryMaybe) {
39+
std::cerr << "Failed to load tracing library: "
40+
<< tracerFactoryMaybe.error().message() << "\n";
41+
return -1;
42+
}
43+
#else
44+
if (tracerFactoryMaybe) {
45+
std::cerr << "Dynamically loading a tracing library should fail "
46+
"without YAML support\n";
47+
return -1;
48+
}
49+
#endif // JAEGERTRACING_WITH_YAML_CPP
50+
return 0;
51+
}
Lines changed: 65 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,65 @@
1+
/*
2+
* Copyright (c) 2018 Uber Technologies, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
#include "TracerFactory.h"
18+
19+
#include "jaegertracing/Tracer.h"
20+
21+
namespace jaegertracing {
22+
23+
opentracing::expected<std::shared_ptr<opentracing::Tracer>>
24+
TracerFactory::MakeTracer(const char* configuration,
25+
std::string& errorMessage) const noexcept try {
26+
#ifndef JAEGERTRACING_WITH_YAML_CPP
27+
errorMessage =
28+
"Failed to construct tracer: Jaeger was not build with yaml support.";
29+
return opentracing::make_unexpected(
30+
std::make_error_code(std::errc::not_supported));
31+
#else
32+
YAML::Node yaml;
33+
try {
34+
yaml = YAML::Load(configuration);
35+
} catch (const YAML::ParserException& e) {
36+
errorMessage = e.what();
37+
return opentracing::make_unexpected(
38+
opentracing::configuration_parse_error);
39+
}
40+
41+
const auto serviceNameNode = yaml["service_name"];
42+
if (!serviceNameNode) {
43+
errorMessage = "`service_name` not provided";
44+
return opentracing::make_unexpected(
45+
opentracing::invalid_configuration_error);
46+
}
47+
if (!serviceNameNode.IsScalar()) {
48+
errorMessage = "`service_name` must be a string";
49+
return opentracing::make_unexpected(
50+
opentracing::invalid_configuration_error);
51+
}
52+
std::string serviceName = serviceNameNode.Scalar();
53+
54+
const auto tracerConfig = jaegertracing::Config::parse(yaml);
55+
return jaegertracing::Tracer::make(serviceName, tracerConfig);
56+
#endif // JAEGERTRACING_WITH_YAML_CPP
57+
} catch (const std::bad_alloc&) {
58+
return opentracing::make_unexpected(
59+
std::make_error_code(std::errc::not_enough_memory));
60+
} catch (const std::exception& e) {
61+
errorMessage = e.what();
62+
return opentracing::make_unexpected(
63+
opentracing::invalid_configuration_error);
64+
}
65+
} // namespace jaegertracing

src/jaegertracing/TracerFactory.h

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
/*
2+
* Copyright (c) 2018 Uber Technologies, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
#ifndef JAEGERTRACING_TRACER_FACTORY_H
18+
#define JAEGERTRACING_TRACER_FACTORY_H
19+
20+
#include <opentracing/tracer_factory.h>
21+
22+
namespace jaegertracing {
23+
24+
class TracerFactory : public opentracing::TracerFactory {
25+
public:
26+
opentracing::expected<std::shared_ptr<opentracing::Tracer>>
27+
MakeTracer(const char* configuration, std::string& errorMessage) const
28+
noexcept override;
29+
};
30+
} // namespace jaegertracing
31+
32+
#endif // JAEGERTRACING_TRACER_FACTORY_H
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
/*
2+
* Copyright (c) 2018 Uber Technologies, Inc.
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
#include "jaegertracing/TracerFactory.h"
18+
#include <gtest/gtest.h>
19+
20+
namespace jaegertracing {
21+
#ifdef JAEGERTRACING_WITH_YAML_CPP
22+
TEST(TracerFactory, testInvalidConfig)
23+
{
24+
const char* invalidConfigTestCases[] = { "",
25+
"abc: {",
26+
R"({
27+
"service_name": {}
28+
})",
29+
R"({
30+
"service_name": "t",
31+
"badField": 97
32+
})" };
33+
TracerFactory tracerFactory;
34+
for (auto&& invalidConfig : invalidConfigTestCases) {
35+
std::string errorMessage;
36+
auto tracerMaybe =
37+
tracerFactory.MakeTracer(invalidConfig, errorMessage);
38+
ASSERT_FALSE(tracerMaybe);
39+
ASSERT_NE(errorMessage, "");
40+
}
41+
}
42+
43+
TEST(TracerFactory, testValidConfig)
44+
{
45+
const char* config = R"(
46+
{
47+
"service_name": "test",
48+
"disabled": true,
49+
"sampler": {
50+
"type": "probabilistic",
51+
"param": 0.001
52+
},
53+
"reporter": {
54+
"queueSize": 100,
55+
"bufferFlushInterval": 10,
56+
"logSpans": false,
57+
"localAgentHostPort": "127.0.0.1:6831"
58+
},
59+
"headers": {
60+
"jaegerDebugHeader": "debug-id",
61+
"jaegerBaggageHeader": "baggage",
62+
"TraceContextHeaderName": "trace-id",
63+
"traceBaggageHeaderPrefix": "testctx-"
64+
},
65+
"baggage_restrictions": {
66+
"denyBaggageOnInitializationFailure": false,
67+
"hostPort": "127.0.0.1:5778",
68+
"refreshInterval": 60
69+
}
70+
})";
71+
TracerFactory tracerFactory;
72+
std::string errorMessage;
73+
auto tracerMaybe = tracerFactory.MakeTracer(config, errorMessage);
74+
ASSERT_EQ(errorMessage, "");
75+
ASSERT_TRUE(tracerMaybe);
76+
}
77+
#else
78+
TEST(TracerFactory, failsWithoutYAML)
79+
{
80+
const char* config = "";
81+
TracerFactory tracerFactory;
82+
std::string errorMessage;
83+
auto tracerMaybe = tracerFactory.MakeTracer(config, errorMessage);
84+
ASSERT_NE(errorMessage, "");
85+
ASSERT_FALSE(tracerMaybe);
86+
}
87+
#endif // JAEGERTRACING_WITH_YAML_CPP
88+
} // namespace jaegertracing

0 commit comments

Comments
 (0)