本文介紹使用SDK時,在指定場景下可以使用的解決方法,幫助您實現符合您期望的操作結果。
腳本參數化
相同的請求,僅僅是傳遞的參數不同,這時推薦使用模板化的方式訪問實例。具體內容,請參見參數模板化,一個請求語句中模板化參數的個數不要超過128個。
請求設置超時
圖數據庫GDB的默認超時時間為30s, 如果您有耗時請求,需要設置較高的超時時間,請參見超時時間設置。
SDK參數配置指南
hosts: [ ${gdbHost} ]
port: 8182
username: ${username}
password: ${password}
connectionPool: {
maxSize: 16,
minSize: 16,
maxInProcessPerConnection: 4,
maxContentLength: ${yourExpectedSize}
}
serializer: {
className: org.apache.tinkerpop.gremlin.driver.ser.GraphBinaryMessageSerializerV1,
config: { serializeResultToString: false }
}
${gdbHost}
:GDB的連接地址,例如gds-bp*******************.graphdb.rds.aliyuncs.com
。${username}
:實例賬號。${password}
:實例密碼。${yourExpectedSize}
: 默認為65536,如果您的結果集過大,有可能會遇到Max frame length of 65536 has been exceeded
該類問題,根據業務調整該值大小便可解決該問題。maxSize
與minSize
:客戶端具有鏈接池,一個客戶端支持多線程并發訪問,需要把這兩個參數設置成一樣,且大于等于您的客戶端線程訪問數,這樣也能避免Timed out while waiting for an available host
錯誤。序列化協議(盡量使用GraphBinaryMessageSerializerV1序列化協議):
GraphBinaryMessageSerializerV1序列化協議:返回的Vertex、Edge為ReferenceVertex,ReferenceEdge,序列化時不會返回properties。性能好。
GraphSONMessageSerializerV3d0序列化協議:返回的 Vertex、Edge為DetachedVertex,DetachedEdge,序列化時會返回所有的properties,因此在Vertex可能存在大量properties時,會增加很多額外的序列化開銷。
僅獲取您需要的結果
根據業務進行判斷,在查詢時僅獲取您需要的結果,不要獲取多余結果,以獲取更高的性能。
建議請求:
g.V('id').valueMap('name') // 該dsl僅獲取name屬性
普通請求:
g.V('id').valueMap() // 該dsl會獲取該點的所有屬性
請求后務必主動拿結果
在客戶端提交請求后,服務端會將處理結果放在隊列中,需要客戶端主動拿結果。
ResultSet results = client.submit(dsl,parameters); //執行該步驟后,務必主動拿結果
List<Result> result = results.all().join(); //主動獲取結果
屬性長度限制
圖數據庫GDB支持簡單的Java基礎類型,即使為String類型的最大長度限制為64k, 且建議您存在GDB中的屬性不應過長。
批量獲取結果
如果您需要獲取大量數據,您可以限制每次返回的包大小,避免出錯。
示例如下:
ResultSet results = client[Integer.parseInt(threadIndex) % num].submitAsync(dsl, options.create()).get(DEFAULT_TIMEOUT, TimeUnit.MILLISECONDS);
List<Result> list = new LinkedList<>();
while (true) {
CompletableFuture<List<Result>> batch = results.some(1024);
List<Result> tmpList = batch.get(DEFAULT_TIMEOUT, TimeUnit.MILLISECONDS);
if (tmpList == null || tmpList.isEmpty()) {
break;
}
/* 分批取回需要的數據 */
list.addAll(tmpList);
}
結果集轉換
如果您需要將圖數據庫GDB的返回結果轉化為SDK可以使用的對象,您可以轉換結果集。
示例如下:
List<Result> results = client.submitAsync("userTest", dsl, parameters);
System.out.println("before-output-detail - " + dsl + " list size - " + results.size() + " useTimeMillis - " + String.valueOf(System.currentTimeMillis() - start));
results.forEach(result -> {
if (result.getObject() instanceof ReferenceVertex) {
ReferenceVertex vertex = (ReferenceVertex) result.getObject();
System.out.println("ReferenceVertex id - " + vertex.id() + " label - " + vertex.label() + " properties - ");
vertex.properties().forEachRemaining(p -> System.out.println(p));
} else if (result.getObject() instanceof DetachedVertex) {
System.out.println("DetachedVertex id - " + result.getVertex().id() + " label - " + result.getVertex().label() + " properties - ");
result.getVertex().properties().forEachRemaining(p -> System.out.println(p));
} else {
System.out.println("DefaultResult - " + result);
}
});