public void ensureCaps() { for (MappedClass mc : mapr.getMappedClasses()) if (mc.getEntityAnnotation() != null && mc.getEntityAnnotation().cap().value() > 0) { CappedAt cap = mc.getEntityAnnotation().cap(); String collName = mapr.getCollectionName(mc.getClazz()); BasicDBObjectBuilder dbCapOpts = BasicDBObjectBuilder.start("capped", true); if (cap.value() > 0) dbCapOpts.add("size", cap.value()); if (cap.count() > 0) dbCapOpts.add("max", cap.count()); DB db = getDB(); if (db.getCollectionNames().contains(collName)) { DBObject dbResult = db.command(BasicDBObjectBuilder.start("collstats", collName).get()); if (dbResult.containsField("capped")) { // TODO: check the cap options. log.warning("DBCollection already exists is cap'd already; doing nothing. " + dbResult); } else { log.warning( "DBCollection already exists with same name(" + collName + ") and is not cap'd; not creating cap'd version!"); } } else { getDB().createCollection(collName, dbCapOpts.get()); log.debug("Created cap'd DBCollection (" + collName + ") with opts " + dbCapOpts); } } }
private <T> void postSaveOperations( Object entity, DBObject dbObj, Map<Object, DBObject> involvedObjects) { mapr.updateKeyInfo(entity, dbObj, createCache()); // call PostPersist on all involved entities (including the entity) for (Map.Entry<Object, DBObject> e : involvedObjects.entrySet()) { Object ent = e.getKey(); DBObject dbO = e.getValue(); MappedClass mc = mapr.getMappedClass(entity); mc.callLifecycleMethods(PostPersist.class, ent, dbO, mapr); } }
// remove any MappedField specified in @IngoreFields on the class. void processIgnoreFieldsAnnotations() { DatastoreImpl dsi = (DatastoreImpl) ds; for (MappedClass mc : dsi.getMapper().getMappedClasses()) { IgnoreFields ignores = (IgnoreFields) mc.getAnnotation(IgnoreFields.class); if (ignores != null) { for (String field : ignores.value().split(",")) { MappedField mf = mc.getMappedFieldByJavaField(field); mc.getPersistenceFields().remove(mf); } } } }
public <T> UpdateResults<T> update(T ent, UpdateOperations<T> ops) { MappedClass mc = mapr.getMappedClass(ent); Query<T> q = (Query<T>) createQuery(mc.getClazz()); q.disableValidation().filter(Mapper.ID_KEY, getId(ent)); if (mc.getFieldsAnnotatedWith(Version.class).size() > 0) { MappedField versionMF = mc.getFieldsAnnotatedWith(Version.class).get(0); Long oldVer = (Long) versionMF.getFieldValue(ent); q.filter(versionMF.getNameToStore(), oldVer); ops.set(versionMF.getNameToStore(), VersionHelper.nextValue(oldVer)); } return update(q, ops); }
protected <T> WriteResult tryVersionedUpdate( DBCollection dbColl, T entity, DBObject dbObj, WriteConcern wc, DB db, MappedClass mc) { WriteResult wr = null; if (mc.getFieldsAnnotatedWith(Version.class).isEmpty()) return wr; MappedField mfVersion = mc.getFieldsAnnotatedWith(Version.class).get(0); String versionKeyName = mfVersion.getNameToStore(); Long oldVersion = (Long) mfVersion.getFieldValue(entity); long newVersion = VersionHelper.nextValue(oldVersion); dbObj.put(versionKeyName, newVersion); if (oldVersion != null && oldVersion > 0) { Object idValue = dbObj.get(Mapper.ID_KEY); UpdateResults<T> res = update( find((Class<T>) entity.getClass(), Mapper.ID_KEY, idValue) .filter(versionKeyName, oldVersion), dbObj, false, false, wc); wr = res.getWriteResult(); if (res.getUpdatedCount() != 1) throw new ConcurrentModificationException( "Entity of class " + entity.getClass().getName() + " (id='" + idValue + "',version='" + oldVersion + "') was concurrently updated."); } else if (wc == null) wr = dbColl.save(dbObj); else wr = dbColl.save(dbObj, wc); // update the version. mfVersion.setFieldValue(entity, newVersion); return wr; }
protected void ensureIndexes( MappedClass mc, boolean background, ArrayList<MappedClass> parentMCs, ArrayList<MappedField> parentMFs) { if (parentMCs.contains(mc)) return; // skip embedded types if (mc.getEmbeddedAnnotation() != null && (parentMCs == null || parentMCs.isEmpty())) return; // Ensure indexes from class annotation Indexes idxs = (Indexes) mc.getAnnotation(Indexes.class); if (idxs != null && idxs.value() != null && idxs.value().length > 0) for (Index index : idxs.value()) { BasicDBObject fields = QueryImpl.parseSortString(index.value()); ensureIndex( mc.getClazz(), index.name(), fields, index.unique(), index.dropDups(), index.background() ? index.background() : background, index.sparse() ? index.sparse() : false); } // Ensure indexes from field annotations, and embedded entities for (MappedField mf : mc.getPersistenceFields()) { if (mf.hasAnnotation(Indexed.class)) { Indexed index = mf.getAnnotation(Indexed.class); StringBuilder field = new StringBuilder(); Class<?> indexedClass = (parentMCs.isEmpty() ? mc : parentMCs.get(0)).getClazz(); if (!parentMCs.isEmpty()) for (MappedField pmf : parentMFs) field.append(pmf.getNameToStore()).append("."); field.append(mf.getNameToStore()); ensureIndex( indexedClass, index.name(), new BasicDBObject(field.toString(), index.value().toIndexValue()), index.unique(), index.dropDups(), index.background() ? index.background() : background, index.sparse() ? index.sparse() : false); } if (!mf.isTypeMongoCompatible() && !mf.hasAnnotation(Reference.class) && !mf.hasAnnotation(Serialized.class)) { ArrayList<MappedClass> newParentClasses = (ArrayList<MappedClass>) parentMCs.clone(); ArrayList<MappedField> newParents = (ArrayList<MappedField>) parentMFs.clone(); newParentClasses.add(mc); newParents.add(mf); ensureIndexes( mapr.getMappedClass(mf.isSingleValue() ? mf.getType() : mf.getSubClass()), background, newParentClasses, newParents); } } }
/** * Add class to watched classes for auditing Not thread safe. Call this method once during app * initialization * * @param auditClass */ public void auditClass(Class auditClass) { MappedClass mappedClass = mongo.getMorphia().getMapper().getMappedClass(auditClass); if (mappedClass != null) { watchedClasses.put(auditClass, mappedClass.getCollectionName() + "History"); } }