This is an automated email from the ASF dual-hosted git repository.

HTHou pushed a commit to branch codex/prometheus
in repository https://gitbox.apache.org/repos/asf/iotdb.git

commit 39b6b6abbd52e59d6c60feab228325b9cd6f1656
Author: HTHou <[email protected]>
AuthorDate: Fri May 8 17:47:05 2026 +0800

    Refine metric scrape model for HELP-based table writes
---
 .../iotdb/metricscrape/MetricScrapeConfig.java     |  60 ++++++-----
 .../iotdb/metricscrape/MetricScrapeService.java    |  12 +--
 .../iotdb/metricscrape/MetricScrapeTarget.java     |  10 +-
 .../iotdb/metricscrape/MetricTableWriter.java      | 114 +++++++++++++--------
 .../iotdb/metricscrape/PrometheusSample.java       |  15 +++
 .../iotdb/metricscrape/PrometheusTextParser.java   |  48 ++++++++-
 .../metricscrape/PrometheusTextParserTest.java     |  21 ++++
 .../java/org/apache/iotdb/db/conf/IoTDBConfig.java |   6 +-
 .../conf/iotdb-system.properties.template          |   8 +-
 9 files changed, 208 insertions(+), 86 deletions(-)

diff --git 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeConfig.java
 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeConfig.java
index 2ea52c7f91e..ab6d0d6f06f 100644
--- 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeConfig.java
+++ 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeConfig.java
@@ -31,20 +31,12 @@ public class MetricScrapeConfig {
 
   private final List<MetricScrapeTarget> targets;
   private final int intervalSeconds;
-  private final String database;
-  private final String table;
   private final int httpTimeoutMs;
 
   private MetricScrapeConfig(
-      List<MetricScrapeTarget> targets,
-      int intervalSeconds,
-      String database,
-      String table,
-      int httpTimeoutMs) {
+      List<MetricScrapeTarget> targets, int intervalSeconds, int 
httpTimeoutMs) {
     this.targets = targets;
     this.intervalSeconds = intervalSeconds;
-    this.database = database;
-    this.table = table;
     this.httpTimeoutMs = httpTimeoutMs;
   }
 
@@ -59,22 +51,23 @@ public class MetricScrapeConfig {
         || config.getMetricScrapeDatabase().trim().isEmpty()) {
       throw new IllegalArgumentException("metric_scrape_database should not be 
empty");
     }
-    if (config.getMetricScrapeTable() == null || 
config.getMetricScrapeTable().trim().isEmpty()) {
-      throw new IllegalArgumentException("metric_scrape_table should not be 
empty");
+    List<String> targetUrls = parseTargetUrls(config.getMetricScrapeTargets());
+    List<String> databases = parseDatabases(config.getMetricScrapeDatabase());
+    if (!targetUrls.isEmpty() && databases.size() != targetUrls.size()) {
+      throw new IllegalArgumentException(
+          "metric_scrape_database count should be equal to 
metric_scrape_targets count");
     }
     return new MetricScrapeConfig(
-        parseTargets(config.getMetricScrapeTargets()),
+        buildTargets(targetUrls, databases),
         config.getMetricScrapeIntervalSeconds(),
-        config.getMetricScrapeDatabase().trim(),
-        config.getMetricScrapeTable().trim(),
         config.getMetricScrapeHttpTimeoutMs());
   }
 
-  private static List<MetricScrapeTarget> parseTargets(String rawTargets) {
+  private static List<String> parseTargetUrls(String rawTargets) {
     if (rawTargets == null || rawTargets.trim().isEmpty()) {
       return Collections.emptyList();
     }
-    List<MetricScrapeTarget> targets = new ArrayList<>();
+    List<String> targets = new ArrayList<>();
     String[] targetItems = rawTargets.split(",");
     for (String targetItem : targetItems) {
       String target = targetItem.trim();
@@ -82,7 +75,32 @@ public class MetricScrapeConfig {
         continue;
       }
       validateTarget(target);
-      targets.add(new MetricScrapeTarget(target));
+      targets.add(target);
+    }
+    return Collections.unmodifiableList(targets);
+  }
+
+  private static List<String> parseDatabases(String rawDatabases) {
+    if (rawDatabases == null || rawDatabases.trim().isEmpty()) {
+      return Collections.emptyList();
+    }
+    List<String> databases = new ArrayList<>();
+    String[] databaseItems = rawDatabases.split(",");
+    for (String databaseItem : databaseItems) {
+      String database = databaseItem.trim();
+      if (database.isEmpty()) {
+        continue;
+      }
+      databases.add(database);
+    }
+    return Collections.unmodifiableList(databases);
+  }
+
+  private static List<MetricScrapeTarget> buildTargets(
+      List<String> targetUrls, List<String> databases) {
+    List<MetricScrapeTarget> targets = new ArrayList<>(targetUrls.size());
+    for (int i = 0; i < targetUrls.size(); i++) {
+      targets.add(new MetricScrapeTarget(targetUrls.get(i), databases.get(i)));
     }
     return Collections.unmodifiableList(targets);
   }
@@ -108,14 +126,6 @@ public class MetricScrapeConfig {
     return intervalSeconds;
   }
 
-  public String getDatabase() {
-    return database;
-  }
-
-  public String getTable() {
-    return table;
-  }
-
   public int getHttpTimeoutMs() {
     return httpTimeoutMs;
   }
diff --git 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeService.java
 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeService.java
index da1c98d93e4..5f1ac3cca58 100644
--- 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeService.java
+++ 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeService.java
@@ -56,8 +56,8 @@ public class MetricScrapeService implements IExternalService {
       return;
     }
 
-    writer = new MetricTableWriter(config.getDatabase(), config.getTable());
-    writer.initializeSchema();
+    writer = new MetricTableWriter();
+    writer.initializeDatabases(config.getTargets());
 
     executorService =
         Executors.newScheduledThreadPool(
@@ -72,11 +72,9 @@ public class MetricScrapeService implements IExternalService 
{
     }
 
     LOGGER.info(
-        "Start MetricScrapeService successfully, targets={}, interval={}s, 
table={}.{}",
+        "Start MetricScrapeService successfully, targets={}, interval={}s",
         config.getTargets(),
-        config.getIntervalSeconds(),
-        config.getDatabase(),
-        config.getTable());
+        config.getIntervalSeconds());
   }
 
   @Override
@@ -105,7 +103,7 @@ public class MetricScrapeService implements 
IExternalService {
         LOGGER.debug("Metric scrape target {} returns no samples.", target);
         return;
       }
-      currentWriter.write(samples);
+      currentWriter.write(target.getDatabase(), samples);
       LOGGER.debug("Metric scrape target {} writes {} samples.", target, 
samples.size());
     } catch (Exception e) {
       LOGGER.warn("Failed to scrape metric target {}.", target, e);
diff --git 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeTarget.java
 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeTarget.java
index 88dec77c6d1..5c55acebfb5 100644
--- 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeTarget.java
+++ 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricScrapeTarget.java
@@ -22,17 +22,23 @@ package org.apache.iotdb.metricscrape;
 public class MetricScrapeTarget {
 
   private final String url;
+  private final String database;
 
-  public MetricScrapeTarget(String url) {
+  public MetricScrapeTarget(String url, String database) {
     this.url = url;
+    this.database = database;
   }
 
   public String getUrl() {
     return url;
   }
 
+  public String getDatabase() {
+    return database;
+  }
+
   @Override
   public String toString() {
-    return url;
+    return url + " -> " + database;
   }
 }
diff --git 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricTableWriter.java
 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricTableWriter.java
index 2b82d19a18d..35c913979ee 100644
--- 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricTableWriter.java
+++ 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/MetricTableWriter.java
@@ -50,13 +50,14 @@ import java.time.ZoneId;
 import java.util.ArrayList;
 import java.util.Collections;
 import java.util.LinkedHashMap;
+import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Map;
+import java.util.Objects;
+import java.util.Set;
 
 public class MetricTableWriter {
 
-  public static final String METRIC_NAME_COLUMN = "metric_name";
-  public static final String VALUE_COLUMN = "value";
   private static final String TIME_COLUMN = "time";
 
   private static final Logger LOGGER = 
LoggerFactory.getLogger(MetricTableWriter.class);
@@ -65,17 +66,12 @@ public class MetricTableWriter {
   private static final SessionManager SESSION_MANAGER = 
SessionManager.getInstance();
   private static final IoTDBConfig IOTDB_CONFIG = 
IoTDBDescriptor.getInstance().getConfig();
 
-  private final String database;
-  private final String table;
   private final IClientSession session;
   private final SqlParser sqlParser = new SqlParser();
   private final Metadata metadata = 
LocalExecutionPlanner.getInstance().metadata;
 
-  public MetricTableWriter(String database, String table) {
-    this.database = database;
-    this.table = table;
+  public MetricTableWriter() {
     this.session = new InternalClientSession("METRIC_SCRAPE");
-    this.session.setDatabaseName(database);
     this.session.setSqlDialect(SqlDialect.TABLE);
     SESSION_MANAGER.supplySession(
         session,
@@ -85,32 +81,31 @@ public class MetricTableWriter {
         ClientVersion.V_1_0);
   }
 
-  public synchronized void initializeSchema() {
-    executeStatement("CREATE DATABASE IF NOT EXISTS " + 
quoteIdentifier(database));
-    session.setDatabaseName(database);
-    executeStatement(
-        "CREATE TABLE IF NOT EXISTS "
-            + quoteIdentifier(table)
-            + " ("
-            + METRIC_NAME_COLUMN
-            + " STRING TAG, "
-            + VALUE_COLUMN
-            + " DOUBLE FIELD)");
+  public synchronized void initializeDatabases(List<MetricScrapeTarget> 
targets) {
+    Set<String> databases = new LinkedHashSet<>();
+    for (MetricScrapeTarget target : targets) {
+      databases.add(target.getDatabase());
+    }
+    for (String database : databases) {
+      executeStatement("CREATE DATABASE IF NOT EXISTS " + 
quoteIdentifier(database));
+    }
   }
 
-  public synchronized void write(List<PrometheusSample> samples) {
+  public synchronized void write(String database, List<PrometheusSample> 
samples) {
     if (samples.isEmpty()) {
       return;
     }
-    Map<List<String>, TabletBuilder> builders = new LinkedHashMap<>();
+    Map<TabletKey, TabletBuilder> builders = new LinkedHashMap<>();
     for (PrometheusSample sample : samples) {
       List<String> labelKeys = new ArrayList<>(sample.getLabels().keySet());
       Collections.sort(labelKeys);
-      validateLabelKeys(labelKeys);
-      TabletBuilder builder = builders.get(labelKeys);
+      validateColumns(sample, labelKeys);
+      TabletKey key =
+          new TabletKey(sample.getMetricFamilyName(), sample.getMetricName(), 
labelKeys);
+      TabletBuilder builder = builders.get(key);
       if (builder == null) {
-        builder = new TabletBuilder(labelKeys);
-        builders.put(labelKeys, builder);
+        builder = new TabletBuilder(database, key);
+        builders.put(key, builder);
       }
       builder.add(sample);
     }
@@ -124,11 +119,16 @@ public class MetricTableWriter {
     SESSION_MANAGER.closeSession(session, COORDINATOR::cleanupQueryExecution, 
false);
   }
 
-  private void validateLabelKeys(List<String> labelKeys) {
+  private void validateColumns(PrometheusSample sample, List<String> 
labelKeys) {
+    if (sample.getMetricFamilyName() == null || 
sample.getMetricFamilyName().trim().isEmpty()) {
+      throw new IllegalArgumentException("Prometheus metric family name should 
not be empty");
+    }
+    if (sample.getMetricName() == null || 
sample.getMetricName().trim().isEmpty()) {
+      throw new IllegalArgumentException("Prometheus metric name should not be 
empty");
+    }
     for (String labelKey : labelKeys) {
-      if (METRIC_NAME_COLUMN.equalsIgnoreCase(labelKey)
-          || VALUE_COLUMN.equalsIgnoreCase(labelKey)
-          || TIME_COLUMN.equalsIgnoreCase(labelKey)) {
+      if (TIME_COLUMN.equalsIgnoreCase(labelKey)
+          || sample.getMetricName().equalsIgnoreCase(labelKey)) {
         throw new IllegalArgumentException(
             "Prometheus label conflicts with reserved IoTDB table column name: 
" + labelKey);
       }
@@ -193,12 +193,49 @@ public class MetricTableWriter {
     return "\"" + identifier.replace("\"", "\"\"") + "\"";
   }
 
+  private static class TabletKey {
+    private final String table;
+    private final String field;
+    private final List<String> labelKeys;
+
+    private TabletKey(String table, String field, List<String> labelKeys) {
+      this.table = table;
+      this.field = field;
+      this.labelKeys = new ArrayList<>(labelKeys);
+    }
+
+    @Override
+    public boolean equals(Object o) {
+      if (this == o) {
+        return true;
+      }
+      if (!(o instanceof TabletKey)) {
+        return false;
+      }
+      TabletKey tabletKey = (TabletKey) o;
+      return Objects.equals(table, tabletKey.table)
+          && Objects.equals(field, tabletKey.field)
+          && Objects.equals(labelKeys, tabletKey.labelKeys);
+    }
+
+    @Override
+    public int hashCode() {
+      return Objects.hash(table, field, labelKeys);
+    }
+  }
+
   private class TabletBuilder {
+    private final String database;
+    private final String table;
+    private final String field;
     private final List<String> labelKeys;
     private final List<PrometheusSample> samples = new ArrayList<>();
 
-    private TabletBuilder(List<String> labelKeys) {
-      this.labelKeys = new ArrayList<>(labelKeys);
+    private TabletBuilder(String database, TabletKey key) {
+      this.database = database;
+      this.table = key.table;
+      this.field = key.field;
+      this.labelKeys = new ArrayList<>(key.labelKeys);
     }
 
     private void add(PrometheusSample sample) {
@@ -213,10 +250,9 @@ public class MetricTableWriter {
       statement.setDatabaseName(database);
       statement.setRowCount(samples.size());
 
-      List<String> measurements = new ArrayList<>(labelKeys.size() + 2);
-      measurements.add(METRIC_NAME_COLUMN);
+      List<String> measurements = new ArrayList<>(labelKeys.size() + 1);
       measurements.addAll(labelKeys);
-      measurements.add(VALUE_COLUMN);
+      measurements.add(field);
       statement.setMeasurements(measurements.toArray(new String[0]));
       statement.setTimes(buildTimes());
       statement.setDataTypes(buildDataTypes(measurements.size()));
@@ -253,10 +289,9 @@ public class MetricTableWriter {
     }
 
     private Object[] buildColumns() {
-      Object[] columns = new Object[labelKeys.size() + 2];
-      columns[0] = buildStringColumn(METRIC_NAME_COLUMN);
+      Object[] columns = new Object[labelKeys.size() + 1];
       for (int i = 0; i < labelKeys.size(); i++) {
-        columns[i + 1] = buildStringColumn(labelKeys.get(i));
+        columns[i] = buildStringColumn(labelKeys.get(i));
       }
       double[] values = new double[samples.size()];
       for (int i = 0; i < samples.size(); i++) {
@@ -269,10 +304,7 @@ public class MetricTableWriter {
     private Binary[] buildStringColumn(String columnName) {
       Binary[] values = new Binary[samples.size()];
       for (int i = 0; i < samples.size(); i++) {
-        String value =
-            METRIC_NAME_COLUMN.equals(columnName)
-                ? samples.get(i).getMetricName()
-                : samples.get(i).getLabels().get(columnName);
+        String value = samples.get(i).getLabels().get(columnName);
         values[i] = new Binary(value.getBytes(StandardCharsets.UTF_8));
       }
       return values;
diff --git 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusSample.java
 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusSample.java
index 664429f792a..9d65845b9d7 100644
--- 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusSample.java
+++ 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusSample.java
@@ -25,6 +25,7 @@ import java.util.Map;
 
 public class PrometheusSample {
 
+  private final String metricFamilyName;
   private final String metricName;
   private final Map<String, String> labels;
   private final double value;
@@ -32,12 +33,26 @@ public class PrometheusSample {
 
   public PrometheusSample(
       String metricName, Map<String, String> labels, double value, long 
timestamp) {
+    this(metricName, metricName, labels, value, timestamp);
+  }
+
+  public PrometheusSample(
+      String metricFamilyName,
+      String metricName,
+      Map<String, String> labels,
+      double value,
+      long timestamp) {
+    this.metricFamilyName = metricFamilyName;
     this.metricName = metricName;
     this.labels = Collections.unmodifiableMap(new LinkedHashMap<>(labels));
     this.value = value;
     this.timestamp = timestamp;
   }
 
+  public String getMetricFamilyName() {
+    return metricFamilyName;
+  }
+
   public String getMetricName() {
     return metricName;
   }
diff --git 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusTextParser.java
 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusTextParser.java
index 949b0901243..8b553a7ff25 100644
--- 
a/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusTextParser.java
+++ 
b/external-service-impl/metric-scrape/src/main/java/org/apache/iotdb/metricscrape/PrometheusTextParser.java
@@ -23,8 +23,10 @@ import 
org.apache.iotdb.commons.queryengine.utils.TimestampPrecisionUtils;
 
 import java.util.ArrayList;
 import java.util.LinkedHashMap;
+import java.util.LinkedHashSet;
 import java.util.List;
 import java.util.Map;
+import java.util.Set;
 import java.util.concurrent.TimeUnit;
 
 public class PrometheusTextParser {
@@ -35,17 +37,19 @@ public class PrometheusTextParser {
     }
     List<PrometheusSample> samples = new ArrayList<>();
     String[] lines = text.split("\\r\\n|\\n|\\r");
+    Set<String> helpMetricNames = collectHelpMetricNames(lines);
     for (int i = 0; i < lines.length; i++) {
       String line = lines[i].trim();
       if (line.isEmpty() || line.startsWith("#")) {
         continue;
       }
-      samples.add(parseSample(line, i + 1, defaultTimestamp));
+      samples.add(parseSample(line, i + 1, defaultTimestamp, helpMetricNames));
     }
     return samples;
   }
 
-  private PrometheusSample parseSample(String line, int lineNumber, long 
defaultTimestamp) {
+  private PrometheusSample parseSample(
+      String line, int lineNumber, long defaultTimestamp, Set<String> 
helpMetricNames) {
     Parser parser = new Parser(line, lineNumber);
     String metricName = parser.parseMetricName();
     Map<String, String> labels = parser.parseLabels();
@@ -55,7 +59,45 @@ public class PrometheusTextParser {
     long timestamp = parser.parseOptionalTimestamp(defaultTimestamp);
     parser.skipWhitespace();
     parser.expectEnd();
-    return new PrometheusSample(metricName, labels, value, timestamp);
+    return new PrometheusSample(
+        resolveMetricFamilyName(metricName, helpMetricNames), metricName, 
labels, value, timestamp);
+  }
+
+  private static Set<String> collectHelpMetricNames(String[] lines) {
+    Set<String> helpMetricNames = new LinkedHashSet<>();
+    for (String rawLine : lines) {
+      String line = rawLine.trim();
+      if (!line.startsWith("# HELP")) {
+        continue;
+      }
+      int position = "# HELP".length();
+      while (position < line.length() && 
Character.isWhitespace(line.charAt(position))) {
+        position++;
+      }
+      int start = position;
+      while (position < line.length() && 
!Character.isWhitespace(line.charAt(position))) {
+        position++;
+      }
+      if (start < position) {
+        helpMetricNames.add(line.substring(start, position));
+      }
+    }
+    return helpMetricNames;
+  }
+
+  private static String resolveMetricFamilyName(String metricName, Set<String> 
helpMetricNames) {
+    if (helpMetricNames.contains(metricName)) {
+      return metricName;
+    }
+
+    String result = null;
+    for (String helpMetricName : helpMetricNames) {
+      if (metricName.startsWith(helpMetricName + "_")
+          && (result == null || helpMetricName.length() > result.length())) {
+        result = helpMetricName;
+      }
+    }
+    return result == null ? metricName : result;
   }
 
   private static double parsePrometheusDouble(String token, int lineNumber) {
diff --git 
a/external-service-impl/metric-scrape/src/test/java/org/apache/iotdb/metricscrape/PrometheusTextParserTest.java
 
b/external-service-impl/metric-scrape/src/test/java/org/apache/iotdb/metricscrape/PrometheusTextParserTest.java
index 15f36474bac..237d2d6495d 100644
--- 
a/external-service-impl/metric-scrape/src/test/java/org/apache/iotdb/metricscrape/PrometheusTextParserTest.java
+++ 
b/external-service-impl/metric-scrape/src/test/java/org/apache/iotdb/metricscrape/PrometheusTextParserTest.java
@@ -40,6 +40,7 @@ public class PrometheusTextParserTest {
 
     assertEquals(2, samples.size());
     PrometheusSample first = samples.get(0);
+    assertEquals("up", first.getMetricFamilyName());
     assertEquals("up", first.getMetricName());
     assertEquals("iotdb", first.getLabels().get("job"));
     assertEquals("127.0.0.1:6667", first.getLabels().get("instance"));
@@ -47,6 +48,7 @@ public class PrometheusTextParserTest {
     assertEquals(1635232143960L, first.getTimestamp());
 
     PrometheusSample second = samples.get(1);
+    assertEquals("rpc:latency_seconds", second.getMetricFamilyName());
     assertEquals("rpc:latency_seconds", second.getMetricName());
     assertEquals("query", second.getLabels().get("method"));
     assertEquals("a\\b\"c", second.getLabels().get("escaped"));
@@ -65,6 +67,7 @@ public class PrometheusTextParserTest {
 
     assertEquals(1, samples.size());
     PrometheusSample sample = samples.get(0);
+    assertEquals("file_count", sample.getMetricFamilyName());
     assertEquals("file_count", sample.getMetricName());
     assertEquals("defaultCluster", sample.getLabels().get("cluster"));
     assertEquals("DataNode", sample.getLabels().get("nodeType"));
@@ -80,10 +83,28 @@ public class PrometheusTextParserTest {
     List<PrometheusSample> samples = new PrometheusTextParser().parse(text, 
100);
 
     assertEquals(1, samples.size());
+    assertEquals("metric[name]", samples.get(0).getMetricFamilyName());
     assertEquals("metric[name]", samples.get(0).getMetricName());
     assertEquals("value", samples.get(0).getLabels().get("tag-key"));
   }
 
+  @Test
+  public void testParseMetricFamilyNameFromHelp() {
+    String text =
+        "# HELP request_duration_seconds Request duration.\n"
+            + "# TYPE request_duration_seconds summary\n"
+            + "request_duration_seconds_sum{method=\"query\"} 10\n"
+            + "request_duration_seconds_count{method=\"query\"} 2\n";
+
+    List<PrometheusSample> samples = new PrometheusTextParser().parse(text, 
100);
+
+    assertEquals(2, samples.size());
+    assertEquals("request_duration_seconds", 
samples.get(0).getMetricFamilyName());
+    assertEquals("request_duration_seconds_sum", 
samples.get(0).getMetricName());
+    assertEquals("request_duration_seconds", 
samples.get(1).getMetricFamilyName());
+    assertEquals("request_duration_seconds_count", 
samples.get(1).getMetricName());
+  }
+
   @Test(expected = IllegalArgumentException.class)
   public void testRejectDuplicateLabel() {
     new PrometheusTextParser().parse("up{job=\"a\",job=\"b\"} 1", 100);
diff --git 
a/iotdb-core/datanode/src/main/java/org/apache/iotdb/db/conf/IoTDBConfig.java 
b/iotdb-core/datanode/src/main/java/org/apache/iotdb/db/conf/IoTDBConfig.java
index 0f814c9cc90..b1850ab7bc1 100644
--- 
a/iotdb-core/datanode/src/main/java/org/apache/iotdb/db/conf/IoTDBConfig.java
+++ 
b/iotdb-core/datanode/src/main/java/org/apache/iotdb/db/conf/IoTDBConfig.java
@@ -134,10 +134,12 @@ public class IoTDBConfig {
   /** The metric scrape interval in seconds. */
   private int metricScrapeIntervalSeconds = 15;
 
-  /** The table model database used by metric scrape service. */
+  /** The comma separated table model databases used by metric scrape service. 
*/
   private String metricScrapeDatabase = "metrics";
 
-  /** The table used by metric scrape service. */
+  /**
+   * The table used by metric scrape service. Deprecated: table names are 
parsed from HELP lines.
+   */
   private String metricScrapeTable = "iotdb_metrics";
 
   /** The HTTP timeout used by metric scrape service. Unit: millisecond */
diff --git 
a/iotdb-core/node-commons/src/assembly/resources/conf/iotdb-system.properties.template
 
b/iotdb-core/node-commons/src/assembly/resources/conf/iotdb-system.properties.template
index 80006bf4832..f2ddb454557 100644
--- 
a/iotdb-core/node-commons/src/assembly/resources/conf/iotdb-system.properties.template
+++ 
b/iotdb-core/node-commons/src/assembly/resources/conf/iotdb-system.properties.template
@@ -2160,16 +2160,12 @@ metric_scrape_targets=
 # Datatype: int
 metric_scrape_interval_seconds=15
 
-# the table model database used by the metric scrape service.
+# the comma separated table model databases used by the metric scrape service.
+# The count and order must match metric_scrape_targets.
 # effectiveMode: restart
 # Datatype: String
 metric_scrape_database=metrics
 
-# the table used by the metric scrape service.
-# effectiveMode: restart
-# Datatype: String
-metric_scrape_table=iotdb_metrics
-
 # the HTTP connect and read timeout used by the metric scrape service in 
milliseconds.
 # effectiveMode: restart
 # Datatype: int

Reply via email to