Author: reschke
Date: Sun Nov 20 13:52:46 2016
New Revision: 1770561
URL: http://svn.apache.org/viewvc?rev=1770561&view=rev
Log:
OAK-3984: RDBDocumentStore: implement new conditional remove method
(slightly refactor code to re-use condition support)
Modified:
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStore.java
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStoreJDBC.java
Modified:
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStore.java
URL:
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStore.java?rev=1770561&r1=1770560&r2=1770561&view=diff
==============================================================================
---
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStore.java
(original)
+++
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStore.java
Sun Nov 20 13:52:46 2016
@@ -279,26 +279,26 @@ public class RDBDocumentStore implements
}
@Override
- public <T extends Document> int remove(Collection<T> collection,
- String indexedProperty, long startValue,
long endValue)
+ public <T extends Document> int remove(Collection<T> collection, String
indexedProperty, long startValue, long endValue)
throws DocumentStoreException {
- int num = 0;
try {
- num = delete(collection, indexedProperty, startValue, endValue);
+ List<QueryCondition> conditions = new ArrayList<QueryCondition>();
+ conditions.add(new QueryCondition(indexedProperty, ">",
startValue));
+ conditions.add(new QueryCondition(indexedProperty, "<", endValue));
+ return deleteWithCondition(collection, conditions);
} finally {
- if (num > 0 && collection == Collection.NODES) {
- // this method is currently being used only for Journal
collection while GC.
- // But, to keep sanctity of the API, we need to acknowledge
that Nodes collection
- // could've been used. But, in this signature, there's no
useful way to invalidate
+ if (collection == Collection.NODES) {
+ // this method is currently being used only for Journal
+ // collection while GC. But, to keep sanctity of the API, we
+ // need to acknowledge that Nodes collection could've been
used.
+ // But, in this signature, there's no useful way to invalidate
// cache.
// So, we use the hammer for this task
invalidateCache();
}
}
- return num;
}
-
@Override
public <T extends Document> boolean create(Collection<T> collection,
List<UpdateOp> updateOps) {
return internalCreate(collection, updateOps);
@@ -1587,18 +1587,16 @@ public class RDBDocumentStore implements
return numDeleted;
}
- private <T extends Document> int delete(Collection<T> collection,
- String indexedProperty, long
startValue, long endValue) {
+ private <T extends Document> int deleteWithCondition(Collection<T>
collection, List<QueryCondition> conditions) {
int numDeleted = 0;
RDBTableMetaData tmd = getTable(collection);
Connection connection = null;
try {
connection = this.ch.getRWConnection();
- numDeleted = db.delete(connection, tmd, indexedProperty,
startValue, endValue);
+ numDeleted = db.deleteWithCondition(connection, tmd, conditions);
connection.commit();
} catch (Exception ex) {
- throw DocumentStoreException.convert(ex, "deleting " + collection
+ ": " +
- indexedProperty + " in (" + startValue + ", " + endValue +
")");
+ throw DocumentStoreException.convert(ex, "deleting " + collection
+ ": " + conditions);
} finally {
this.ch.closeConnection(connection);
}
Modified:
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStoreJDBC.java
URL:
http://svn.apache.org/viewvc/jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStoreJDBC.java?rev=1770561&r1=1770560&r2=1770561&view=diff
==============================================================================
---
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStoreJDBC.java
(original)
+++
jackrabbit/oak/trunk/oak-core/src/main/java/org/apache/jackrabbit/oak/plugins/document/rdb/RDBDocumentStoreJDBC.java
Sun Nov 20 13:52:46 2016
@@ -225,18 +225,22 @@ public class RDBDocumentStoreJDBC {
}
}
- public int delete(Connection connection, RDBTableMetaData tmd, String
property, long startValue, long endValue)
+ public int deleteWithCondition(Connection connection, RDBTableMetaData
tmd, List<QueryCondition> conditions)
throws SQLException, DocumentStoreException {
- if (!MODIFIED.equals(property)) {
- throw new DocumentStoreException("Unsupported condition: " +
- property + " in (" + startValue + ", " + endValue +
")");
+
+ StringBuilder query = new StringBuilder("delete from " +
tmd.getName());
+
+ String whereClause = buildWhereClause(null, null, null, conditions);
+ if (whereClause.length() != 0) {
+ query.append(" where ").append(whereClause);
}
- PreparedStatement stmt = connection.prepareStatement("delete from " +
tmd.getName() +
- " where MODIFIED > ? AND MODIFIED < ?");
+
+ PreparedStatement stmt = connection.prepareStatement(query.toString());
try {
- int i = 1;
- stmt.setLong(i++, startValue);
- stmt.setLong(i++, endValue);
+ int si = 1;
+ for (QueryCondition cond : conditions) {
+ stmt.setLong(si++, cond.getValue());
+ }
return stmt.executeUpdate();
} finally {
stmt.close();
@@ -443,71 +447,17 @@ public class RDBDocumentStoreJDBC {
}
}
- private final static Map<String, String> INDEXED_PROP_MAPPING;
- static {
- Map<String, String> tmp = new HashMap<String, String>();
- tmp.put(MODIFIED, "MODIFIED");
- tmp.put(NodeDocument.HAS_BINARY_FLAG, "HASBINARY");
- tmp.put(NodeDocument.DELETED_ONCE, "DELETEDONCE");
- INDEXED_PROP_MAPPING = Collections.unmodifiableMap(tmp);
- }
-
- private final static Set<String> SUPPORTED_OPS;
- static {
- Set<String> tmp = new HashSet<String>();
- tmp.add(">=");
- tmp.add(">");
- tmp.add("<=");
- tmp.add("<");
- tmp.add("=");
- SUPPORTED_OPS = Collections.unmodifiableSet(tmp);
- }
-
@Nonnull
public List<RDBRow> query(Connection connection, RDBTableMetaData tmd,
String minId, String maxId,
List<String> excludeKeyPatterns, List<QueryCondition> conditions,
int limit) throws SQLException {
long start = System.currentTimeMillis();
StringBuilder selectClause = new StringBuilder();
- StringBuilder whereClause = new StringBuilder();
if (limit != Integer.MAX_VALUE && this.dbInfo.getFetchFirstSyntax() ==
FETCHFIRSTSYNTAX.TOP) {
selectClause.append("TOP " + limit + " ");
}
selectClause.append("ID, MODIFIED, MODCOUNT, CMODCOUNT, HASBINARY,
DELETEDONCE, DATA, BDATA from ").append(tmd.getName());
- // dynamically build where clause
- String whereSep = "";
- if (minId != null) {
- whereClause.append("ID > ?");
- whereSep = " and ";
- }
- if (maxId != null) {
- whereClause.append(whereSep).append("ID < ?");
- whereSep = " and ";
- }
- if (!excludeKeyPatterns.isEmpty()) {
- whereClause.append(whereSep);
- whereSep = " and ";
- whereClause.append("not (");
- for (int i = 0; i < excludeKeyPatterns.size(); i++) {
- whereClause.append(i == 0 ? "" : " or ");
- whereClause.append("ID like ?");
- }
- whereClause.append(")");
- }
- for (QueryCondition cond : conditions) {
- String op = cond.getOperator();
- if (!SUPPORTED_OPS.contains(op)) {
- throw new DocumentStoreException("unsupported operator: " +
op);
- }
- String indexedProperty = cond.getPropertyName();
- String column = INDEXED_PROP_MAPPING.get(indexedProperty);
- if (column != null) {
- whereClause.append(whereSep).append(column).append("
").append(op).append(" ?");
- whereSep = " and ";
- } else {
- throw new DocumentStoreException("unsupported indexed
property: " + indexedProperty);
- }
- }
+ String whereClause = buildWhereClause(minId, maxId,
excludeKeyPatterns, conditions);
StringBuilder query = new StringBuilder();
query.append("select ").append(selectClause);
@@ -753,6 +703,65 @@ public class RDBDocumentStoreJDBC {
}
}
+ private final static Map<String, String> INDEXED_PROP_MAPPING;
+ static {
+ Map<String, String> tmp = new HashMap<String, String>();
+ tmp.put(MODIFIED, "MODIFIED");
+ tmp.put(NodeDocument.HAS_BINARY_FLAG, "HASBINARY");
+ tmp.put(NodeDocument.DELETED_ONCE, "DELETEDONCE");
+ INDEXED_PROP_MAPPING = Collections.unmodifiableMap(tmp);
+ }
+
+ private final static Set<String> SUPPORTED_OPS;
+ static {
+ Set<String> tmp = new HashSet<String>();
+ tmp.add(">=");
+ tmp.add(">");
+ tmp.add("<=");
+ tmp.add("<");
+ tmp.add("=");
+ SUPPORTED_OPS = Collections.unmodifiableSet(tmp);
+ }
+
+ private static String buildWhereClause(String minId, String maxId,
List<String> excludeKeyPatterns, List<QueryCondition> conditions) {
+ StringBuilder result = new StringBuilder();
+
+ String whereSep = "";
+ if (minId != null) {
+ result.append("ID > ?");
+ whereSep = " and ";
+ }
+ if (maxId != null) {
+ result.append(whereSep).append("ID < ?");
+ whereSep = " and ";
+ }
+ if (excludeKeyPatterns != null && !excludeKeyPatterns.isEmpty()) {
+ result.append(whereSep);
+ whereSep = " and ";
+ result.append("not (");
+ for (int i = 0; i < excludeKeyPatterns.size(); i++) {
+ result.append(i == 0 ? "" : " or ");
+ result.append("ID like ?");
+ }
+ result.append(")");
+ }
+ for (QueryCondition cond : conditions) {
+ String op = cond.getOperator();
+ if (!SUPPORTED_OPS.contains(op)) {
+ throw new DocumentStoreException("unsupported operator: " +
op);
+ }
+ String indexedProperty = cond.getPropertyName();
+ String column = INDEXED_PROP_MAPPING.get(indexedProperty);
+ if (column != null) {
+ result.append(whereSep).append(column).append("
").append(op).append(" ?");
+ whereSep = " and ";
+ } else {
+ throw new DocumentStoreException("unsupported indexed
property: " + indexedProperty);
+ }
+ }
+ return result.toString();
+ }
+
private static String getIdFromRS(RDBTableMetaData tmd, ResultSet rs, int
idx) throws SQLException {
if (tmd.isIdBinary()) {
try {