Package org.hibernate.ogm.datastore.mongodb.test.options.writeconcern

Source Code of org.hibernate.ogm.datastore.mongodb.test.options.writeconcern.WriteConcernPropagationTest

/*
* Hibernate OGM, Domain model persistence for NoSQL datastores
*
* License: GNU Lesser General Public License (LGPL), version 2.1 or later
* See the lgpl.txt file in the root directory or <http://www.gnu.org/licenses/lgpl-2.1.html>.
*/
package org.hibernate.ogm.datastore.mongodb.test.options.writeconcern;

import static org.hibernate.ogm.datastore.mongodb.utils.MockMongoClientBuilder.mockClient;
import static org.mockito.Matchers.any;
import static org.mockito.Matchers.anyBoolean;
import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.times;
import static org.mockito.Mockito.verify;

import java.lang.annotation.ElementType;
import java.util.List;

import org.hibernate.Session;
import org.hibernate.Transaction;
import org.hibernate.ogm.OgmSessionFactory;
import org.hibernate.ogm.cfg.DocumentStoreProperties;
import org.hibernate.ogm.cfg.OgmConfiguration;
import org.hibernate.ogm.cfg.OgmProperties;
import org.hibernate.ogm.datastore.document.options.AssociationStorageType;
import org.hibernate.ogm.datastore.mongodb.MongoDB;
import org.hibernate.ogm.datastore.mongodb.impl.MongoDBDatastoreProvider;
import org.hibernate.ogm.datastore.mongodb.options.WriteConcernType;
import org.hibernate.ogm.datastore.mongodb.utils.MockMongoClientBuilder.MockMongoClient;
import org.hibernate.ogm.utils.TestHelper;
import org.junit.After;
import org.junit.Test;

import com.mongodb.BasicDBList;
import com.mongodb.BasicDBObject;
import com.mongodb.DBObject;
import com.mongodb.WriteConcern;

/**
* Tests that the configured write concern is applied when performing operations against MongoDB.
*
* @author Gunnar Morling
*/
public class WriteConcernPropagationTest {

  private OgmSessionFactory sessions;

  @After
  public void closeSessionFactory() {
    sessions.close();
  }

  @Test
  @SuppressWarnings("unchecked")
  public void shouldApplyConfiguredWriteConcernForInsertOfTuple() {
    // given an empty database
    MockMongoClient mockClient = mockClient().build();
    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) );

    final Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when inserting a golf player
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1 );
    session.persist( ben );

    transaction.commit();
    session.close();

    // then expect one (batched) insert with the configured write concern
    verify( mockClient.getCollection( "GolfPlayer" ) ).insert( any( List.class ), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForUpdateOfTuple() {
    // given a database with a golf player
    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", getPlayer() )
        .build();
    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) );

    final Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when updating the golf player
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.2 );
    session.merge( ben );

    transaction.commit();
    session.close();

    // then expect one (batched) insert with the configured write concern
    verify( mockClient.getCollection( "GolfPlayer" ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForRemoveTuple() {
    // given a database with a golf player
    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", getPlayer() )
        .build();

    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) );

    final Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when removing the golf player
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1 );
    session.delete( ben );

    transaction.commit();
    session.close();

    // then expect a call to remove with the configured write concern
    verify( mockClient.getCollection( "GolfPlayer" ) ).remove( any( DBObject.class ), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForCreationOfEmbeddedAssociation() {
    // given a persisted player and a golf course
    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", getPlayer() )
        .insert( "GolfCourse", getGolfCourse() )
        .build();

    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) );

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when associating the golf course to the player
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1, new GolfCourse( 1L, "Bepple Peach" ) );
    session.merge( ben );

    transaction.commit();
    session.close();

    // then expect one update using the configured write concern for adding the row
    verify( mockClient.getCollection( "GolfPlayer" ), times( 1 ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForCreationOfAssociationStoredAsDocument() {
    // given an empty database
    MockMongoClient mockClient = mockClient().build();
    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ), AssociationStorageType.ASSOCIATION_DOCUMENT );

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when inserting a player with an associated course
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1, new GolfCourse( 1L, "Bepple Peach" ) );
    session.persist( ben );

    transaction.commit();
    session.close();

    // then expect association operations using the configured write concern
    verify( mockClient.getCollection( "Associations" ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.MAJORITY ) );
  }

  @SuppressWarnings("unchecked")
  @Test
  public void shouldApplyWriteConcernConfiguredOnPropertyLevelForCreationOfAssociationStoredAsDocument() {
    // given an empty database
    MockMongoClient mockClient = mockClient().build();

    OgmConfiguration configuration = TestHelper.getDefaultTestConfiguration( getAnnotatedClasses() );
    configuration.getProperties().put( OgmProperties.DATASTORE_PROVIDER, new MongoDBDatastoreProvider( mockClient.getClient() ) );
    configuration.getProperties().put( DocumentStoreProperties.ASSOCIATIONS_STORE, AssociationStorageType.ASSOCIATION_DOCUMENT );
    configuration.configureOptionsFor( MongoDB.class )
      .entity( GolfPlayer.class )
        .writeConcern( WriteConcernType.REPLICA_ACKNOWLEDGED )
        .property( "playedCourses", ElementType.FIELD )
          .writeConcern( WriteConcernType.ACKNOWLEDGED );

    sessions = configuration.buildSessionFactory();

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when inserting a player with an associated course
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1, new GolfCourse( 1L, "Bepple Peach" ) );
    session.persist( ben );

    transaction.commit();
    session.close();

    // then expect tuple and association operations using the configured write concerns
    verify( mockClient.getCollection( "GolfPlayer" ) ).insert( any( List.class ), eq( WriteConcern.REPLICA_ACKNOWLEDGED ) );
    verify( mockClient.getCollection( "Associations" ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.ACKNOWLEDGED ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForUpdateOfEmbeddedAssociation() {
    // given a persisted player with one associated golf course
    BasicDBObject player = getPlayer();
    player.put( "playedCourses", getPlayedCoursesAssociationEmbedded() );

    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", player )
        .insert( "GolfCourse", getGolfCourse() )
        .build();

    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) );

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when merging the player with two associated courses
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1, new GolfCourse( 1L, "Bepple Peach" ), new GolfCourse( 2L, "Ant Sandrews" ) );
    session.merge( ben );

    transaction.commit();
    session.close();

    // then expect updates to the player document using the configured write concern
    verify( mockClient.getCollection( "GolfPlayer" ), times( 2 ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForUpdateOfAssociationStoredAsDocument() {
    // given a persisted player with one associated golf course
    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", getPlayer() )
        .insert( "GolfCourse", getGolfCourse() )
        .insert( "Associations", getPlayedCoursesAssociationAsDocument() )
        .build();

    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ), AssociationStorageType.ASSOCIATION_DOCUMENT );

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when merging the player with two associated courses
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1, new GolfCourse( 1L, "Bepple Peach" ), new GolfCourse( 2L, "Ant Sandrews" ) );
    session.merge( ben );

    transaction.commit();
    session.close();

    // then expect one update to the association collection
    verify( mockClient.getCollection( "Associations" ), times( 1 ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForRemovalOfEmbeddedAssociation() {
    // given a persisted player with one associated golf course
    BasicDBObject player = getPlayer();
    player.put( "playedCourses", getPlayedCoursesAssociationEmbedded() );

    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", player )
        .insert( "GolfCourse", getGolfCourse() )
        .build();

    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) );

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when removing the association
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1 );
    session.merge( ben );

    transaction.commit();
    session.close();

    // then expect one call to update using the configured write concern
    verify( mockClient.getCollection( "GolfPlayer" ) ).update( any( DBObject.class ), any( DBObject.class ), anyBoolean(), anyBoolean(), eq( WriteConcern.MAJORITY ) );
  }

  @Test
  public void shouldApplyConfiguredWriteConcernForRemovalOfAssociationStoredAsDocument() {
    // given a persisted player with one associated golf course
    MockMongoClient mockClient = mockClient()
        .insert( "GolfPlayer", getPlayer() )
        .insert( "GolfCourse", getGolfCourse() )
        .insert( "Associations", getPlayedCoursesAssociationAsDocument() )
        .build();

    setupSessionFactory( new MongoDBDatastoreProvider( mockClient.getClient() ) , AssociationStorageType.ASSOCIATION_DOCUMENT );

    Session session = sessions.openSession();
    Transaction transaction = session.beginTransaction();

    // when removing the association
    GolfPlayer ben = new GolfPlayer( 1L, "Ben", 0.1 );
    session.merge( ben );

    transaction.commit();
    session.close();

    // then expect one call to remove with the configured write concern
    verify( mockClient.getCollection( "Associations" ) ).remove( any( DBObject.class ), eq( WriteConcern.MAJORITY ) );
  }

  private Class<?>[] getAnnotatedClasses() {
    return new Class<?>[] { GolfPlayer.class, GolfCourse.class };
  }

  private void setupSessionFactory(MongoDBDatastoreProvider provider) {
    setupSessionFactory( provider, null );
  }

  private void setupSessionFactory(MongoDBDatastoreProvider provider, AssociationStorageType associationStorage) {
    OgmConfiguration configuration = TestHelper.getDefaultTestConfiguration( getAnnotatedClasses() );

    configuration.getProperties().put( OgmProperties.DATASTORE_PROVIDER, provider );

    if ( associationStorage != null ) {
      configuration.getProperties().put( DocumentStoreProperties.ASSOCIATIONS_STORE, associationStorage );
    }

    sessions = configuration.buildSessionFactory();
  }

  private BasicDBObject getGolfCourse() {
    BasicDBObject bepplePeach = new BasicDBObject();
    bepplePeach.put( "_id", 1L );
    bepplePeach.put( "name", "Bepple Peach" );
    return bepplePeach;
  }

  private BasicDBObject getPlayer() {
    BasicDBObject golfPlayer = new BasicDBObject();
    golfPlayer.put( "_id", 1L );
    golfPlayer.put( "name", "Ben" );
    golfPlayer.put( "handicap", 0.1 );
    return golfPlayer;
  }

  private BasicDBList getPlayedCoursesAssociationEmbedded() {
    BasicDBObject bepplePeachRef = new BasicDBObject();
    bepplePeachRef.put( "playedCourses_id", 1L );

    BasicDBList playedCourses = new BasicDBList();
    playedCourses.add( bepplePeachRef );

    return playedCourses;
  }

  private BasicDBObject getPlayedCoursesAssociationAsDocument() {
    BasicDBObject id = new BasicDBObject();
    id.put( "golfPlayer_id", 1L );
    id.put( "table", "GolfPlayer_GolfCourse" );

    BasicDBObject row = new BasicDBObject();
    row.put( "playedCourses_id", 1L );

    BasicDBList rows = new BasicDBList();
    rows.add( row );

    BasicDBObject association = new BasicDBObject();
    association.put( "_id", id );
    association.put( "rows", rows );
    return association;
  }
}
TOP

Related Classes of org.hibernate.ogm.datastore.mongodb.test.options.writeconcern.WriteConcernPropagationTest

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.