Skip to content

Commit

Permalink
[refactor] move code from MetricsDataController to MetricsService (#2437
Browse files Browse the repository at this point in the history
)

Co-authored-by: Calvin <naruse_shinji@163.com>
  • Loading branch information
pwallk and Calvin979 authored Aug 6, 2024
1 parent c2c00d4 commit d6b1969
Show file tree
Hide file tree
Showing 6 changed files with 335 additions and 117 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -22,22 +22,10 @@
import io.swagger.v3.oas.annotations.Operation;
import io.swagger.v3.oas.annotations.Parameter;
import io.swagger.v3.oas.annotations.tags.Tag;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;
import org.apache.hertzbeat.common.constants.CommonConstants;
import org.apache.hertzbeat.common.entity.dto.Field;
import org.apache.hertzbeat.common.entity.dto.Message;
import org.apache.hertzbeat.common.entity.dto.MetricsData;
import org.apache.hertzbeat.common.entity.dto.MetricsHistoryData;
import org.apache.hertzbeat.common.entity.dto.Value;
import org.apache.hertzbeat.common.entity.dto.ValueRow;
import org.apache.hertzbeat.common.entity.message.CollectRep;
import org.apache.hertzbeat.warehouse.store.history.HistoryDataReader;
import org.apache.hertzbeat.warehouse.store.realtime.RealTimeDataReader;
import org.apache.hertzbeat.warehouse.service.MetricsDataService;
import org.springframework.http.ResponseEntity;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
Expand All @@ -55,20 +43,17 @@ public class MetricsDataController {

private static final Integer METRIC_FULL_LENGTH = 3;

private final RealTimeDataReader realTimeDataReader;
private final Optional<HistoryDataReader> historyDataReader;
private final MetricsDataService metricsDataService;

public MetricsDataController(RealTimeDataReader realTimeDataReader,
Optional<HistoryDataReader> historyDataReader) {
this.realTimeDataReader = realTimeDataReader;
this.historyDataReader = historyDataReader;
public MetricsDataController(MetricsDataService metricsDataService) {
this.metricsDataService = metricsDataService;
}

@GetMapping("/api/warehouse/storage/status")
@Operation(summary = "Query Warehouse Storage Server Status", description = "Query the availability status of the storage service under the warehouse")
public ResponseEntity<Message<Void>> getWarehouseStorageServerStatus() {

if (historyDataReader.isPresent() && historyDataReader.get().isServerAvailable()) {
Boolean status = metricsDataService.getWarehouseStorageServerStatus();
if (Boolean.TRUE.equals(status)) {
return ResponseEntity.ok(Message.success());
}

Expand All @@ -83,47 +68,11 @@ public ResponseEntity<Message<MetricsData>> getMetricsData(
@PathVariable Long monitorId,
@Parameter(description = "Metrics Name", example = "cpu")
@PathVariable String metrics) {
boolean available = realTimeDataReader.isServerAvailable();
if (!available) {
return ResponseEntity.ok(Message.fail(FAIL_CODE, "real time store not available"));
}
CollectRep.MetricsData storageData = realTimeDataReader.getCurrentMetricsData(monitorId, metrics);
if (storageData == null) {
MetricsData metricsData = metricsDataService.getMetricsData(monitorId, metrics);
if (metricsData == null){
return ResponseEntity.ok(Message.success("query metrics data is empty"));
}
{
MetricsData.MetricsDataBuilder dataBuilder = MetricsData.builder();
dataBuilder.id(storageData.getId()).app(storageData.getApp()).metrics(storageData.getMetrics())
.time(storageData.getTime());
List<Field> fields = storageData.getFieldsList().stream().map(tmpField ->
Field.builder().name(tmpField.getName())
.type(Integer.valueOf(tmpField.getType()).byteValue())
.label(tmpField.getLabel())
.unit(tmpField.getUnit())
.build())
.collect(Collectors.toList());
dataBuilder.fields(fields);
List<ValueRow> valueRows = new LinkedList<>();
for (CollectRep.ValueRow valueRow : storageData.getValuesList()) {
Map<String, String> labels = new HashMap<>(8);
List<Value> values = new LinkedList<>();
for (int i = 0; i < fields.size(); i++) {
Field field = fields.get(i);
String origin = valueRow.getColumns(i);
if (CommonConstants.NULL_VALUE.equals(origin)) {
values.add(new Value());
} else {
values.add(new Value(origin));
if (field.getLabel()) {
labels.put(field.getName(), origin);
}
}
}
valueRows.add(ValueRow.builder().labels(labels).values(values).build());
}
dataBuilder.valueRows(valueRows);
return ResponseEntity.ok(Message.success(dataBuilder.build()));
}
return ResponseEntity.ok(Message.success(metricsData));
}

@GetMapping("/api/monitor/{monitorId}/metric/{metricFull}")
Expand All @@ -140,8 +89,7 @@ public ResponseEntity<Message<MetricsHistoryData>> getMetricHistoryData(
@Parameter(description = "aggregate data calc. off by default; 4-hour window, query limit >1 week", example = "false")
@RequestParam(required = false) Boolean interval
) {

if (historyDataReader.isEmpty() || !historyDataReader.get().isServerAvailable()) {
if (!metricsDataService.getWarehouseStorageServerStatus()) {
return ResponseEntity.ok(Message.fail(FAIL_CODE, "time series database not available"));
}
String[] names = metricFull.split("\\.");
Expand All @@ -151,19 +99,7 @@ public ResponseEntity<Message<MetricsHistoryData>> getMetricHistoryData(
String app = names[0];
String metrics = names[1];
String metric = names[2];
if (history == null) {
history = "6h";
}
Map<String, List<Value>> instanceValuesMap;
if (interval == null || !interval) {
instanceValuesMap = historyDataReader.get().getHistoryMetricData(monitorId, app, metrics, metric, label, history);
} else {
instanceValuesMap = historyDataReader.get().getHistoryIntervalMetricData(monitorId, app, metrics, metric, label, history);
}
MetricsHistoryData historyData = MetricsHistoryData.builder()
.id(monitorId).metrics(metrics).values(instanceValuesMap)
.field(Field.builder().name(metric).type(CommonConstants.TYPE_NUMBER).build())
.build();
MetricsHistoryData historyData = metricsDataService.getMetricHistoryData(monitorId, app, metrics, metric, label, history, interval);
return ResponseEntity.ok(Message.success(historyData));
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You 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 org.apache.hertzbeat.warehouse.service;

import org.apache.hertzbeat.common.entity.dto.MetricsData;
import org.apache.hertzbeat.common.entity.dto.MetricsHistoryData;

/**
* service for metrics data
*/
public interface MetricsDataService {

/**
* warehouse storage server availability or not
* @return true or false
*/
Boolean getWarehouseStorageServerStatus();

/**
* Query Real Time Metrics Data
* @param monitorId Monitor Id
* @param metrics Metrics Name
* @return metrics data
*/
MetricsData getMetricsData(Long monitorId, String metrics);

/**
* Queries historical data for a specified metric for monitoring
* @param monitorId Monitor Id
* @param app Monitor Type
* @param metrics Metrics Name
* @param metric Metrics Field Name
* @param label Label Filter
* @param history Query Historical Time Period
* @param interval aggregate data calc
* @return metrics history data
*/
MetricsHistoryData getMetricHistoryData(Long monitorId, String app, String metrics, String metric, String label, String history, Boolean interval);
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,118 @@
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You 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 org.apache.hertzbeat.warehouse.service.impl;

import java.util.HashMap;
import java.util.LinkedList;
import java.util.List;
import java.util.Map;
import java.util.Optional;
import java.util.stream.Collectors;
import org.apache.hertzbeat.common.constants.CommonConstants;
import org.apache.hertzbeat.common.entity.dto.Field;
import org.apache.hertzbeat.common.entity.dto.MetricsData;
import org.apache.hertzbeat.common.entity.dto.MetricsHistoryData;
import org.apache.hertzbeat.common.entity.dto.Value;
import org.apache.hertzbeat.common.entity.dto.ValueRow;
import org.apache.hertzbeat.common.entity.message.CollectRep;
import org.apache.hertzbeat.common.support.exception.CommonException;
import org.apache.hertzbeat.warehouse.service.MetricsDataService;
import org.apache.hertzbeat.warehouse.store.history.HistoryDataReader;
import org.apache.hertzbeat.warehouse.store.realtime.RealTimeDataReader;
import org.springframework.stereotype.Service;

/**
* Metrics Data Service impl
*/
@Service
public class MetricsDataServiceImpl implements MetricsDataService {

private final RealTimeDataReader realTimeDataReader;

private final Optional<HistoryDataReader> historyDataReader;

public MetricsDataServiceImpl(RealTimeDataReader realTimeDataReader, Optional<HistoryDataReader> historyDataReader) {
this.realTimeDataReader = realTimeDataReader;
this.historyDataReader = historyDataReader;
}

@Override
public Boolean getWarehouseStorageServerStatus() {
return historyDataReader.isPresent() && historyDataReader.get().isServerAvailable();
}

@Override
public MetricsData getMetricsData(Long monitorId, String metrics) {
boolean available = realTimeDataReader.isServerAvailable();
if (!available) {
throw new CommonException("real time store not available");
}
CollectRep.MetricsData storageData = realTimeDataReader.getCurrentMetricsData(monitorId, metrics);
if (storageData == null) {
return null;
}
MetricsData.MetricsDataBuilder dataBuilder = MetricsData.builder();
dataBuilder.id(storageData.getId()).app(storageData.getApp()).metrics(storageData.getMetrics())
.time(storageData.getTime());
List<Field> fields = storageData.getFieldsList().stream().map(tmpField ->
Field.builder().name(tmpField.getName())
.type(Integer.valueOf(tmpField.getType()).byteValue())
.label(tmpField.getLabel())
.unit(tmpField.getUnit())
.build())
.collect(Collectors.toList());
dataBuilder.fields(fields);
List<ValueRow> valueRows = new LinkedList<>();
for (CollectRep.ValueRow valueRow : storageData.getValuesList()) {
Map<String, String> labels = new HashMap<>(8);
List<Value> values = new LinkedList<>();
for (int i = 0; i < fields.size(); i++) {
Field field = fields.get(i);
String origin = valueRow.getColumns(i);
if (CommonConstants.NULL_VALUE.equals(origin)) {
values.add(new Value());
} else {
values.add(new Value(origin));
if (field.getLabel()) {
labels.put(field.getName(), origin);
}
}
}
valueRows.add(ValueRow.builder().labels(labels).values(values).build());
}
dataBuilder.valueRows(valueRows);
return dataBuilder.build();
}

@Override
public MetricsHistoryData getMetricHistoryData(Long monitorId, String app, String metrics, String metric, String label, String history, Boolean interval) {
if (history == null) {
history = "6h";
}
Map<String, List<Value>> instanceValuesMap;
if (interval == null || !interval) {
instanceValuesMap = historyDataReader.get().getHistoryMetricData(monitorId, app, metrics, metric, label, history);
} else {
instanceValuesMap = historyDataReader.get().getHistoryIntervalMetricData(monitorId, app, metrics, metric, label, history);
}
return MetricsHistoryData.builder()
.id(monitorId).metrics(metrics).values(instanceValuesMap)
.field(Field.builder().name(metric).type(CommonConstants.TYPE_NUMBER).build())
.build();
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,12 +15,13 @@
* limitations under the License.
*/

package org.apache.hertzbeat.warehouse.service;
package org.apache.hertzbeat.warehouse.service.impl;

import java.util.Collections;
import java.util.List;
import lombok.extern.slf4j.Slf4j;
import org.apache.hertzbeat.common.entity.message.CollectRep;
import org.apache.hertzbeat.warehouse.service.WarehouseService;
import org.apache.hertzbeat.warehouse.store.realtime.AbstractRealTimeDataStorage;
import org.springframework.stereotype.Service;

Expand Down
Loading

0 comments on commit d6b1969

Please sign in to comment.