Line data Source code
1 : /*
2 : ___________________________________________
3 : | _ ___ _ |
4 : | | | |__ \ | | |
5 : | | |__ ) |__ _ __ _ ___ _ __ | |_ |
6 : | | '_ \ / // _` |/ _` |/ _ \ '_ \| __| | HTTP/2 AGENT FOR MOCK TESTING
7 : | | | | |/ /| (_| | (_| | __/ | | | |_ | Version 0.0.z
8 : | |_| |_|____\__,_|\__, |\___|_| |_|\__| | https://github.com/testillano/h2agent
9 : | __/ | |
10 : | |___/ |
11 : |___________________________________________|
12 :
13 : Licensed under the MIT License <http://opensource.org/licenses/MIT>.
14 : SPDX-License-Identifier: MIT
15 : Copyright (c) 2021 Eduardo Ramos
16 :
17 : Permission is hereby granted, free of charge, to any person obtaining a copy
18 : of this software and associated documentation files (the "Software"), to deal
19 : in the Software without restriction, including without limitation the rights
20 : to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
21 : copies of the Software, and to permit persons to whom the Software is
22 : furnished to do so, subject to the following conditions:
23 :
24 : The above copyright notice and this permission notice shall be included in all
25 : copies or substantial portions of the Software.
26 :
27 : THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
28 : IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
29 : FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
30 : AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
31 : LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
32 : OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
33 : SOFTWARE.
34 : */
35 :
36 : #include <sstream>
37 : #include <string>
38 : #include <algorithm>
39 :
40 : #include <nlohmann/json.hpp>
41 :
42 : #include <ert/tracing/Logger.hpp>
43 :
44 : #include <AdminClientEndpoint.hpp>
45 :
46 :
47 : #include <functions.hpp>
48 :
49 :
50 : namespace h2agent
51 : {
52 : namespace model
53 : {
54 :
55 7 : void AdminClientEndpoint::connect(bool fromScratch, size_t numWorkers) {
56 :
57 7 : if (fromScratch) {
58 1 : client_.reset();
59 1 : clients_.clear();
60 : }
61 :
62 7 : if (numWorkers > 1) num_workers_ = numWorkers; // store for lazy connection
63 7 : if (num_workers_ < 1) num_workers_ = 1;
64 :
65 : // Ensure we have the right number of clients
66 7 : if (clients_.size() < num_workers_) {
67 7 : clients_.resize(num_workers_);
68 : }
69 :
70 14 : for (size_t i = 0; i < num_workers_; i++) {
71 7 : if (!clients_[i]) {
72 7 : clients_[i] = std::make_shared<h2agent::http2::MyTrafficHttp2Client>("h2agent_traffic_client", host_, std::to_string(port_), secure_, nullptr);
73 : try {
74 7 : clients_[i]->enableMetrics(metrics_, response_delay_seconds_histogram_bucket_boundaries_, message_size_bytes_histogram_bucket_boundaries_, application_name_ + "_" + h2agent::model::fixMetricsName(key_)/*source label*/);
75 7 : clients_[i]->enableMyMetrics(metrics_, application_name_);
76 : }
77 0 : catch(std::exception &e)
78 : {
79 0 : clients_[i]->enableMetrics(nullptr);
80 0 : clients_[i]->enableMyMetrics(nullptr);
81 0 : std::string msg = ert::tracing::Logger::asString("Cannot enable metrics for client endpoint '%s' worker %zu: %s", key_.c_str(), i, e.what());
82 0 : ert::tracing::Logger::error(msg, ERT_FILE_LOCATION);
83 0 : }
84 : }
85 : }
86 :
87 : // Keep client_ as alias for clients_[0] for backward compatibility
88 7 : if (!clients_.empty()) client_ = clients_[0];
89 7 : }
90 :
91 19 : void AdminClientEndpoint::setMetricsData(ert::metrics::Metrics *metrics, const ert::metrics::bucket_boundaries_t &responseDelaySecondsHistogramBucketBoundaries,
92 : const ert::metrics::bucket_boundaries_t &messageSizeBytesHistogramBucketBoundaries, const std::string &applicationName) {
93 :
94 19 : metrics_ = metrics;
95 19 : response_delay_seconds_histogram_bucket_boundaries_ = responseDelaySecondsHistogramBucketBoundaries;
96 19 : message_size_bytes_histogram_bucket_boundaries_ = messageSizeBytesHistogramBucketBoundaries;
97 19 : application_name_ = applicationName;
98 19 : }
99 :
100 26 : bool AdminClientEndpoint::load(const nlohmann::json &j) {
101 :
102 : // Store whole document (useful for GET operation)
103 26 : json_ = j;
104 :
105 : // Mandatory
106 26 : auto it = j.find("id");
107 26 : key_ = *it;
108 :
109 26 : it = j.find("host");
110 26 : host_ = *it;
111 :
112 26 : it = j.find("port");
113 26 : port_ = *it;
114 :
115 : // Optionals
116 26 : it = j.find("secure");
117 26 : secure_ = false;
118 26 : if (it != j.end() && it->is_boolean()) {
119 13 : secure_ = *it;
120 : }
121 26 : it = j.find("permit");
122 26 : permit_ = true;
123 26 : if (it != j.end() && it->is_boolean()) {
124 5 : permit_ = *it;
125 : }
126 :
127 : // Validations not in schema:
128 26 : if (key_.empty()) {
129 3 : ert::tracing::Logger::error("Invalid client endpoint identifier: provide a non-empty string", ERT_FILE_LOCATION);
130 3 : return false;
131 : }
132 :
133 23 : if (host_.empty()) {
134 1 : ert::tracing::Logger::error("Invalid client endpoint host: provide a non-empty string", ERT_FILE_LOCATION);
135 1 : return false;
136 : }
137 :
138 22 : return true;
139 : }
140 :
141 6 : nlohmann::json AdminClientEndpoint::asJson() const
142 : {
143 6 : if (!client_) return json_;
144 :
145 2 : nlohmann::json result = json_;
146 2 : result["status"] = client_->getConnectionStatus();
147 :
148 2 : return result;
149 2 : }
150 :
151 0 : std::uint64_t AdminClientEndpoint::getSendSeq() const
152 : {
153 0 : return send_seq_.load();
154 : }
155 :
156 : }
157 : }
158 :
|