@@ -51,11 +51,19 @@ private[dynamodb] class TableConnector(tableName: String, totalSegments: Int, pa
51
51
val targetCapacity = parameters.getOrElse(" targetCapacity" , " 1" ).toDouble
52
52
val readFactor = if (consistentRead) 1 else 2
53
53
54
+ // Provisioned or on-demand throughput.
55
+ val readThroughput = Option (desc.getProvisionedThroughput.getReadCapacityUnits)
56
+ .filter(_ > 0 ).map(_.longValue())
57
+ .getOrElse(100L )
58
+ val writeThroughput = Option (desc.getProvisionedThroughput.getWriteCapacityUnits)
59
+ .filter(_ > 0 ).map(_.longValue())
60
+ .getOrElse(100L )
61
+
54
62
// Rate limit calculation.
55
63
val tableSize = desc.getTableSizeBytes
56
64
val avgItemSize = tableSize.toDouble / desc.getItemCount
57
- val readCapacity = desc.getProvisionedThroughput.getReadCapacityUnits * targetCapacity
58
- val writeCapacity = desc.getProvisionedThroughput.getWriteCapacityUnits * targetCapacity
65
+ val readCapacity = readThroughput * targetCapacity
66
+ val writeCapacity = writeThroughput * targetCapacity
59
67
60
68
val readLimit = readCapacity / totalSegments
61
69
val itemLimit = ((bytesPerRCU / avgItemSize * readLimit).toInt * readFactor) max 1
@@ -100,26 +108,24 @@ private[dynamodb] class TableConnector(tableName: String, totalSegments: Int, pa
100
108
val rateLimiter = RateLimiter .create(writeLimit max 1 )
101
109
val client = getDynamoDBClient(region)
102
110
103
-
104
-
105
111
// For each item.
106
112
items.foreach(row => {
107
- val key : Map [String ,AttributeValue ] = keySchema match {
108
- case KeySchema (hashKey, None ) => Map (hashKey -> mapValueToAttributeValue(row(hashKeyIndex), schema(hashKey).dataType))
113
+ val key : Map [String , AttributeValue ] = keySchema match {
114
+ case KeySchema (hashKey, None ) => Map (hashKey -> mapValueToAttributeValue(row(hashKeyIndex), schema(hashKey).dataType))
109
115
case KeySchema (hashKey, Some (rangeKey)) =>
110
- Map (hashKey -> mapValueToAttributeValue(row(hashKeyIndex), schema(hashKey).dataType),
111
- rangeKey-> mapValueToAttributeValue(row(rangeKeyIndex.get), schema(rangeKey).dataType))
116
+ Map (hashKey -> mapValueToAttributeValue(row(hashKeyIndex), schema(hashKey).dataType),
117
+ rangeKey -> mapValueToAttributeValue(row(rangeKeyIndex.get), schema(rangeKey).dataType))
112
118
113
119
}
114
- val nonNullColumnIndices = columnIndices.filter(c => row(c._2)!= null )
120
+ val nonNullColumnIndices = columnIndices.filter(c => row(c._2) != null )
115
121
val updateExpression = s " SET ${nonNullColumnIndices.map(c => s " ${c._1}=: ${c._1}" ).mkString(" , " )}"
116
122
val expressionAttributeValues = nonNullColumnIndices.map(c => s " : ${c._1}" -> mapValueToAttributeValue(row(c._2), schema(c._1).dataType)).toMap.asJava
117
123
val updateItemReq = new UpdateItemRequest ()
118
124
.withReturnConsumedCapacity(ReturnConsumedCapacity .TOTAL )
119
- .withTableName(tableName)
120
- .withKey(key.asJava)
121
- .withUpdateExpression(updateExpression)
122
- .withExpressionAttributeValues(expressionAttributeValues)
125
+ .withTableName(tableName)
126
+ .withKey(key.asJava)
127
+ .withUpdateExpression(updateExpression)
128
+ .withExpressionAttributeValues(expressionAttributeValues)
123
129
124
130
val updateItemResult = client.updateItem(updateItemReq)
125
131
@@ -191,7 +197,7 @@ private[dynamodb] class TableConnector(tableName: String, totalSegments: Int, pa
191
197
192
198
private def mapValueToAttributeValue (element : Any , elementType : DataType ): AttributeValue = {
193
199
elementType match {
194
- case ArrayType (innerType, _) => new AttributeValue ().withL(element.asInstanceOf [Seq [_]].map(e => mapValueToAttributeValue(e, innerType)):_* )
200
+ case ArrayType (innerType, _) => new AttributeValue ().withL(element.asInstanceOf [Seq [_]].map(e => mapValueToAttributeValue(e, innerType)): _* )
195
201
case MapType (keyType, valueType, _) =>
196
202
if (keyType != StringType ) throw new IllegalArgumentException (
197
203
s " Invalid Map key type ' ${keyType.typeName}'. DynamoDB only supports String as Map key type. " )
@@ -200,7 +206,7 @@ private[dynamodb] class TableConnector(tableName: String, totalSegments: Int, pa
200
206
201
207
case StructType (fields) =>
202
208
val row = element.asInstanceOf [Row ]
203
- new AttributeValue ().withM( (fields.indices map { i =>
209
+ new AttributeValue ().withM((fields.indices map { i =>
204
210
fields(i).name -> mapValueToAttributeValue(row(i), fields(i).dataType)
205
211
}).toMap.asJava)
206
212
case StringType => new AttributeValue ().withS(element.asInstanceOf [String ])
@@ -224,8 +230,9 @@ private[dynamodb] class TableConnector(tableName: String, totalSegments: Int, pa
224
230
handleBatchWriteResponse(client, rateLimiter)(newResponse)
225
231
}
226
232
}
233
+
227
234
private def handleUpdateItemResult (rateLimiter : RateLimiter )
228
- (result : UpdateItemResult ): Unit = {
235
+ (result : UpdateItemResult ): Unit = {
229
236
// Rate limit on write capacity.
230
237
if (result.getConsumedCapacity != null ) {
231
238
rateLimiter.acquire(result.getConsumedCapacity.getCapacityUnits.toInt)
0 commit comments