Skip to content

Commit

Permalink
Forward notifications between striosqlite v2 and v3
Browse files Browse the repository at this point in the history
  • Loading branch information
nikitin-da committed Dec 30, 2017
1 parent 97b030c commit 6c705f2
Show file tree
Hide file tree
Showing 7 changed files with 228 additions and 0 deletions.
1 change: 1 addition & 0 deletions build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -76,6 +76,7 @@ ext.libraries = [

// StorIO old versions
storIOSQLite1 : 'com.pushtorefresh.storio:sqlite:1.13.0',
storIOSQLite2 : 'com.pushtorefresh.storio2:sqlite:2.1.0',

// Libraries for tests and sample app
junit : 'junit:junit:4.12',
Expand Down
1 change: 1 addition & 0 deletions settings.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@ include ':storio-content-resolver-annotations-processor'
include ':storio-content-resolver-annotations-processor-test'

include ':storio-interop1to3'
include ':storio-interop2to3'

include ':storio-test-without-rxjava'

Expand Down
34 changes: 34 additions & 0 deletions storio-interop2to3/build.gradle
Original file line number Diff line number Diff line change
@@ -0,0 +1,34 @@
apply plugin: 'com.android.library'
apply plugin: 'kotlin-android'

android {
compileSdkVersion rootProject.ext.compileSdkVersion

defaultConfig {
versionName VERSION_NAME
versionCode Integer.parseInt(VERSION_CODE)
minSdkVersion rootProject.ext.minSdkVersion
}

packagingOptions {
exclude 'LICENSE.txt' // multiple libs have this file -> cause build error
}
}

dependencies {
implementation libraries.storIOSQLite2
implementation libraries.storIOSQLite

// Do not use compileOnly because without rxJava and rxJava2 using interoperability makes sense.
implementation libraries.rxJava
implementation libraries.rxJava2

testImplementation libraries.junit
testImplementation libraries.kotlinStdLib
testImplementation libraries.mockitoKotlin
testImplementation libraries.assertJ
}

apply from: '../gradle/checkstyle.gradle'
apply from: '../gradle/jacoco-android.gradle'
apply from: '../gradle/publish-android-lib.gradle'
3 changes: 3 additions & 0 deletions storio-interop2to3/gradle.properties
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
POM_NAME=storio-interop2to3
POM_ARTIFACT_ID=storio-interop2to3
POM_PACKAGING=jar
2 changes: 2 additions & 0 deletions storio-interop2to3/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
<?xml version="1.0" encoding="utf-8"?>
<manifest package="com.pushtorefresh.storio3.interop2to3" />
Original file line number Diff line number Diff line change
@@ -0,0 +1,73 @@
package com.pushtorefresh.storio3.interop2to3;

import android.support.annotation.NonNull;

import java.util.Collections;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;

import io.reactivex.BackpressureStrategy;
import io.reactivex.functions.Consumer;
import rx.functions.Action1;

public class StorIOSQLite2To3 {

private final Set<com.pushtorefresh.storio2.sqlite.Changes> forwardedChanges2 = Collections.newSetFromMap(
new ConcurrentHashMap<com.pushtorefresh.storio2.sqlite.Changes, Boolean>()
);

private final Set<com.pushtorefresh.storio3.sqlite.Changes> forwardedChanges3 = Collections.newSetFromMap(
new ConcurrentHashMap<com.pushtorefresh.storio3.sqlite.Changes, Boolean>()
);

public void forwardNotifications(
@NonNull final com.pushtorefresh.storio2.sqlite.StorIOSQLite sqlite2,
@NonNull final com.pushtorefresh.storio3.sqlite.StorIOSQLite sqlite3
) {
sqlite2.observeChanges()
.subscribe(new Action1<com.pushtorefresh.storio2.sqlite.Changes>() {
@Override
public void call(@NonNull com.pushtorefresh.storio2.sqlite.Changes changes2) {
if (!forwardedChanges2.remove(changes2)) { // Check to prevent cyclic forwarding.
final com.pushtorefresh.storio3.sqlite.Changes changes3ToForward
= convertToV3(changes2);
forwardedChanges3.add(changes3ToForward);
sqlite3.lowLevel().notifyAboutChanges(changes3ToForward);
}
}
});

sqlite3.observeChanges(BackpressureStrategy.BUFFER)
.subscribe(new Consumer<com.pushtorefresh.storio3.sqlite.Changes>() {
@Override
public void accept(com.pushtorefresh.storio3.sqlite.Changes changes3) throws Exception {
if (!forwardedChanges3.remove(changes3)) { // Check to prevent cyclic forwarding.
final com.pushtorefresh.storio2.sqlite.Changes changes2ToForward
= convertToV2(changes3);
forwardedChanges2.add(changes2ToForward);
sqlite2.lowLevel().notifyAboutChanges(changes2ToForward);
}
}
});
}

@NonNull
private com.pushtorefresh.storio2.sqlite.Changes convertToV2(
@NonNull com.pushtorefresh.storio3.sqlite.Changes changes3
) {
return com.pushtorefresh.storio2.sqlite.Changes.newInstance(
changes3.affectedTables(),
changes3.affectedTags()
);
}

@NonNull
private com.pushtorefresh.storio3.sqlite.Changes convertToV3(
@NonNull com.pushtorefresh.storio2.sqlite.Changes changes2
) {
return com.pushtorefresh.storio3.sqlite.Changes.newInstance(
changes2.affectedTables(),
changes2.affectedTags()
);
}
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,114 @@
package com.pushtorefresh.storio3.interop2to3

import com.nhaarman.mockito_kotlin.mock
import io.reactivex.BackpressureStrategy
import org.junit.Before
import org.junit.Test
import com.pushtorefresh.storio2.sqlite.Changes as Changes2
import com.pushtorefresh.storio2.sqlite.StorIOSQLite as StorIOSQLite2
import com.pushtorefresh.storio2.sqlite.impl.DefaultStorIOSQLite as DefaultStorIOSQLite2
import com.pushtorefresh.storio3.sqlite.Changes as Changes3
import com.pushtorefresh.storio3.sqlite.StorIOSQLite as StorIOSQLite3
import com.pushtorefresh.storio3.sqlite.impl.DefaultStorIOSQLite as DefaultStorIOSQLite3
import io.reactivex.subscribers.TestSubscriber as TestSubscriberRx2
import rx.observers.TestSubscriber as TestSubscriberRx1

class StorIOSQLite2To3Test {

val observer2 = TestSubscriberRx1.create<Changes2>()

val observer3 = TestSubscriberRx2.create<Changes3>()

lateinit var storIOSQLite2: StorIOSQLite2

lateinit var storIOSQLite3: StorIOSQLite3

lateinit var changes2WithTags: Changes2

lateinit var changes2WithoutTags: Changes2

lateinit var changes3WithTags: Changes3

lateinit var changes3WithoutTags: Changes3

@Before
fun `before each test`() {
storIOSQLite2 = DefaultStorIOSQLite2.builder()
.sqliteOpenHelper(mock())
.defaultScheduler(null)
.build()
storIOSQLite3 = DefaultStorIOSQLite3.builder()
.sqliteOpenHelper(mock())
.defaultRxScheduler(null)
.build()
val interop = StorIOSQLite2To3()
interop.forwardNotifications(storIOSQLite2, storIOSQLite3)

storIOSQLite2.observeChanges().subscribe(observer2)
storIOSQLite3.observeChanges(BackpressureStrategy.BUFFER).subscribe(observer3)

val tables = HashSet<String>()
tables.add("table1")
tables.add("table2")

val tags = HashSet<String>()
tags.add("tag1")
tags.add("tag2")

changes2WithTags = Changes2.newInstance(tables, tags)
changes3WithTags = Changes3.newInstance(tables, tags)

changes2WithoutTags = Changes2.newInstance(tables, null as Collection<String>?)
changes3WithoutTags = Changes3.newInstance(tables, null as Collection<String>?)
}

@Test
fun `forwardNotifications should forward from 2 to 3 with tags`() {
storIOSQLite2.lowLevel().notifyAboutChanges(changes2WithTags)
observer2.assertValue(changes2WithTags)
observer3.assertValue(changes3WithTags)
}

@Test
fun `forwardNotifications should forward from 2 to 3 without tags`() {
storIOSQLite2.lowLevel().notifyAboutChanges(changes2WithoutTags)
observer2.assertValue(changes2WithoutTags)
observer3.assertValue(changes3WithoutTags)
}

@Test
fun `forwardNotifications should forward from 2 to 3 multiple`() {
storIOSQLite2.lowLevel().notifyAboutChanges(changes2WithTags)
observer2.assertValue(changes2WithTags)
observer3.assertValue(changes3WithTags)

storIOSQLite2.lowLevel().notifyAboutChanges(changes2WithTags)
observer2.assertValues(changes2WithTags, changes2WithTags)
observer3.assertValues(changes3WithTags, changes3WithTags)
}

@Test
fun `forwardNotifications should forward from 3 to 2 with tags`() {
storIOSQLite3.lowLevel().notifyAboutChanges(changes3WithTags)
observer2.assertValue(changes2WithTags)
observer3.assertValue(changes3WithTags)
}

@Test
fun `forwardNotifications should forward from 3 to 2 without tags`() {
storIOSQLite3.lowLevel().notifyAboutChanges(changes3WithoutTags)
observer2.assertValue(changes2WithoutTags)
observer3.assertValue(changes3WithoutTags)
}

@Test
fun `forwardNotifications should forward from 3 to 2 with multiple`() {
storIOSQLite3.lowLevel().notifyAboutChanges(changes3WithTags)
observer2.assertValue(changes2WithTags)
observer3.assertValue(changes3WithTags)

storIOSQLite3.lowLevel().notifyAboutChanges(changes3WithTags)
observer2.assertValues(changes2WithTags, changes2WithTags)
observer3.assertValues(changes3WithTags, changes3WithTags)
}
}

0 comments on commit 6c705f2

Please sign in to comment.