/Users/deen/code/yugabyte-db/src/yb/tserver/tserver_metrics_heartbeat_data_provider.cc
Line | Count | Source (jump to first uncovered line) |
1 | | // Copyright (c) YugaByte, Inc. |
2 | | // |
3 | | // Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except |
4 | | // in compliance with the License. You may obtain a copy of the License at |
5 | | // |
6 | | // http://www.apache.org/licenses/LICENSE-2.0 |
7 | | // |
8 | | // Unless required by applicable law or agreed to in writing, software distributed under the License |
9 | | // is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express |
10 | | // or implied. See the License for the specific language governing permissions and limitations |
11 | | // under the License. |
12 | | // |
13 | | |
14 | | #include "yb/tserver/tserver_metrics_heartbeat_data_provider.h" |
15 | | |
16 | | #include "yb/consensus/log.h" |
17 | | |
18 | | #include "yb/master/master_heartbeat.pb.h" |
19 | | |
20 | | #include "yb/tablet/tablet.h" |
21 | | #include "yb/tablet/tablet_metadata.h" |
22 | | #include "yb/tablet/tablet_peer.h" |
23 | | |
24 | | #include "yb/tserver/tablet_server.h" |
25 | | #include "yb/tserver/ts_tablet_manager.h" |
26 | | #include "yb/tserver/tserver_service.service.h" |
27 | | |
28 | | #include "yb/util/logging.h" |
29 | | #include "yb/util/mem_tracker.h" |
30 | | #include "yb/util/metrics.h" |
31 | | |
32 | | DEFINE_int32(tserver_heartbeat_metrics_interval_ms, 5000, |
33 | | "Interval (in milliseconds) at which tserver sends its metrics in a heartbeat to " |
34 | | "master."); |
35 | | |
36 | | DEFINE_bool(tserver_heartbeat_metrics_add_drive_data, true, |
37 | | "Add drive data to metrics which tserver sends to master"); |
38 | | |
39 | | using namespace std::literals; |
40 | | |
41 | | namespace yb { |
42 | | namespace tserver { |
43 | | |
44 | | TServerMetricsHeartbeatDataProvider::TServerMetricsHeartbeatDataProvider(TabletServer* server) : |
45 | | PeriodicalHeartbeatDataProvider(server, |
46 | | MonoDelta::FromMilliseconds(FLAGS_tserver_heartbeat_metrics_interval_ms)), |
47 | 5.81k | start_time_(MonoTime::Now()) {} |
48 | | |
49 | | void TServerMetricsHeartbeatDataProvider::DoAddData( |
50 | 37.7k | const master::TSHeartbeatResponsePB& last_resp, master::TSHeartbeatRequestPB* req) { |
51 | | // Get the total memory used. |
52 | 37.7k | size_t mem_usage = MemTracker::GetRootTracker()->GetUpdatedConsumption(true /* force */); |
53 | 37.7k | auto* metrics = req->mutable_metrics(); |
54 | 37.7k | metrics->set_total_ram_usage(static_cast<int64_t>(mem_usage)); |
55 | 0 | VLOG_WITH_PREFIX(4) << "Total Memory Usage: " << mem_usage; |
56 | | |
57 | 37.7k | uint64_t total_file_sizes = 0; |
58 | 37.7k | uint64_t uncompressed_file_sizes = 0; |
59 | 37.7k | uint64_t num_files = 0; |
60 | | |
61 | 37.7k | bool no_full_tablet_report = !req->has_tablet_report() || req->tablet_report().is_incremental(); |
62 | 37.7k | bool should_add_tablet_data = |
63 | 37.7k | FLAGS_tserver_heartbeat_metrics_add_drive_data && no_full_tablet_report; |
64 | | |
65 | | |
66 | 306k | for (const auto& tablet_peer : server().tablet_manager()->GetTabletPeers()) { |
67 | 306k | if (tablet_peer) { |
68 | 306k | auto tablet = tablet_peer->shared_tablet(); |
69 | 306k | if (tablet) { |
70 | 295k | auto sizes = tablet->GetCurrentVersionSstFilesAllSizes(); |
71 | 295k | total_file_sizes += sizes.first; |
72 | 295k | uncompressed_file_sizes += sizes.second; |
73 | 295k | num_files += tablet->GetCurrentVersionNumSSTFiles(); |
74 | 295k | if (should_add_tablet_data && tablet_peer->log_available() && |
75 | 295k | tablet_peer->tablet_metadata()->tablet_data_state() == |
76 | 295k | tablet::TabletDataState::TABLET_DATA_READY) { |
77 | 295k | auto tablet_metadata = req->add_storage_metadata(); |
78 | 295k | tablet_metadata->set_tablet_id(tablet_peer->tablet_id()); |
79 | 295k | tablet_metadata->set_sst_file_size(sizes.first); |
80 | 295k | tablet_metadata->set_wal_file_size(tablet_peer->log()->OnDiskSize()); |
81 | 295k | tablet_metadata->set_uncompressed_sst_file_size(sizes.second); |
82 | 295k | tablet_metadata->set_may_have_orphaned_post_split_data( |
83 | 295k | tablet->MayHaveOrphanedPostSplitData()); |
84 | 295k | } |
85 | 295k | } |
86 | 306k | } |
87 | 306k | } |
88 | 37.7k | metrics->set_total_sst_file_size(total_file_sizes); |
89 | 37.7k | metrics->set_uncompressed_sst_file_size(uncompressed_file_sizes); |
90 | 37.7k | metrics->set_num_sst_files(num_files); |
91 | | |
92 | | // Get the total number of read and write operations. |
93 | 37.7k | auto reads_hist = server().GetMetricsHistogram( |
94 | 37.7k | TabletServerServiceRpcMethodIndexes::kRead); |
95 | 37.7k | uint64_t num_reads = (reads_hist != nullptr) ? reads_hist->TotalCount() : 0; |
96 | | |
97 | 37.7k | auto writes_hist = server().GetMetricsHistogram( |
98 | 37.7k | TabletServerServiceRpcMethodIndexes::kWrite); |
99 | 37.7k | uint64_t num_writes = (writes_hist != nullptr) ? writes_hist->TotalCount() : 0; |
100 | | |
101 | | // Calculate the read and write ops per second. |
102 | 37.7k | MonoDelta diff = CoarseMonoClock::Now() - prev_run_time(); |
103 | 37.7k | double_t div = diff.ToSeconds(); |
104 | | |
105 | 37.7k | double rops_per_sec = (div > 0 && num_reads > 0) ? |
106 | 31.5k | (static_cast<double>(num_reads - prev_reads_) / div) : 0; |
107 | | |
108 | 37.7k | double wops_per_sec = (div > 0 && num_writes > 0) ? |
109 | 29.9k | (static_cast<double>(num_writes - prev_writes_) / div) : 0; |
110 | | |
111 | 37.7k | prev_reads_ = num_reads; |
112 | 37.7k | prev_writes_ = num_writes; |
113 | 37.7k | metrics->set_read_ops_per_sec(rops_per_sec); |
114 | 37.7k | metrics->set_write_ops_per_sec(wops_per_sec); |
115 | 37.7k | uint64_t uptime_seconds = CalculateUptime(); |
116 | | |
117 | 37.7k | metrics->set_uptime_seconds(uptime_seconds); |
118 | | |
119 | 0 | VLOG_WITH_PREFIX(4) << "Read Ops per second: " << rops_per_sec; |
120 | 0 | VLOG_WITH_PREFIX(4) << "Write Ops per second: " << wops_per_sec; |
121 | 0 | VLOG_WITH_PREFIX(4) << "Total SST File Sizes: "<< total_file_sizes; |
122 | 0 | VLOG_WITH_PREFIX(4) << "Uptime seconds: "<< uptime_seconds; |
123 | | |
124 | 37.7k | if (FLAGS_tserver_heartbeat_metrics_add_drive_data) { |
125 | 38.3k | for (const std::string& path : server().fs_manager()->GetFsRootDirs()) { |
126 | 38.3k | auto stat = server().GetEnv()->GetFilesystemStatsBytes(path.c_str()); |
127 | 38.3k | if (!stat.ok()) { |
128 | 13.3k | continue; |
129 | 13.3k | } |
130 | 25.0k | auto* path_metric = metrics->add_path_metrics(); |
131 | 25.0k | path_metric->set_path_id(path); |
132 | 25.0k | path_metric->set_used_space(stat->used_space); |
133 | 25.0k | path_metric->set_total_space(stat->total_space); |
134 | 25.0k | } |
135 | 37.7k | } |
136 | 37.7k | } |
137 | | |
138 | 37.7k | uint64_t TServerMetricsHeartbeatDataProvider::CalculateUptime() { |
139 | 37.7k | MonoDelta delta = MonoTime::Now().GetDeltaSince(start_time_); |
140 | 37.7k | uint64_t uptime_seconds = static_cast<uint64_t>(delta.ToSeconds()); |
141 | 37.7k | return uptime_seconds; |
142 | 37.7k | } |
143 | | |
144 | | |
145 | | } // namespace tserver |
146 | | } // namespace yb |