001/* 002 * (C) Copyright 2014-2017 Nuxeo (http://nuxeo.com/) and others. 003 * 004 * Licensed under the Apache License, Version 2.0 (the "License"); 005 * you may not use this file except in compliance with the License. 006 * You may obtain a copy of the License at 007 * 008 * http://www.apache.org/licenses/LICENSE-2.0 009 * 010 * Unless required by applicable law or agreed to in writing, software 011 * distributed under the License is distributed on an "AS IS" BASIS, 012 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 013 * See the License for the specific language governing permissions and 014 * limitations under the License. 015 * 016 * Contributors: 017 * Florent Guillaume 018 */ 019package org.nuxeo.ecm.core.storage.dbs; 020 021import java.io.Serializable; 022import java.util.Collection; 023import java.util.List; 024import java.util.Map; 025import java.util.Set; 026import java.util.stream.Stream; 027 028import org.nuxeo.ecm.core.api.PartialList; 029import org.nuxeo.ecm.core.api.ScrollResult; 030import org.nuxeo.ecm.core.blob.BlobManager; 031import org.nuxeo.ecm.core.model.LockManager; 032import org.nuxeo.ecm.core.model.Repository; 033import org.nuxeo.ecm.core.query.sql.model.OrderByClause; 034import org.nuxeo.ecm.core.storage.FulltextConfiguration; 035import org.nuxeo.ecm.core.storage.State; 036import org.nuxeo.ecm.core.storage.State.StateDiff; 037import org.nuxeo.ecm.core.storage.dbs.DBSTransactionState.ChangeTokenUpdater; 038 039/** 040 * Interface for a {@link Repository} for Document-Based Storage. 041 * 042 * @since 5.9.4 043 */ 044public interface DBSRepository extends Repository, LockManager { 045 046 /** 047 * Gets the blob manager. 048 * 049 * @return the blob manager. 050 */ 051 BlobManager getBlobManager(); 052 053 /** 054 * Gets the fulltext configuration. 055 * 056 * @return the fulltext configuration 057 * @since 7.10-HF04, 8.1 058 */ 059 FulltextConfiguration getFulltextConfiguration(); 060 061 /** 062 * Checks if fulltext indexing (and search) is disabled. 063 * 064 * @return {@code true} if fulltext indexing is disabled, {@code false} if it is enabled 065 * @since 7.1, 6.0-HF02 066 */ 067 boolean isFulltextDisabled(); 068 069 /** 070 * Checks if fulltext search is disabled. 071 * 072 * @return {@code true} if fulltext search is disabled, {@code false} if it is enabled 073 * @since 10.2 074 */ 075 boolean isFulltextSearchDisabled(); 076 077 078 /** 079 * Checks if database-managed document change tokens are enabled. 080 * 081 * @return {@code true} if the database maintains document change tokens 082 * @since 9.1 083 */ 084 boolean isChangeTokenEnabled(); 085 086 /** 087 * Gets the root id. 088 * 089 * @return the root id. 090 */ 091 String getRootId(); 092 093 /** 094 * Generates a new id for a document. 095 * 096 * @return the new id 097 */ 098 String generateNewId(); 099 100 /** 101 * Reads the state of a document. 102 * 103 * @param id the document id 104 * @return the document state, or {@code null} if not found 105 */ 106 State readState(String id); 107 108 /** 109 * Reads the partial state of a document. 110 * 111 * @param id the document id 112 * @param keys the keys to read 113 * @return the document partial state, or {@code null} if not found 114 * @since 9.10 115 */ 116 default State readPartialState(String id, Collection<String> keys) { 117 // overrides should optimize to only return the required keys and nothing more 118 return readState(id); 119 } 120 121 /** 122 * Reads the states of several documents. 123 * <p> 124 * The returned states may be in a different order than the ids. 125 * 126 * @param ids the document ids 127 * @return the document states, an element by be {@code null} if not found 128 */ 129 List<State> readStates(List<String> ids); 130 131 /** 132 * Creates a document. 133 * 134 * @param state the document state 135 */ 136 void createState(State state); 137 138 /** 139 * Creates documents. 140 * 141 * @param states the document states 142 */ 143 default void createStates(List<State> states) { 144 states.forEach(this::createState); 145 } 146 147 /** 148 * Updates a document. 149 * 150 * @param id the document id 151 * @param diff the diff to apply 152 * @param changeTokenUpdater how to get and update the change token (may be {@code null}) 153 */ 154 void updateState(String id, StateDiff diff, ChangeTokenUpdater changeTokenUpdater); 155 156 /** 157 * Deletes a set of document. 158 * 159 * @param ids the document ids 160 */ 161 void deleteStates(Set<String> ids); 162 163 /** 164 * Reads the state of a child document. 165 * 166 * @param parentId the parent document id 167 * @param name the name of the child 168 * @param ignored a set of document ids that should not be considered 169 * @return the state of the child document, or {@code null} if not found 170 */ 171 State readChildState(String parentId, String name, Set<String> ignored); 172 173 /** 174 * Checks if a document has a child with the given name 175 * 176 * @param parentId the parent document id 177 * @param name the name of the child 178 * @param ignored a set of document ids that should not be considered 179 * @return {@code true} if the child exists, {@code false} if not 180 */ 181 boolean hasChild(String parentId, String name, Set<String> ignored); 182 183 /** 184 * Queries the repository for documents having key = value. 185 * 186 * @param key the key 187 * @param value the value 188 * @param ignored a set of document ids that should not be considered 189 * @return the document states matching the query 190 */ 191 List<State> queryKeyValue(String key, Object value, Set<String> ignored); 192 193 /** 194 * Queries the repository for documents having key1 = value1 and key2 = value2. 195 * 196 * @param key1 the first key 197 * @param value1 the first value 198 * @param key2 the second key 199 * @param value2 the second value 200 * @param ignored a set of document ids that should not be considered 201 * @return the document states matching the query 202 */ 203 List<State> queryKeyValue(String key1, Object value1, String key2, Object value2, Set<String> ignored); 204 205 /** 206 * Returns a stream of descendants from a given root document, in no particular order. This does not include 207 * information about the root document itself. 208 * <p> 209 * THE STREAM MUST BE CLOSED WHEN DONE to release resources. 210 * 211 * @param id the root document id 212 * @param keys what to collect about the descendants in addition to their ids 213 * @return a stream of {@link State}s; THE STREAM MUST BE CLOSED WHEN DONE 214 * @since 9.3 215 */ 216 Stream<State> getDescendants(String id, Set<String> keys); 217 218 /** 219 * Returns a stream of descendants from a given root document, in no particular order. This does not include 220 * information about the root document itself. 221 * <p> 222 * THE STREAM MUST BE CLOSED WHEN DONE to release resources. 223 * 224 * @param id the root document id 225 * @param keys what to collect about the descendants in addition to their ids 226 * @param limit the maximum number of descendants to return 227 * @return a stream of {@link State}s; THE STREAM MUST BE CLOSED WHEN DONE 228 * @since 9.10 229 */ 230 default Stream<State> getDescendants(String id, Set<String> keys, int limit) { 231 // limit unused by default, override for a more efficient implementation 232 return getDescendants(id, keys); 233 } 234 235 /** 236 * Queries the repository to check if there are documents having key = value. 237 * 238 * @param key the key 239 * @param value the value 240 * @param ignored a set of document ids that should not be considered 241 * @return {@code true} if the query matches at least one document, {@code false} if the query matches nothing 242 */ 243 boolean queryKeyValuePresence(String key, String value, Set<String> ignored); 244 245 /** 246 * Queries the repository for documents matching a NXQL query, and returns a projection of the documents. 247 * 248 * @param evaluator the map-based evaluator for the query 249 * @param orderByClause an ORDER BY clause 250 * @param distinctDocuments {@code true} if the projection should return a maximum of one row per document 251 * @param limit the limit on the number of documents to return 252 * @param offset the offset in the list of documents to return 253 * @param countUpTo if {@code -1}, count the total size without offset/limit.<br> 254 * If {@code 0}, don't count the total size, set it to {@code -1} .<br> 255 * If {@code n}, count the total number if there are less than n documents otherwise set the total size 256 * to {@code -2}. 257 * @return a partial list of maps containing the NXQL projections requested, and the total size according to 258 * countUpTo 259 */ 260 PartialList<Map<String, Serializable>> queryAndFetch(DBSExpressionEvaluator evaluator, OrderByClause orderByClause, 261 boolean distinctDocuments, int limit, int offset, int countUpTo); 262 263 /** 264 * Gets the lock manager for this repository. 265 * 266 * @return the lock manager 267 * @since 7.4 268 */ 269 LockManager getLockManager(); 270 271 /** 272 * Executes the given query and returns the first batch of results containing id of documents, next batch must be 273 * requested within the {@code keepAliveSeconds} delay. 274 * 275 * @since 8.4 276 */ 277 ScrollResult<String> scroll(DBSExpressionEvaluator evaluator, int batchSize, int keepAliveSeconds); 278 279 /** 280 * Get the next batch of results containing id of documents, the {@code scrollId} is part of the previous 281 * {@link ScrollResult} response. 282 * 283 * @since 8.4 284 */ 285 ScrollResult<String> scroll(String scrollId); 286 287 /** 288 * Called when created a transaction. 289 * 290 * @since 8.10 291 */ 292 default void begin() { 293 294 } 295 296 /** 297 * Saves and flushes to database. 298 * 299 * @since 8.10 300 */ 301 default void commit() { 302 303 } 304 305 /** 306 * Rolls back the save state by applying the undo log. 307 * 308 * @since 8.10 309 */ 310 default void rollback() { 311 312 } 313 314}