Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
…try-cpp into origin/propagation
  • Loading branch information
Tianlin-Zhao committed Aug 21, 2020
2 parents 5eaa32d + 1ce011f commit ba2bfaa
Show file tree
Hide file tree
Showing 7 changed files with 241 additions and 46 deletions.
30 changes: 15 additions & 15 deletions api/test/trace/trace_state_test.cc
Original file line number Diff line number Diff line change
Expand Up @@ -23,19 +23,19 @@ TEST(EntryTest, KeyValueConstruction)
TraceState::Entry e(key, val);

EXPECT_EQ(key.size(), e.GetKey().size());
EXPECT_EQ(strcmp(key.data(), e.GetKey().data()), 0);
EXPECT_EQ(key, e.GetKey());

EXPECT_EQ(val.size(), e.GetValue().size());
EXPECT_EQ(strcmp(val.data(), e.GetValue().data()), 0);
EXPECT_EQ(val, e.GetValue());
}

// Test copy constructor
TEST(EntryTest, Copy)
{
TraceState::Entry e("test_key", "test_value");
TraceState::Entry copy(e);
EXPECT_EQ(strcmp(copy.GetKey().data(), e.GetKey().data()), 0);
EXPECT_EQ(strcmp(copy.GetValue().data(), e.GetValue().data()), 0);
EXPECT_EQ(copy.GetKey(), e.GetKey());
EXPECT_EQ(copy.GetValue(), e.GetValue());
}

// Test assignment operator
Expand All @@ -44,8 +44,8 @@ TEST(EntryTest, Assignment)
TraceState::Entry e("test_key", "test_value");
TraceState::Entry empty;
empty = e;
EXPECT_EQ(strcmp(empty.GetKey().data(), e.GetKey().data()), 0);
EXPECT_EQ(strcmp(empty.GetValue().data(), e.GetValue().data()), 0);
EXPECT_EQ(empty.GetKey(), e.GetKey());
EXPECT_EQ(empty.GetValue(), e.GetValue());
}

TEST(EntryTest, SetValue)
Expand All @@ -55,7 +55,7 @@ TEST(EntryTest, SetValue)
e.SetValue(new_val);

EXPECT_EQ(new_val.size(), e.GetValue().size());
EXPECT_EQ(strcmp(new_val.data(), e.GetValue().data()), 0);
EXPECT_EQ(new_val, e.GetValue());
}

// -------------------------- TraceState class tests ---------------------------
Expand All @@ -65,9 +65,9 @@ TEST(TraceStateTest, DefaultConstruction)
TraceState s;
opentelemetry::nostd::string_view return_val = "";
EXPECT_FALSE(s.Get("missing_key", return_val));
EXPECT_EQ(return_val.data(), "");
EXPECT_EQ(return_val, "");
EXPECT_TRUE(s.Empty());
EXPECT_EQ(0, s.Entries().size());
EXPECT_EQ(s.Entries().size(), 0);
}

TEST(TraceStateTest, Set)
Expand All @@ -84,8 +84,8 @@ TEST(TraceStateTest, Set)

opentelemetry::nostd::span<TraceState::Entry> entries = s.Entries();
EXPECT_EQ(entries.size(), 1);
EXPECT_EQ(entries[0].GetKey().data(), key);
EXPECT_EQ(entries[0].GetValue().data(), val);
EXPECT_EQ(entries[0].GetKey(), key);
EXPECT_EQ(entries[0].GetValue(), val);
}

TEST(TraceStateTest, Get)
Expand All @@ -105,12 +105,12 @@ TEST(TraceStateTest, Get)
for (int i = 0; i < kNumPairs; i++)
{
EXPECT_TRUE(s.Get(keys[i], return_val));
EXPECT_EQ(return_val.data(), values[i]);
EXPECT_EQ(return_val, values[i]);
return_val = "";
}

EXPECT_FALSE(s.Get("fake_key", return_val));
EXPECT_EQ(return_val.data(), "");
EXPECT_EQ(return_val, "");
}

TEST(TraceStateTest, Empty)
Expand All @@ -137,8 +137,8 @@ TEST(TraceStateTest, Entries)
opentelemetry::nostd::span<TraceState::Entry> entries = s.Entries();
for (int i = 0; i < kNumPairs; i++)
{
EXPECT_EQ(entries[i].GetKey().data(), keys[i]);
EXPECT_EQ(entries[i].GetValue().data(), values[i]);
EXPECT_EQ(entries[i].GetKey(), keys[i]);
EXPECT_EQ(entries[i].GetValue(), values[i]);
}
}

Expand Down
31 changes: 31 additions & 0 deletions examples/zpages/BUILD
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
# Copyright 2020, OpenTelemetry Authors
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

package(default_visibility = ["//visibility:public"])

cc_binary(
name = "zpages_example",
srcs = [
"zpages_example.cc",
],
linkopts = select({
"//bazel:windows": [],
"//conditions:default": ["-pthread"],
}),
deps = [
"//ext:headers",
"//ext/src/zpages",
"//sdk/src/trace",
],
)
57 changes: 57 additions & 0 deletions examples/zpages/zpages_example.cc
Original file line number Diff line number Diff line change
@@ -0,0 +1,57 @@
/**
* This is a basic example for zpages that helps users get familiar with how to
* use this feature in OpenTelemetery
*/
#include <chrono>
#include <iostream>
#include <string>
#include "opentelemetry/context/threadlocal_context.h"

#include "opentelemetry/ext/zpages/zpages.h" // Required file include for zpages

using opentelemetry::core::SteadyTimestamp;

int main(int argc, char *argv[])
{

/**
* The following line initializes zPages and starts a webserver at
* http://localhost:30000/tracez/ where spans that are created in the application
* can be viewed.
* Note that the webserver is destroyed after the application ends execution.
*/
ZPages::Initialize();
auto tracer = opentelemetry::trace::Provider::GetTracerProvider()->GetTracer("");

std::cout << "This example for zPages creates a few types of spans and then "
<< "creates a span every second for the duration of the application"
<< "\n";

// Error span
std::map<std::string, opentelemetry::common::AttributeValue> attribute_map;
attribute_map["completed_search_for"] = "Unknown user";
tracer->StartSpan("find user", attribute_map)
->SetStatus(opentelemetry::trace::CanonicalCode::NOT_FOUND, "User not found");

// Long time duration span
std::map<std::string, opentelemetry::common::AttributeValue> attribute_map2;
attribute_map2["completed_search_for"] = "John Doe";
opentelemetry::trace::StartSpanOptions start;
start.start_steady_time = SteadyTimestamp(nanoseconds(1));
opentelemetry::trace::EndSpanOptions end;
end.end_steady_time = SteadyTimestamp(nanoseconds(1000000000000));
tracer->StartSpan("find user", attribute_map2, start)->End(end);

// Running(deadlock) span
std::map<std::string, opentelemetry::common::AttributeValue> attribute_map3;
attribute_map3["searching_for"] = "Deleted user";
auto running_span = tracer->StartSpan("find user", attribute_map3);

// Create a completed span every second till user stops the loop
std::cout << "Presss CTRL+C to stop...\n";
while (true)
{
std::this_thread::sleep_for(seconds(1));
tracer->StartSpan("ping user")->End();
}
}
65 changes: 65 additions & 0 deletions ext/include/opentelemetry/ext/zpages/zpages.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,65 @@
#pragma once

#include <chrono>
#include <memory>

#include "opentelemetry/ext/zpages/tracez_data_aggregator.h"
#include "opentelemetry/ext/zpages/tracez_http_server.h"
#include "opentelemetry/ext/zpages/tracez_processor.h"

#include "opentelemetry/nostd/shared_ptr.h"
#include "opentelemetry/sdk/trace/tracer_provider.h"
#include "opentelemetry/trace/provider.h"

using opentelemetry::ext::zpages::TracezDataAggregator;
using opentelemetry::ext::zpages::TracezHttpServer;
using opentelemetry::ext::zpages::TracezSpanProcessor;
using std::chrono::microseconds;

/**
* Wrapper for zPages that initializes all the components required for zPages,
* and starts the HTTP server in the constructor and ends it in the destructor.
* The constructor and destructor for this object is private to prevent
* creation other than by calling the static function Initialize(). This follows the
* meyers singleton pattern and only a single instance of the class is allowed.
*/
class ZPages
{
public:
/**
* This function is called if the user wishes to include zPages in their
* application. It creates a static instance of this class.
*/
static void Initialize() { static ZPages instance; }

private:
/**
* Constructor is responsible for initializing the tracer, tracez processor,
* tracez data aggregator and the tracez server. The server is also started in
* constructor.
*/
ZPages()
{
auto tracez_processor_ = std::make_shared<TracezSpanProcessor>();
auto tracez_provider_ = opentelemetry::nostd::shared_ptr<opentelemetry::trace::TracerProvider>(
new opentelemetry::sdk::trace::TracerProvider(tracez_processor_));

auto tracez_aggregator =
std::unique_ptr<TracezDataAggregator>(new TracezDataAggregator(tracez_processor_));

tracez_server_ =
std::unique_ptr<TracezHttpServer>(new TracezHttpServer(std::move(tracez_aggregator)));

tracez_server_->start();

opentelemetry::trace::Provider::SetTracerProvider(tracez_provider_);
}

~ZPages()
{
// shut down the server when the object goes out of scope(at the end of the
// program)
tracez_server_->stop();
}
std::unique_ptr<TracezHttpServer> tracez_server_;
};
34 changes: 27 additions & 7 deletions sdk/include/opentelemetry/sdk/metrics/exporter.h
Original file line number Diff line number Diff line change
@@ -1,3 +1,19 @@
/*
* Copyright The OpenTelemetry Authors
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/

#pragma once

#include <memory>
Expand All @@ -22,7 +38,17 @@ enum class ExportResult
* Exporting failed. The caller must not retry exporting the same batch; the
* batch must be dropped.
*/
kFailure
kFailure = 1,

/**
* The collection does not have enough space to receive the export batch.
*/
kFailureFull = 2,

/**
* The export() function was passed an invalid argument.
*/
kFailureInvalidArgument = 3,
};
/**
* MetricsExporter defines the interface that protocol-specific span exporters must
Expand All @@ -39,12 +65,6 @@ class MetricsExporter
* @param records a vector of unique pointers to metric records
*/
virtual ExportResult Export(const std::vector<Record> &records) noexcept = 0;

/**
* In the Metrics specification, there is no Shutdown function required for exporters
* The Shutdown function can be implemented within exporters that wish to have one,
* but will not be enforced through this header
*/
};
} // namespace metrics
} // namespace sdk
Expand Down
43 changes: 42 additions & 1 deletion sdk/include/opentelemetry/sdk/metrics/ungrouped_processor.h
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,47 @@ namespace sdk

namespace metrics
{

struct KeyStruct
{
std::string name;
std::string description;
std::string labels;
metrics_api::InstrumentKind ins_kind;

// constructor
KeyStruct(std::string name,
std::string description,
std::string labels,
metrics_api::InstrumentKind ins_kind)
{
this->name = name;
this->description = description;
this->labels = labels;
this->ins_kind = ins_kind;
}

// operator== is required to compare keys in case of hash collision
bool operator==(const KeyStruct &p) const
{
return name == p.name && description == p.description && labels == p.labels &&
ins_kind == p.ins_kind;
}
};

struct KeyStruct_Hash
{
std::size_t operator()(const KeyStruct &keystruct) const
{
std::size_t name_size = keystruct.name.length();
std::size_t desc_size = keystruct.description.length();
std::size_t labels_size = keystruct.labels.length();
std::size_t ins_size = (int)keystruct.ins_kind;

return (name_size ^ desc_size ^ labels_size) + ins_size;
}
};

class UngroupedMetricsProcessor : public MetricsProcessor
{
public:
Expand All @@ -31,7 +72,7 @@ class UngroupedMetricsProcessor : public MetricsProcessor

private:
bool stateful_;
std::unordered_map<std::string, sdkmetrics::AggregatorVariant> batch_map_;
std::unordered_map<KeyStruct, sdkmetrics::AggregatorVariant, KeyStruct_Hash> batch_map_;

/**
* get_instrument returns the instrument from the passed in AggregatorVariant. We have to
Expand Down
Loading

0 comments on commit ba2bfaa

Please sign in to comment.