package org.xmlsh.aws;
import java.io.IOException;
import java.util.ArrayList;
import java.util.List;
import java.util.Map;
import javax.xml.stream.XMLStreamException;
import org.xmlsh.aws.util.AWSDDBCommand;
import org.xmlsh.core.CoreException;
import org.xmlsh.core.Options;
import org.xmlsh.core.UnexpectedException;
import org.xmlsh.core.XValue;
import com.amazonaws.AmazonClientException;
import com.amazonaws.services.dynamodbv2.model.AttributeValue;
import com.amazonaws.services.dynamodbv2.model.QueryRequest;
import com.amazonaws.services.dynamodbv2.model.QueryResult;
import com.amazonaws.services.dynamodbv2.model.Select;
import net.sf.saxon.s9api.SaxonApiException;
public class ddbQuery extends AWSDDBCommand {
private int kLIMIT = 100;
/**
* @param args
* @throws IOException
*/
@Override
public int run(List<XValue> args) throws Exception {
Options opts = getOptions(sTABLE_OPTIONS, sKEY_OPTIONS, sRETURN_OPTIONS,
sCONSISTANT_OPTS,
sDOCUMENT_OPTS, sATTR_EXPR_OPTIONS,
"limit:,query:,filter=filter-expression:,select:,index-name:,key-condition-expression:,projection-expression:");
parseOptions(opts, args);
args = opts.getRemainingArgs();
setSerializeOpts(this.getSerializeOpts(opts));
try {
getDDBClient(opts);
} catch (UnexpectedException e) {
usage(e.getLocalizedMessage());
return 1;
}
int ret = -1;
ret = query(opts);
return ret;
}
private int query(Options opts)
throws IOException, XMLStreamException, SaxonApiException, CoreException {
boolean bConsistantRead = opts.hasOpt("consistant");
String filterExpression = opts.getOptString("filter", null);
Map<String, AttributeValue> exclusiveStartKey = null;
QueryRequest queryRequest = new QueryRequest()
.withTableName(opts.getOptStringRequired("table"))
.withConsistentRead(bConsistantRead)
.withExpressionAttributeNames(parseAttrNameExprs(opts))
.withExpressionAttributeValues(parseAttrValueExprs(opts));
int userLimit = opts.getOptInt("limit", 0);
if(userLimit > 0)
queryRequest.setLimit(Math.min(userLimit, kLIMIT));
if(opts.hasOpt("index-name"))
queryRequest.setIndexName(opts.getOptStringRequired("index-name"));
if(opts.hasOpt("key-condition-expression"))
queryRequest.setKeyConditionExpression(
opts.getOptStringRequired("key-condition-expression"));
if(opts.hasOpt("projection-expression"))
queryRequest.setProjectionExpression(
opts.getOptStringRequired("projection-expression"));
if(filterExpression != null)
queryRequest.setFilterExpression(filterExpression);
if(opts.hasOpt("select"))
queryRequest.setSelect(parseSelect(opts.getOptStringRequired("select")));
ArrayList<RequestMetrics> metrics = new ArrayList<RequestMetrics>();
// start result eary due to looping
boolean bStarted = false;
do {
traceCall("query");
if(exclusiveStartKey != null)
queryRequest.setExclusiveStartKey(exclusiveStartKey);
QueryResult result;
try {
result = getAWSClient().query(queryRequest);
} catch (AmazonClientException e) {
return handleException(e);
} finally {
if(bStarted)
endResult();
}
if(!bStarted)
bStarted = startResult();
for(Map<String, AttributeValue> item : result.getItems())
writeItem(item);
metrics.add(new RequestMetrics(result.getCount(),
result.getScannedCount(), result.getConsumedCapacity()));
exclusiveStartKey = result.getLastEvaluatedKey();
} while(exclusiveStartKey != null);
writeMetrics(metrics);
endResult();
return 0;
}
private Select parseSelect(String select) {
return Select.fromValue(select.toUpperCase());
}
}