[go: nahoru, domu]

blob: 9da1bfdc156202de735b6ed10424c505e6bfb74d [file] [log] [blame]
/*
* Copyright 2020 The Android Open Source Project
*
* 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
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* 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 androidx.datastore.rxjava3;
import static androidx.testutils.AssertionsKt.assertThrows;
import static com.google.common.truth.Truth.assertThat;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.TemporaryFolder;
import java.io.File;
import java.io.IOException;
import java.util.concurrent.CancellationException;
import java.util.concurrent.TimeUnit;
import io.reactivex.rxjava3.core.Single;
import io.reactivex.rxjava3.subscribers.TestSubscriber;
public class RxDataStoreTest {
@Rule
public TemporaryFolder tempFolder = new TemporaryFolder();
private static Single<Byte> incrementByte(Byte byteIn) {
return Single.just(++byteIn);
}
@Test
public void testGetSingleValue() throws Exception {
File newFile = tempFolder.newFile();
RxDataStore<Byte> byteStore =
new RxDataStoreBuilder<Byte>(() -> newFile, new TestingSerializer()).build();
Byte firstByte = byteStore.data().blockingFirst();
assertThat(firstByte).isEqualTo(0);
Single<Byte> incrementByte = byteStore.updateDataAsync(
RxDataStoreTest::incrementByte);
assertThat(incrementByte.blockingGet()).isEqualTo(1);
firstByte = byteStore.data().blockingFirst();
assertThat(firstByte).isEqualTo(1);
}
@Test
public void testTake3() throws Exception {
File newFile = tempFolder.newFile();
RxDataStore<Byte> byteStore =
new RxDataStoreBuilder<Byte>(() -> newFile, new TestingSerializer())
.build();
TestSubscriber<Byte> testSubscriber = byteStore.data().test();
byteStore.updateDataAsync(RxDataStoreTest::incrementByte);
// Wait for our subscriber to see the second write, otherwise we may skip from 0 - 2
testSubscriber.awaitCount(2);
byteStore.updateDataAsync(RxDataStoreTest::incrementByte);
testSubscriber.awaitCount(3).assertValues((byte) 0, (byte) 1, (byte) 2);
}
@Test
public void testReadFailure() throws Exception {
File newFile = tempFolder.newFile();
TestingSerializer testingSerializer = new TestingSerializer();
RxDataStore<Byte> byteStore =
new RxDataStoreBuilder<Byte>(() -> newFile, testingSerializer).build();
testingSerializer.setFailingRead(true);
TestSubscriber<Byte> testSubscriber = byteStore.data().test();
assertThat(testSubscriber.await(5, TimeUnit.SECONDS)).isTrue();
testSubscriber.assertError(IOException.class);
testingSerializer.setFailingRead(false);
testSubscriber = byteStore.data().test();
testSubscriber.awaitCount(1).assertValues((byte) 0);
}
@Test
public void testWriteFailure() throws Exception {
File newFile = tempFolder.newFile();
TestingSerializer testingSerializer = new TestingSerializer();
RxDataStore<Byte> byteStore =
new RxDataStoreBuilder<Byte>(() -> newFile, testingSerializer).build();
TestSubscriber<Byte> testSubscriber = byteStore.data().test();
testingSerializer.setFailingWrite(true);
Single<Byte> incrementByte = byteStore.updateDataAsync(RxDataStoreTest::incrementByte);
incrementByte.cache().test().await().assertError(IOException.class);
testSubscriber.awaitCount(1).assertNoErrors().assertValues((byte) 0);
testingSerializer.setFailingWrite(false);
Single<Byte> incrementByte2 = byteStore.updateDataAsync(RxDataStoreTest::incrementByte);
assertThat(incrementByte2.blockingGet()).isEqualTo((byte) 1);
testSubscriber.awaitCount(2).assertValues((byte) 0, (byte) 1);
}
@Test
public void openingSameDataStoreTwice_throwsException() throws IOException {
File newFile = tempFolder.newFile();
TestingSerializer testingSerializer = new TestingSerializer();
RxDataStore<Byte> byteRxDataStore = new RxDataStoreBuilder<Byte>(() -> newFile,
testingSerializer).build();
assertThat(byteRxDataStore.data().blockingFirst()).isEqualTo((byte) 0);
RxDataStore<Byte> byteRxDataStore2 = new RxDataStoreBuilder<Byte>(() -> newFile,
testingSerializer).build();
assertThrows(IllegalStateException.class, () -> byteRxDataStore2.data().blockingFirst());
}
@Test
public void canCloseDataStore() throws Exception {
File newFile = tempFolder.newFile();
TestingSerializer testingSerializer = new TestingSerializer();
RxDataStore<Byte> byteRxDataStore = new RxDataStoreBuilder<Byte>(() -> newFile,
testingSerializer).build();
assertThat(byteRxDataStore.data().blockingFirst()).isEqualTo((byte) 0);
byteRxDataStore.dispose();
byteRxDataStore.shutdownComplete().blockingAwait();
TestSubscriber<Byte> testSubscriber = byteRxDataStore.data().test();
assertThat(testSubscriber.await(5, TimeUnit.SECONDS)).isTrue();
// Note(rohitsat): this is different from coroutines bc asFlowable converts the
// CancellationException to onComplete
testSubscriber.assertNoErrors()
.assertComplete()
.assertValueCount(0);
// NOTE(rohitsat): this is different from data()
byteRxDataStore.updateDataAsync(Single::just).test().await().assertError(
CancellationException.class);
RxDataStore<Byte> byteRxDataStore2 = new RxDataStoreBuilder<Byte>(() -> newFile,
testingSerializer).build();
// Should not throw
assertThat(byteRxDataStore2.data().blockingFirst()).isEqualTo((byte) 0);
}
}