【问题标题】:One or more parameter values were invalid dynamoDB + Java一个或多个参数值无效 dynamoDB + Java
【发布时间】:2018-11-29 01:12:05
【问题描述】:

我正在尝试在 DynamoDB 中创建一个表。我可以使用 DynamoDB 控制台,但我更喜欢通过 Java 来完成。但是下面的代码给出了异常,我找不到原因..

请检查以下代码..

String serviceRef = "ServiceRef";
ArrayList<KeySchemaElement> keySchema = new ArrayList<KeySchemaElement>();
keySchema.add(new KeySchemaElement()
        .withAttributeName("ServiceID")
        .withKeyType(KeyType.HASH));

ArrayList<AttributeDefinition> attributeDefinitions = new ArrayList<AttributeDefinition>();
attributeDefinitions.add(new AttributeDefinition()
        .withAttributeName("ServiceID")
        .withAttributeType(ScalarAttributeType.N)
        .withAttributeName("ServiceName")
        .withAttributeType(ScalarAttributeType.S)
        .withAttributeName("CreatedDateUTC")
        .withAttributeType(ScalarAttributeType.N)
        .withAttributeName("UpdatedDateUTC")
        .withAttributeType(ScalarAttributeType.N)
        .withAttributeName("IsDeleted")
        .withAttributeType(ScalarAttributeType.B));

CreateTableRequest request = new CreateTableRequest()
        .withTableName(serviceRef)
        .withKeySchema(keySchema)
        .withAttributeDefinitions(attributeDefinitions)
        .withProvisionedThroughput(
                new ProvisionedThroughput().withReadCapacityUnits(5L).withWriteCapacityUnits(1L));

System.out.println("Issuing create table request for: " + serviceRef);
dynamoDBClient.createTable(request);
System.out.println("Waiting for table Name: " + serviceRef + " to be created...");
try {
    Tables.awaitTableToBecomeActive(dynamoDBClient, serviceRef);
} catch (InterruptedException e) {
    e.printStackTrace();
}

这段代码有什么问题? 它给出的错误是 -

Exception in thread "main" com.amazonaws.AmazonServiceException: One or more parameter values were invalid: Some index key attributes are not defined in AttributeDefinitions. Keys: [ServiceID], AttributeDefinitions: [IsDeleted] (Service: AmazonDynamoDBv2; Status Code: 400; Error Code: ValidationException; Request ID: SA8P5UUVH37T8P1R7F6VVPP357VV4KQNSO5AEMVJF66Q9ASUAAJG)
    at com.amazonaws.http.AmazonHttpClient.handleErrorResponse(AmazonHttpClient.java:1219)
    at com.amazonaws.http.AmazonHttpClient.executeOneRequest(AmazonHttpClient.java:803)
    at com.amazonaws.http.AmazonHttpClient.executeHelper(AmazonHttpClient.java:505)
    at com.amazonaws.http.AmazonHttpClient.execute(AmazonHttpClient.java:317)
    at com.amazonaws.services.dynamodbv2.AmazonDynamoDBClient.invoke(AmazonDynamoDBClient.java:1803)
    at com.amazonaws.services.dynamodbv2.AmazonDynamoDBClient.createTable(AmazonDynamoDBClient.java:832)
    at com.rit.randemmiddleware.controller.TestMain.main(TestMain.java:38)

还有在空间中使用什么

Tables.awaitTableToBecomeActive(dynamoDBClient, serviceRef);

因为它显示已弃用。

【问题讨论】:

  • 要测试表是否处于活动状态,javadoc 建议您使用 TableUtils.waitUntilActive(AmazonDynamoDB, String)。

标签: java amazon-dynamodb


【解决方案1】:

您误用了 AttributeDefinition 方法链接。您错误地创建了一个属性定义,其名称一直在更改(从“ServiceID”到“ServiceName”再到“CreatedDateUTC”等,最后到“IsDeleted”)。

您需要提供属性定义的数组或集合。例如:

attributeDefinitions.add(
    new AttributeDefinition()
        .withAttributeName("ServiceID")
        .withAttributeType(ScalarAttributeType.N),
    new AttributeDefinition()
        .withAttributeName("ServiceName")
        .withAttributeType(ScalarAttributeType.S),
    ...
);

【讨论】:

  • 非常感谢,我犯了一个非常基本的错误。现在相应地更改我的代码后,我可以创建我的表。
【解决方案2】:

还有必要提到 AttributeDefinitions 应该只包含表 decalration/description (KeySchema 和 GlobalSecondaryIndexes)所必需的列。因为 DynamoDB 是无模式的。

如果您尝试创建一个具有比索引所需属性更多的表,您将收到如下错误:Exception in thread "main" com.amazonaws.services.dynamodbv2.model.AmazonDynamoDBException: One or more parameter values were invalid: Some AttributeDefinitions are not used. AttributeDefinitions: [Precipitation, Temperature, Rank, ID, Date, Location], keys used: [ID, Date, Location]

我带着以下箱子来到这里:

属性定义:

attributeDefinitions.add(new AttributeDefinition("ID", "S"));
attributeDefinitions.add(new AttributeDefinition("Location", "S"));
attributeDefinitions.add(new AttributeDefinition("Date", "S"));
attributeDefinitions.add(new AttributeDefinition("Precipitation", "N"));
attributeDefinitions.add(new AttributeDefinition("Temperature", "N"));
attributeDefinitions.add(new AttributeDefinition("Rank", "N"));

密钥架构:

tableKeySchema.add(new KeySchemaElement("ID", KeyType.HASH))

全球二级索引:

GlobalSecondaryIndex locationDateIndex = new GlobalSecondaryIndex()
            .withIndexName("Location_Date-Index")
            .withProjection(new 
Projection().withProjectionType(ProjectionType.ALL))
            .withProvisionedThroughput(new ProvisionedThroughput(10l, 1l))
            .withKeySchema(new KeySchemaElement("Location", KeyType.HASH))
            .withKeySchema(new KeySchemaElement("Date", KeyType.RANGE));

创建表请求:

CreateTableRequest createTableRequest = new CreateTableRequest()
    .withTableName(tableName)
    .withProvisionedThroughput(new ProvisionedThroughput(5L, 1L))
    .withAttributeDefinitions(attributeDefinitions)
    .withKeySchema(tableKeySchema)
    .withGlobalSecondaryIndexes(locationDateIndex);

上面的错误:

Exception in thread "main" com.amazonaws.services.dynamodbv2.model.AmazonDynamoDBException: 
One or more parameter values were invalid: Some AttributeDefinitions are not used. 
AttributeDefinitions: [Precipitation, Temperature, Rank, ID, Date, Location], 
keys used: [ID, Date, Location] (Service: AmazonDynamoDBv2; Status Code: 400; 
Error Code: ValidationException; Request ID: ...)

减少属性定义列表解决了我的问题:

attributeDefinitions.add(new AttributeDefinition("ID", "S"));
attributeDefinitions.add(new AttributeDefinition("Location", "S"));
attributeDefinitions.add(new AttributeDefinition("Date", "S"));

PS:我在这里回答是因为此页面与我在 Google 中的请求相关。

【讨论】:

  • 感谢您花时间回答这个问题,这帮助我解决了我的问题。
【解决方案3】:

您只创建了一个AttributeDefinition。您的方法链接只生成一个AttributeDefinition,而不是它们的列表。您还只需为您的表或 GSI 的 KeySchema 的属性创建一个 AttributeDefinition

attributeDefinitions.add(new AttributeDefinition()
        .withAttributeName("ServiceID")
        .withAttributeType(ScalarAttributeType.N));

对于您的弃用问题,请查看TablesJavadoc

已弃用。

使用TableUtils

TablesUtils.waitUntilActive(dynamoDBClient, serviceRef);

【讨论】:

  • 感谢您的回复。我现在可以创建我的代码了。但从那我得到了另一个问题。如果我创建一个空表会怎样?它会变得活跃吗?我得到的当前异常是......线程“主”com.amazonaws.AmazonClientException 中的异常:Table ServiceRef 从未在 com.amazonaws.services.dynamodbv2.util.TableUtils.waitUntilActive(TableUtils.java:150) 在 com 处激活.amazonaws.services.dynamodbv2.util.TableUtils.waitUntilActive(TableUtils.java:117) 在 com.rit.randemmiddleware.controller.TestMain.main(TestMain.java:47)
  • @GourabBanerjee 您是在使用 DynamoDB Local,还是针对端点运行?
  • 没有。我使用凭证直接连接到 Amazon SQS。是的,我使用 US_WEST_2 作为区域端点。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-05-07
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2020-11-05
  • 1970-01-01
相关资源
最近更新 更多