簡體   English   中英

ElasticSearch的TransportClient 5.4.3中是否存在內存泄漏,還是我的代碼存在缺陷?

[英]Are there memory leaks in ElasticSearch's TransportClient 5.4.3 or is my code flawed?

ElasticSearch的TransportClient 5.4.3中是否存在內存泄漏? 還是我沒有正確使用和關閉對象?

我在JRE 1.8.0_66上的Jenkins(2.68)中使用客戶端,並在Groovy中編寫代碼。 BulkRequestBuilder用於提交多個記錄。

在整個代碼中,這些4x 16 MB字節數組出現在內存中,但是即使經過TransportClient.close()方法也永遠不會關閉: 4個16 MB字節數組 如果我更慢地執行代碼,則最多可以得到這些16 MB字節數組的9倍,其中一些看起來非常相似: 7個16MB字節數組

我相信我會完全遵守官方文檔: https : //www.elastic.co/guide/en/elasticsearch/client/java-api/current/transport-client.html

這是我使用的代碼的精簡版:

@Grapes([
    @Grab(group = "org.apache.logging.log4j", module = "log4j-api", version = "2.8.2", initClass = true),
    @Grab(group = "org.apache.logging.log4j", module = "log4j-core", version = "2.8.2", initClass = true),
    @Grab(group = "org.elasticsearch.client", module = "transport", version = "5.4.3", initClass = true)
])
public class ElasticSearchReport implements Serializable {

    pubblic void execute() {
        // Data to report.
        List<Map<String, Object>> data = ...

        // ElasticSearch settings. Do not use sniffing because we want to upload data to the master node.
        Settings settings = Settings.builder()
            .put("cluster.name", "my-cluster")
            .put("client.transport.sniff", false)
            .build()

        PreBuiltTransportClient preBuiltTransportClient = new PreBuiltTransportClient(settings)
        TransportClient client = preBuiltTransportClient.addTransportAddress(new InetSocketTransportAddress(InetAddress.getByName("my-elastic-search-host"), 9300))
        List<String> errors = new LinkedList<String>()

        try {
            BulkRequestBuilder bulkRequest = client.prepareBulk()

            // Build the bulk query with each data entry.
            data.each({entry ->
                String serialisedEntry = SerializationUtils.toJson(entry)
                bulkRequest.add(client.prepareIndex("my-index", "my-type").setSource(serialisedEntry, XContentType.JSON))
            })

            // Process the response.
            bulkRequest.get().getItems().each({response ->
                if (response.failed) {
                    errors.add(response.failure.message)
                    return
                }

                final String statusName = response.status().name()

                // Check statusName ...
            })

            if (errors) throw new Exception(...)
        } finally {
            client.close()
            preBuiltTransportClient.close()
        }
    }
}

從我正在使用的對象來看,只有PreBuiltTransportClientTransportClient實現了Closeable因此我試圖在我的finally塊中顯式關閉它們。

使用.withCloseable() (Groovy等效於try-with-resources )進行了try-with-resources但是它並不能阻止問題的發生。

我以為我的bulkRequest.get().getItems().each({response ->行做的很有趣,所以我用以下內容替換了它,但沒有效果:

BulkResponse bulkResponse = bulkRequest.get()
BulkItemResponse[] bulkItemResponses = bulkResponse.getItems()
for (int responseIndex = 0; responseIndex < bulkItemResponses.length; responseIndex++) { ... }

我還嘗試過用BulkResponse bulkResponse = bulkRequest.get() BulkResponse bulkResponse = bulkRequest.execute().actionGet()替換BulkResponse bulkResponse = bulkRequest.get()BulkResponse bulkResponse = bulkRequest.execute().actionGet()

ElasticSearch Java REST客戶端似乎沒有這些問題。 我已經切換到它,還沒有遇到內存不足的錯誤。 一旦關閉客戶端並確定范圍,所有相對較大的字節數組都將釋放。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM