- Added new methods that allow a query of a single term over name, address, phone, telegram an website fields
- Linking this result to the code that handles the UI update (working for merchants only)
This commit is contained in:
parent
07e39e9001
commit
aebff15033
8 changed files with 144 additions and 21 deletions
|
@ -47,6 +47,11 @@ android {
|
|||
sourceCompatibility JavaVersion.VERSION_1_8
|
||||
targetCompatibility JavaVersion.VERSION_1_8
|
||||
}
|
||||
// Gradle automatically adds 'android.test.runner' as a dependency.
|
||||
useLibrary 'android.test.runner'
|
||||
useLibrary 'android.test.base'
|
||||
useLibrary 'android.test.mock'
|
||||
|
||||
}
|
||||
|
||||
dependencies {
|
||||
|
@ -100,9 +105,12 @@ dependencies {
|
|||
debugImplementation 'com.amitshekhar.android:debug-db:1.0.4'
|
||||
|
||||
// TODO enable and make proper testing
|
||||
// testImplementation 'junit:junit:4.12'
|
||||
testImplementation 'junit:junit:4.12'
|
||||
// Core library
|
||||
androidTestImplementation 'androidx.test:core:1.1.0'
|
||||
|
||||
// testImplementation "androidx.arch.core:core-testing:$lifecycle_version"
|
||||
// testImplementation "androidx.room:room-testing:$room_version"
|
||||
// androidTestImplementation 'androidx.test:runner:1.1.0'
|
||||
// androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.0'
|
||||
androidTestImplementation 'androidx.test.espresso:espresso-core:3.1.1'
|
||||
}
|
||||
|
|
|
@ -0,0 +1,65 @@
|
|||
package cy.agorise.bitsybitshareswallet;
|
||||
|
||||
import android.content.Context
|
||||
import androidx.room.Room
|
||||
import androidx.test.core.app.ApplicationProvider
|
||||
import androidx.test.runner.AndroidJUnit4
|
||||
import cy.agorise.bitsybitshareswallet.database.BitsyDatabase
|
||||
import cy.agorise.bitsybitshareswallet.database.entities.Merchant
|
||||
import org.junit.After
|
||||
import org.junit.Assert
|
||||
import org.junit.Before
|
||||
import org.junit.Test
|
||||
import org.junit.runner.RunWith
|
||||
import java.io.IOException
|
||||
|
||||
@RunWith(AndroidJUnit4::class)
|
||||
public class MerchantQueryTest {
|
||||
private lateinit var db: BitsyDatabase
|
||||
|
||||
@Before
|
||||
fun createDb(){
|
||||
val context = ApplicationProvider.getApplicationContext<Context>()
|
||||
db = Room.inMemoryDatabaseBuilder(context, BitsyDatabase::class.java).build()
|
||||
|
||||
// Creating a few sample merchants
|
||||
val merchant1 = Merchant("5c23c8c234c83f0013e67786",
|
||||
"Café del Mar",
|
||||
"Address1",
|
||||
17.82834,
|
||||
-9.38483,
|
||||
"+1 999.999.9999",
|
||||
"@user",
|
||||
"https://100Natural.com")
|
||||
val merchant2 = Merchant("5c23c91a34c83f0013e67787",
|
||||
"Condesa Acapulco",
|
||||
"Address2",
|
||||
13.82834,
|
||||
-67.38483,
|
||||
"+1 999.999.9999",
|
||||
"@user",
|
||||
"https://100Natural.com")
|
||||
db.merchantDao().insert(merchant1)
|
||||
db.merchantDao().insert(merchant2)
|
||||
}
|
||||
|
||||
@After
|
||||
@Throws(IOException::class)
|
||||
fun closeDb(){
|
||||
db.close()
|
||||
}
|
||||
|
||||
@Test
|
||||
fun testSimpleQuery(){
|
||||
val allMerchants = db.merchantDao().getAllSync()
|
||||
Assert.assertEquals(2, allMerchants.size)
|
||||
}
|
||||
|
||||
@Test
|
||||
fun testSearchQuery(){
|
||||
val query = "%con%"
|
||||
val merchants = db.merchantDao().findMerchantsByWordSync(query)
|
||||
Assert.assertEquals(1, merchants.size)
|
||||
Assert.assertEquals(merchants[0].name, "Condesa Acapulco")
|
||||
}
|
||||
}
|
|
@ -6,6 +6,7 @@ import androidx.room.Insert
|
|||
import androidx.room.OnConflictStrategy
|
||||
import androidx.room.Query
|
||||
import cy.agorise.bitsybitshareswallet.database.entities.Merchant
|
||||
import io.reactivex.Single
|
||||
|
||||
@Dao
|
||||
interface MerchantDao {
|
||||
|
@ -18,6 +19,15 @@ interface MerchantDao {
|
|||
@Query("SELECT * FROM merchants")
|
||||
fun getAll(): LiveData<List<Merchant>>
|
||||
|
||||
@Query("SELECT * FROM merchants")
|
||||
fun getAllSync(): List<Merchant>
|
||||
|
||||
@Query("SELECT * FROM merchants WHERE (name LIKE :query) OR (address LIKE :query) OR (phone LIKE :query) OR (telegram LIKE :query) OR (website LIKE :query)")
|
||||
fun findMerchantsByWord(query: String): Single<List<Merchant>>
|
||||
|
||||
@Query("SELECT * FROM merchants WHERE (name LIKE :query) OR (address LIKE :query) OR (phone LIKE :query) OR (telegram LIKE :query) OR (website LIKE :query)")
|
||||
fun findMerchantsByWordSync(query: String): List<Merchant>
|
||||
|
||||
@Query("DELETE FROM merchants")
|
||||
fun deleteAll()
|
||||
}
|
|
@ -6,6 +6,7 @@ import androidx.room.Insert
|
|||
import androidx.room.OnConflictStrategy
|
||||
import androidx.room.Query
|
||||
import cy.agorise.bitsybitshareswallet.database.entities.Teller
|
||||
import io.reactivex.Single
|
||||
|
||||
@Dao
|
||||
interface TellerDao {
|
||||
|
@ -18,6 +19,9 @@ interface TellerDao {
|
|||
@Query("SELECT * FROM tellers")
|
||||
fun getAll(): LiveData<List<Teller>>
|
||||
|
||||
@Query("SELECT * FROM tellers WHERE (name LIKE :query) OR (address LIKE :query) OR (phone LIKE :query) OR (telegram LIKE :query) OR (website LIKE :query)")
|
||||
fun findTellersByWord(query: String): Single<List<Teller>>
|
||||
|
||||
@Query("DELETE FROM tellers")
|
||||
fun deleteAll()
|
||||
}
|
|
@ -6,13 +6,8 @@ import android.content.pm.PackageManager
|
|||
import android.database.Cursor
|
||||
import android.database.MatrixCursor
|
||||
import android.os.Bundle
|
||||
import android.util.Log
|
||||
import com.google.android.gms.maps.GoogleMap
|
||||
import com.google.android.gms.maps.OnMapReadyCallback
|
||||
import com.google.android.gms.maps.SupportMapFragment
|
||||
|
||||
import cy.agorise.bitsybitshareswallet.R
|
||||
import android.preference.PreferenceManager
|
||||
import android.util.Log
|
||||
import android.view.*
|
||||
import android.widget.PopupWindow
|
||||
import android.widget.TextView
|
||||
|
@ -27,12 +22,18 @@ import androidx.lifecycle.ViewModelProviders
|
|||
import com.afollestad.materialdialogs.MaterialDialog
|
||||
import com.afollestad.materialdialogs.customview.customView
|
||||
import com.google.android.gms.maps.CameraUpdateFactory
|
||||
import com.google.android.gms.maps.model.*
|
||||
import com.google.android.gms.maps.GoogleMap
|
||||
import com.google.android.gms.maps.OnMapReadyCallback
|
||||
import com.google.android.gms.maps.SupportMapFragment
|
||||
import com.google.android.gms.maps.model.LatLngBounds
|
||||
import com.google.android.gms.maps.model.MapStyleOptions
|
||||
import com.google.android.gms.maps.model.Marker
|
||||
import com.google.maps.android.MarkerManager
|
||||
import com.google.maps.android.clustering.Cluster
|
||||
import com.google.maps.android.clustering.ClusterItem
|
||||
import com.google.maps.android.clustering.ClusterManager
|
||||
import com.jakewharton.rxbinding3.appcompat.queryTextChangeEvents
|
||||
import cy.agorise.bitsybitshareswallet.R
|
||||
import cy.agorise.bitsybitshareswallet.database.entities.Merchant
|
||||
import cy.agorise.bitsybitshareswallet.database.entities.Teller
|
||||
import cy.agorise.bitsybitshareswallet.utils.Constants
|
||||
|
@ -42,7 +43,9 @@ import cy.agorise.bitsybitshareswallet.utils.toast
|
|||
import cy.agorise.bitsybitshareswallet.viewmodels.MerchantViewModel
|
||||
import io.reactivex.android.schedulers.AndroidSchedulers
|
||||
import io.reactivex.disposables.CompositeDisposable
|
||||
import java.lang.Exception
|
||||
import io.reactivex.schedulers.Schedulers
|
||||
import java.math.BigInteger
|
||||
import java.util.*
|
||||
import java.util.concurrent.TimeUnit
|
||||
|
||||
|
||||
|
@ -173,21 +176,35 @@ class MerchantsFragment : Fragment(), OnMapReadyCallback, SearchView.OnSuggestio
|
|||
}
|
||||
|
||||
private fun updateSearchViewSuggestions(query: String) {
|
||||
// TODO make call to the db to obtain the list of merchants/tellers
|
||||
val merchObs = mMerchantViewModel.queryMerchants(query)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
|
||||
// Create a cursor out of an Array
|
||||
val cursor = MatrixCursor(arrayOf(SUGGEST_COLUMN_ID, SUGGEST_COLUMN_NAME,
|
||||
SUGGEST_COLUMN_ADDRESS, SUGGEST_COLUMN_IS_MERCHANT, SUGGEST_COLUMN_IMAGE_RESOURCE))
|
||||
val tellerObs = mMerchantViewModel.queryTellers(query)
|
||||
.subscribeOn(Schedulers.io())
|
||||
.observeOn(AndroidSchedulers.mainThread())
|
||||
|
||||
for (i in 1..3) {
|
||||
if (i%2 == 1)
|
||||
cursor.addRow(arrayOf(i.toString(), "Merchant $i", "Address $i", 1, R.drawable.ic_merchant_pin))
|
||||
else
|
||||
cursor.addRow(arrayOf(i.toString(), "Teller $i", "Address $i", 0, R.drawable.ic_teller_pin))
|
||||
//TODO: Combine the results of both the merchants and teller queries
|
||||
// val combined: Observable<List<Any>> = Observable.combineLatest<List<Merchant>, List<Teller>, List<Any>>(merchObs, tellerObs, BiFunction { t1: List<Merchant>, t2:List<Teller> -> Arrays.asList(t1, t2)})
|
||||
|
||||
merchObs.subscribe({list ->
|
||||
run {
|
||||
Log.d(TAG, "list with ${list.size} elements")
|
||||
val cursor = MatrixCursor(
|
||||
arrayOf(
|
||||
SUGGEST_COLUMN_ID, SUGGEST_COLUMN_NAME,
|
||||
SUGGEST_COLUMN_ADDRESS, SUGGEST_COLUMN_IS_MERCHANT, SUGGEST_COLUMN_IMAGE_RESOURCE
|
||||
)
|
||||
)
|
||||
for (item in list) {
|
||||
cursor.addRow(arrayOf(BigInteger(item._id, 16).toLong(), item.name, item.address, 1, R.drawable.ic_merchant_pin))
|
||||
}
|
||||
|
||||
mSearchView?.suggestionsAdapter?.changeCursor(cursor)
|
||||
}
|
||||
},
|
||||
{error -> Log.e(TAG, "Error while retrieving autocomplete suggestions. Msg: ${error}")})
|
||||
|
||||
}
|
||||
|
||||
override fun onSuggestionSelect(position: Int): Boolean {
|
||||
return onSuggestionClick(position)
|
||||
|
|
|
@ -11,6 +11,7 @@ import cy.agorise.bitsybitshareswallet.database.entities.Merchant
|
|||
import cy.agorise.bitsybitshareswallet.network.FeathersResponse
|
||||
import cy.agorise.bitsybitshareswallet.network.MerchantsWebservice
|
||||
import cy.agorise.bitsybitshareswallet.utils.Constants
|
||||
import io.reactivex.Single
|
||||
import retrofit2.Call
|
||||
import retrofit2.Response
|
||||
import retrofit2.Retrofit
|
||||
|
@ -79,4 +80,8 @@ class MerchantRepository internal constructor(val context: Context) : retrofit2.
|
|||
return null
|
||||
}
|
||||
}
|
||||
|
||||
fun findMerchantsByWord(query: String): Single<List<Merchant>> {
|
||||
return mMerchantDao.findMerchantsByWord("%$query%")
|
||||
}
|
||||
}
|
|
@ -11,6 +11,7 @@ import cy.agorise.bitsybitshareswallet.database.entities.Teller
|
|||
import cy.agorise.bitsybitshareswallet.network.FeathersResponse
|
||||
import cy.agorise.bitsybitshareswallet.network.MerchantsWebservice
|
||||
import cy.agorise.bitsybitshareswallet.utils.Constants
|
||||
import io.reactivex.Single
|
||||
import retrofit2.Call
|
||||
import retrofit2.Response
|
||||
import retrofit2.Retrofit
|
||||
|
@ -79,4 +80,8 @@ class TellerRepository internal constructor(val context: Context) : retrofit2.Ca
|
|||
return null
|
||||
}
|
||||
}
|
||||
|
||||
fun findTellerByWord(word: String): Single<List<Teller>> {
|
||||
return mTellerDao.findTellersByWord("%$word%")
|
||||
}
|
||||
}
|
|
@ -7,6 +7,7 @@ import cy.agorise.bitsybitshareswallet.database.entities.Merchant
|
|||
import cy.agorise.bitsybitshareswallet.database.entities.Teller
|
||||
import cy.agorise.bitsybitshareswallet.repositories.MerchantRepository
|
||||
import cy.agorise.bitsybitshareswallet.repositories.TellerRepository
|
||||
import io.reactivex.Single
|
||||
|
||||
class MerchantViewModel(application: Application) : AndroidViewModel(application) {
|
||||
private var mMerchantRepository = MerchantRepository(application)
|
||||
|
@ -19,4 +20,12 @@ class MerchantViewModel(application: Application) : AndroidViewModel(application
|
|||
internal fun getAllTellers(): LiveData<List<Teller>> {
|
||||
return mTellerRepository.getAll()
|
||||
}
|
||||
|
||||
fun queryMerchants(query: String): Single<List<Merchant>> {
|
||||
return mMerchantRepository.findMerchantsByWord(query)
|
||||
}
|
||||
|
||||
fun queryTellers(query: String): Single<List<Teller>> {
|
||||
return mTellerRepository.findTellerByWord(query)
|
||||
}
|
||||
}
|
Loading…
Reference in a new issue