/**
* Original iOS version by Jens Alfke
* Ported to Android by Marty Schoch
* <p/>
* Copyright (c) 2012 Couchbase, Inc. All rights reserved.
* <p/>
* Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file
* except in compliance with the License. You may obtain a copy of the License at
* <p/>
* http://www.apache.org/licenses/LICENSE-2.0
* <p/>
* Unless required by applicable law or agreed to in writing, software distributed under the
* License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
* either express or implied. See the License for the specific language governing permissions
* and limitations under the License.
*/
package com.couchbase.lite;
import com.couchbase.lite.internal.Body;
import com.couchbase.lite.internal.RevisionInternal;
import com.couchbase.lite.util.Log;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class CRUDOperationsTest extends LiteTestCaseWithDB implements Database.ChangeListener {
public static final String TAG = "CRUDOperations";
/**
* in DatabaseInternal_Tests.m
* - (void) test01_CRUD
*/
public void testCRUDOperations() throws CouchbaseLiteException {
database.addChangeListener(this);
String privateUUID = database.privateUUID();
String publicUUID = database.publicUUID();
Log.v(TAG, "DB private UUID = '" + privateUUID + "', public UUID = '" + publicUUID + "'");
assertTrue(privateUUID.length() >= 20);
assertTrue(publicUUID.length() >= 20);
// Get a nonexistent document
assertNull(database.getDocument("nonexistent", null, true));
//create a document
Map<String, Object> documentProperties = new HashMap<String, Object>();
documentProperties.put("foo", 1);
documentProperties.put("bar", false);
//documentProperties.put("baz", "touch");
Body body = new Body(documentProperties);
RevisionInternal rev1 = new RevisionInternal(body);
assertNotNull(rev1);
Status status = new Status();
rev1 = database.putRevision(rev1, null, false, status);
assertEquals(Status.CREATED, status.getCode());
Log.v(TAG, "Created " + rev1);
assertTrue(rev1.getDocID().length() >= 10);
assertTrue(rev1.getRevID().startsWith("1-"));
//read it back
RevisionInternal readRev = database.getDocument(rev1.getDocID(), null, true);
assertNotNull(readRev);
Map<String, Object> readRevProps = readRev.getProperties();
assertEquals(userProperties(body.getProperties()), userProperties(readRevProps));
//now update it
documentProperties = readRev.getProperties();
documentProperties.put("status", "updated!");
body = new Body(documentProperties);
RevisionInternal rev2 = new RevisionInternal(body);
RevisionInternal rev2input = rev2;
rev2 = database.putRevision(rev2, rev1.getRevID(), false, status);
assertEquals(Status.CREATED, status.getCode());
Log.v(TAG, "Updated " + rev2);
assertEquals(rev1.getDocID(), rev2.getDocID());
assertTrue(rev2.getRevID().startsWith("2-"));
//read it back
readRev = database.getDocument(rev2.getDocID(), null, true);
assertNotNull(readRev);
assertEquals(userProperties(readRev.getProperties()), userProperties(body.getProperties()));
// Try to update the first rev, which should fail:
try {
database.putRevision(rev2input, rev1.getRevID(), false, status);
fail("Should be failed");
} catch (CouchbaseLiteException e) {
assertEquals(Status.CONFLICT, e.getCBLStatus().getCode());
}
// Check the changes feed, with and without filters:
RevisionList changes = database.changesSince(0, null, null, null);
Log.v(TAG, "Changes = " + changes);
assertEquals(1, changes.size());
changes = database.changesSince(0, null, new ReplicationFilter() {
@Override
public boolean filter(SavedRevision revision, Map<String, Object> params) {
return "updated!".equals(revision.getProperties().get("status"));
}
}, null);
assertEquals(1, changes.size());
changes = database.changesSince(0, null, new ReplicationFilter() {
@Override
public boolean filter(SavedRevision revision, Map<String, Object> params) {
return "not updated!".equals(revision.getProperties().get("status"));
}
}, null);
assertEquals(0, changes.size());
// Delete it:
RevisionInternal revD = new RevisionInternal(rev2.getDocID(), null, true);
RevisionInternal revResult = null;
try {
revResult = database.putRevision(revD, null, false, status);
fail("Should be failed");
} catch (CouchbaseLiteException e) {
assertEquals(Status.CONFLICT, e.getCBLStatus().getCode());
}
assertNull(revResult);
revD = database.putRevision(revD, rev2.getRevID(), false, status);
assertEquals(Status.OK, status.getCode());
assertEquals(revD.getDocID(), rev2.getDocID());
assertTrue(revD.getRevID().startsWith("3-"));
// Delete nonexistent doc:
RevisionInternal revFake = new RevisionInternal("fake", null, true);
try {
database.putRevision(revFake, null, false, status);
fail("Should be failed");
} catch (CouchbaseLiteException e) {
assertEquals(Status.NOT_FOUND, e.getCBLStatus().getCode());
}
// Read it back (should fail):
readRev = database.getDocument(revD.getDocID(), null, true);
assertNull(readRev);
// Get Changes feed
changes = database.changesSince(0, null, null, null);
assertEquals(1, changes.size());
// Get Revision History
List<RevisionInternal> history = database.getRevisionHistory(revD);
assertEquals(revD, history.get(0));
assertEquals(rev2, history.get(1));
assertEquals(rev1, history.get(2));
}
@Override
public void changed(Database.ChangeEvent event) {
List<DocumentChange> changes = event.getChanges();
for (DocumentChange change : changes) {
RevisionInternal rev = change.getAddedRevision();
assertNotNull(rev);
assertNotNull(rev.getDocID());
assertNotNull(rev.getRevID());
// body could be null if withBody = false
if(rev.getProperties() != null) {
assertEquals(rev.getDocID(), rev.getProperties().get("_id"));
assertEquals(rev.getRevID(), rev.getProperties().get("_rev"));
}
}
}
}