การสแกนช่วง AWS DynamoDB โดยใช้ DynamoDBMapper

ฉันได้ลองใช้ DynamoDB ครั้งแรกหลังจากใช้ฐานข้อมูลเชิงสัมพันธ์มาเป็นเวลานาน ขณะนี้กำลังดำเนินการอัปเดตผลการทดสอบสำหรับการวิเคราะห์ในภายหลัง โปรดพิจารณาตารางและดัชนีรองต่อไปนี้

12

ฉันพยายามรับชื่อทดสอบที่กำหนด การทดสอบทำงานในช่วงการแก้ไขที่ทราบโดยใช้โค้ด Java ต่อไปนี้:

HashMap<String, Condition> scanMap = new HashMap<>();
scanMap.put("revision", new Condition().withComparisonOperator(ComparisonOperator.BETWEEN).withAttributeValueList(Arrays.asList(new AttributeValue("N:"+String.valueOf(minRev)), new AttributeValue("N:"+String.valueOf(maxRev)))));
scanMap.put("testName", new Condition().withComparisonOperator(ComparisonOperator.EQ).withAttributeValueList(new AttributeValue(Collections.singletonList(testName))));
DynamoDBScanExpression scanExpression = new DynamoDBScanExpression().withScanFilter(scanMap);
scanExpression.setIndexName("testName-revision-index");
List<ValidationReport> reports = getMapper().scan(ValidationReport.class, scanExpression);

ฉันพยายามลบ "N:" โดยไม่มีโชค การลบนิพจน์การแก้ไขทั้งหมดจะส่งคืนการทดสอบทั้งหมดโดยไม่มีข้อจำกัดเกี่ยวกับช่วงการแก้ไข

ความช่วยเหลือใด ๆ ที่จะได้รับการชื่นชมที่นี่


person Ohad Benita    schedule 24.05.2017    source แหล่งที่มา


คำตอบ (1)


ดูเหมือนว่าฉันกำลังเห่าผิดต้นไม้ที่นี่ พยายามใช้ Scan แทน Query :

ลูกค้าไม่ควรใช้ ScanFilter ซึ่งเลิกใช้แล้ว ประเภทข้อมูลรายการ/แมปเหมาะสมกับไวยากรณ์ FilterExpression ใหม่มากกว่า ฉันสงสัยว่าปัญหาเกิดขึ้นกับแอตทริบิวต์หลายค่าที่มี "N:" อยู่ในชื่อ ดูเหมือนจะไม่ใกล้เคียงกับรูปแบบลวด หากต้องการใช้นิพจน์ตัวกรอง "ใหม่" ควรสร้าง ExpressionAttributeNames และ ExpressionAttributeValues ​​เพื่อบอก AWS SDK เกี่ยวกับคุณลักษณะสำหรับตัวกรอง addExpressionAttributeNamesEntry และ addExpressionAttributeValuesEntryhttp://docs.aws.amazon.com/AWSJavaSDK/ล่าสุด/javadoc/com/amazonaws/services/dynamodbv2/datamodeling/DynamoDBScanExpression.html นอกจากนี้ ฉันจะเสียใจหากไม่ได้ชี้ให้เห็นว่าการสแกนไม่ใช่การกระทำของ API ที่ถูกต้องสำหรับการสืบค้นนี้ แบบสอบถามคือการกระทำที่ถูกต้อง testName ควรใช้กับ Query ด้วย KeyConditionExpression เพื่อจำกัดการค้นหาให้แคบลงจนถึงพาร์ติชันที่ถูกต้อง และควรเพิ่มการแก้ไขให้เหมือนกันด้วยไวยากรณ์ BETWEEN การสแกนมีไว้สำหรับการสำรองข้อมูลและการดำเนินการในเบื้องหลัง และในกรณีนี้ สามารถใช้สคีมาดัชนีของลูกค้าร่วมกับ Query เพื่อจำกัดการค้นหาให้แคบลงได้ ข้อควรระวังเกี่ยวกับการใช้การสแกน นี่คือแนวทางปฏิบัติที่ดีที่สุดขั้นพื้นฐาน:http://docs.aws.amazon.com/amazondynamodb/latest/developerguide/QueryAndScanGuidelines.html

ดังนั้นฉันจึงใช้ Query แทน:

    Map<String, AttributeValue> eav = new HashMap<String, AttributeValue>();
    eav.put(":v1", new AttributeValue().withS(testName));
    eav.put(":v2", new AttributeValue().withS(version));
    eav.put(":v3", new AttributeValue().withN(String.valueOf(minRev)));
    eav.put(":v4", new AttributeValue().withN(String.valueOf(maxRev)));

    final DynamoDBQueryExpression<ValidationReport> query = new DynamoDBQueryExpression<>();
    query.withKeyConditionExpression("testName = :v1");
    query.withFilterExpression("buildVersion = :v2 and revision BETWEEN :v3 AND :v4");
    query.setConsistentRead(false);
    query.withExpressionAttributeValues(eav);
    return getMapper().query(ValidationReport.class, query);`

โปรดทราบว่าเมื่อใช้ AttributeValue จะมีความแตกต่างค่อนข้างมากระหว่างสิ่งต่อไปนี้:

new AttributeValue().withS("SomeStringValue")
new AttributeValue().withN("SomeNumber")

ซึ่งเป็นสิ่งที่ฉันขาดหายไป

person Ohad Benita    schedule 25.05.2017