This is an automated email from the ASF dual-hosted git repository. zhaoqingran pushed a commit to branch fix-Prometheus in repository https://gitbox.apache.org/repos/asf/hertzbeat.git
commit 627032aa87cd3b7efd8966463074b56d355eb04a Author: Logic <[email protected]> AuthorDate: Thu Jul 10 19:46:00 2025 +0800 refactor(collector): optimize HTTP response handling and memory usage - Restructured the parseResponse logic to handle different parse types more efficiently - Moved entity content consumption inside the PROMETHEUS and HEADER parse type blocks - Added null check and empty string handling for response entity - Improved code readability and reduced nesting --- .../collector/collect/http/HttpCollectImpl.java | 70 ++++++++++++---------- 1 file changed, 40 insertions(+), 30 deletions(-) diff --git a/hertzbeat-collector/hertzbeat-collector-basic/src/main/java/org/apache/hertzbeat/collector/collect/http/HttpCollectImpl.java b/hertzbeat-collector/hertzbeat-collector-basic/src/main/java/org/apache/hertzbeat/collector/collect/http/HttpCollectImpl.java index e38ef6c4bc..8af8a19fa1 100644 --- a/hertzbeat-collector/hertzbeat-collector-basic/src/main/java/org/apache/hertzbeat/collector/collect/http/HttpCollectImpl.java +++ b/hertzbeat-collector/hertzbeat-collector-basic/src/main/java/org/apache/hertzbeat/collector/collect/http/HttpCollectImpl.java @@ -68,6 +68,7 @@ import org.apache.hertzbeat.common.util.Base64Util; import org.apache.hertzbeat.common.util.CommonUtil; import org.apache.hertzbeat.common.util.IpDomainUtil; import org.apache.http.Header; +import org.apache.http.HttpEntity; import org.apache.http.HttpHeaders; import org.apache.http.HttpStatus; import org.apache.http.auth.AuthScope; @@ -144,37 +145,46 @@ public class HttpCollectImpl extends AbstractCollect { builder.setMsg(NetworkConstants.STATUS_CODE + SignConstants.BLANK + statusCode); return; } - /* - this could create large objects, potentially impacting JVM memory space significantly. - Option 1: Parse using InputStream, but this requires significant code changes; - Option 2: Manually trigger garbage collection, similar to how it's done in Dubbo for large inputs. - */ - String resp = EntityUtils.toString(response.getEntity(), StandardCharsets.UTF_8); - if (!StringUtils.hasText(resp)) { - log.info("http response entity is empty, status: {}.", statusCode); - } - Long responseTime = System.currentTimeMillis() - startTime; + + long responseTime = System.currentTimeMillis() - startTime; String parseType = metrics.getHttp().getParseType(); + HttpEntity entity = response.getEntity(); + try { - switch (parseType) { - case DispatchConstants.PARSE_JSON_PATH -> - parseResponseByJsonPath(resp, metrics.getAliasFields(), metrics.getHttp(), builder, responseTime); - case DispatchConstants.PARSE_PROM_QL -> - parseResponseByPromQl(resp, metrics.getAliasFields(), metrics.getHttp(), builder); - case DispatchConstants.PARSE_PROMETHEUS -> - parseResponseByPrometheusExporter(response.getEntity().getContent(), metrics.getAliasFields(), builder); - case DispatchConstants.PARSE_XML_PATH -> - parseResponseByXmlPath(resp, metrics, builder, responseTime); - case DispatchConstants.PARSE_WEBSITE -> - parseResponseByWebsite(resp, metrics, metrics.getHttp(), builder, responseTime, statusCode); - case DispatchConstants.PARSE_SITE_MAP -> - parseResponseBySiteMap(resp, metrics.getAliasFields(), builder); - case DispatchConstants.PARSE_HEADER -> - parseResponseByHeader(builder, metrics.getAliasFields(), response); - case DispatchConstants.PARSE_CONFIG -> - parseResponseByConfig(resp, metrics.getAliasFields(), metrics.getHttp(), builder, responseTime); - default -> - parseResponseByDefault(resp, metrics.getAliasFields(), metrics.getHttp(), builder, responseTime); + if (DispatchConstants.PARSE_PROMETHEUS.equals(parseType)) { + if (entity != null) { + parseResponseByPrometheusExporter(entity.getContent(), metrics.getAliasFields(), builder); + } + } else if (DispatchConstants.PARSE_HEADER.equals(parseType)) { + parseResponseByHeader(builder, metrics.getAliasFields(), response); + // Consume entity to release connection + EntityUtils.consumeQuietly(entity); + } else { + /* + this could create large objects, potentially impacting JVM memory space significantly. + Option 1: Parse using InputStream, but this requires significant code changes; + Option 2: Manually trigger garbage collection, similar to how it's done in Dubbo for large inputs. + */ + String resp = entity == null ? "" : EntityUtils.toString(entity, StandardCharsets.UTF_8); + if (!StringUtils.hasText(resp)) { + log.info("http response entity is empty, status: {}.", statusCode); + } + switch (parseType) { + case DispatchConstants.PARSE_JSON_PATH -> + parseResponseByJsonPath(resp, metrics.getAliasFields(), metrics.getHttp(), builder, responseTime); + case DispatchConstants.PARSE_PROM_QL -> + parseResponseByPromQl(resp, metrics.getAliasFields(), metrics.getHttp(), builder); + case DispatchConstants.PARSE_XML_PATH -> + parseResponseByXmlPath(resp, metrics, builder, responseTime); + case DispatchConstants.PARSE_WEBSITE -> + parseResponseByWebsite(resp, metrics, metrics.getHttp(), builder, responseTime, statusCode); + case DispatchConstants.PARSE_SITE_MAP -> + parseResponseBySiteMap(resp, metrics.getAliasFields(), builder); + case DispatchConstants.PARSE_CONFIG -> + parseResponseByConfig(resp, metrics.getAliasFields(), metrics.getHttp(), builder, responseTime); + default -> + parseResponseByDefault(resp, metrics.getAliasFields(), metrics.getHttp(), builder, responseTime); + } } } catch (Exception e) { log.info("parse error: {}.", e.getMessage(), e); @@ -856,4 +866,4 @@ public class HttpCollectImpl extends AbstractCollect { } return successCodeSet.contains(statusCode); } -} +} \ No newline at end of file --------------------------------------------------------------------- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
