Example usage for com.mongodb.bulk BulkWriteError toString

List of usage examples for com.mongodb.bulk BulkWriteError toString

Introduction

In this page you can find the example usage for com.mongodb.bulk BulkWriteError toString.

Prototype

@Override
    public String toString() 

Source Link

Usage

From source file:org.opencb.opencga.storage.mongodb.variant.load.stage.MongoDBVariantStageLoader.java

License:Apache License

/**
 * Given a map of id -> binary[], inserts the binary objects in the stage collection.
 *
 * {//w w  w . j  a  va  2s .c  om
 *     <studyId> : {
 *         <fileId> : [ BinData(), BinData() ]
 *     }
 * }
 *
 * The field <fileId> is an array to detect duplicated variants within the same file.
 *
 * It may happen that an update with upsert:true fail if two different threads try to
 * update the same non existing document.
 * See https://jira.mongodb.org/browse/SERVER-14322
 *
 * In that case, the non inserted values will be returned.
 *
 * @param values        Map with all the values to insert
 * @param result        MongoDBVariantWriteResult to fill
 * @param retryIds      List of IDs to retry. If not null, only will update those documents within this set
 * @return              List of non updated documents.
 * @throws MongoBulkWriteException if the exception was not a DuplicatedKeyException (e:11000)
 */
private Set<String> updateMongo(ListMultimap<Document, Binary> values, MongoDBVariantWriteResult result,
        Set<String> retryIds) {

    Set<String> nonInsertedIds = Collections.emptySet();
    if (values.isEmpty()) {
        return nonInsertedIds;
    }
    List<Bson> queries = new LinkedList<>();
    List<Bson> updates = new LinkedList<>();
    for (Document id : values.keySet()) {
        if (retryIds == null || retryIds.contains(id.getString("_id"))) {
            List<Binary> binaryList = values.get(id);
            queries.add(eq("_id", id.getString("_id")));
            if (binaryList.size() == 1) {
                updates.add(combine(
                        resumeStageLoad ? addToSet(fieldName, binaryList.get(0))
                                : push(fieldName, binaryList.get(0)),
                        setOnInsert(END_FIELD, id.get(END_FIELD)), setOnInsert(REF_FIELD, id.get(REF_FIELD)),
                        setOnInsert(ALT_FIELD, id.get(ALT_FIELD))));
            } else {
                updates.add(combine(
                        resumeStageLoad ? addEachToSet(fieldName, binaryList) : pushEach(fieldName, binaryList),
                        setOnInsert(END_FIELD, id.get(END_FIELD)), setOnInsert(REF_FIELD, id.get(REF_FIELD)),
                        setOnInsert(ALT_FIELD, id.get(ALT_FIELD))));
            }
        }
    }

    try {
        final BulkWriteResult mongoResult = collection.update(queries, updates, QUERY_OPTIONS).first();
        result.setNewVariants(mongoResult.getInsertedCount())
                .setUpdatedVariants(mongoResult.getModifiedCount());
    } catch (MongoBulkWriteException e) {
        result.setNewVariants(e.getWriteResult().getInsertedCount())
                .setUpdatedVariants(e.getWriteResult().getModifiedCount());

        if (retryIds != null) {
            // If retryIds != null, means that this this was the second attempt to update. In this case, do fail.
            LOGGER.error("BulkWriteErrors when retrying the updates");
            throw e;
        }

        nonInsertedIds = new HashSet<>();
        for (BulkWriteError writeError : e.getWriteErrors()) {
            if (ErrorCategory.fromErrorCode(writeError.getCode()).equals(ErrorCategory.DUPLICATE_KEY)) { //Dup Key error code
                Matcher matcher = DUP_KEY_WRITE_RESULT_ERROR_PATTERN.matcher(writeError.getMessage());
                if (matcher.find()) {
                    String id = matcher.group(1);
                    nonInsertedIds.add(id);
                    LOGGER.warn("Catch error : {}", writeError.toString());
                    LOGGER.warn("DupKey exception inserting '{}'. Retry!", id);
                } else {
                    LOGGER.error("WriteError with code {} does not match with the pattern {}",
                            writeError.getCode(), DUP_KEY_WRITE_RESULT_ERROR_PATTERN.pattern());
                    throw e;
                }
            } else {
                throw e;
            }
        }
    }
    return nonInsertedIds;
}