Koin setup tweaks

This commit is contained in:
Aidan Follestad 2018-12-06 22:01:45 -08:00
commit 9a849ab8ac
13 changed files with 100 additions and 165 deletions

View file

@ -13,6 +13,8 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
@file:Suppress("unused")
package com.afollestad.nocknock
import android.app.Application
@ -21,7 +23,7 @@ import com.afollestad.nocknock.koin.mainModule
import com.afollestad.nocknock.koin.viewModelModule
import com.afollestad.nocknock.notifications.NockNotificationManager
import com.afollestad.nocknock.notifications.notificationsModule
import com.afollestad.nocknock.utilities.utilitiesModule
import com.afollestad.nocknock.utilities.commonModule
import org.koin.android.ext.android.inject
import org.koin.android.ext.android.startKoin
import timber.log.Timber
@ -42,7 +44,7 @@ class NockNockApp : Application() {
val modules = listOf(
mainModule,
engineModule,
utilitiesModule,
commonModule,
notificationsModule,
viewModelModule
)

View file

@ -21,23 +21,19 @@ import android.app.job.JobScheduler
import android.content.Context.JOB_SCHEDULER_SERVICE
import android.content.Context.NOTIFICATION_SERVICE
import androidx.room.Room.databaseBuilder
import com.afollestad.nocknock.R
import com.afollestad.nocknock.data.AppDatabase
import com.afollestad.nocknock.notifications.Qualifiers.APP_ICON_RES
import com.afollestad.nocknock.notifications.Qualifiers.MAIN_ACTIVITY_CLASS
import com.afollestad.nocknock.ui.main.MainActivity
import com.afollestad.nocknock.utilities.Qualifiers.MAIN_ACTIVITY_CLASS
import com.afollestad.nocknock.utilities.ext.systemService
import okhttp3.OkHttpClient
import org.koin.dsl.module.module
const val MAIN_MODULE = "main"
val mainActivityCls = MainActivity::class.java
/** @author Aidan Follestad (@afollestad) */
val mainModule = module(MAIN_MODULE) {
val mainModule = module {
single(name = APP_ICON_RES) { R.mipmap.ic_launcher }
single(name = MAIN_ACTIVITY_CLASS) { MainActivity::class.java }
single(name = MAIN_ACTIVITY_CLASS) { mainActivityCls }
single { databaseBuilder(get(), AppDatabase::class.java, "NockNock.db").build() }

View file

@ -23,10 +23,8 @@ import com.afollestad.nocknock.utilities.Qualifiers.MAIN_DISPATCHER
import org.koin.androidx.viewmodel.ext.koin.viewModel
import org.koin.dsl.module.module
const val VIEW_MODEL_MODULE = "view_models"
/** @author Aidan Follestad (@afollestad) */
val viewModelModule = module(VIEW_MODEL_MODULE) {
val viewModelModule = module {
viewModel {
MainViewModel(

View file

@ -50,10 +50,11 @@ class MainActivity : AppCompatActivity() {
private lateinit var adapter: ServerAdapter
private val statusUpdateReceiver =
private val statusUpdateReceiver by lazy {
StatusUpdateIntentReceiver(application, intentProvider) {
viewModel.postSiteUpdate(it)
}
}
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)

View file

@ -58,10 +58,11 @@ class ViewSiteActivity : AppCompatActivity() {
internal val viewModel by viewModel<ViewSiteViewModel>()
private val intentProvider by inject<IntentProvider>()
private val statusUpdateReceiver =
private val statusUpdateReceiver by lazy {
StatusUpdateIntentReceiver(application, intentProvider) {
viewModel.setModel(it)
}
}
@SuppressLint("SetTextI18n")
override fun onCreate(savedInstanceState: Bundle?) {

View file

@ -0,0 +1,39 @@
/**
* Designed and developed by Aidan Follestad (@afollestad)
*
* 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 com.afollestad.nocknock.utilities
import com.afollestad.nocknock.utilities.Qualifiers.IO_DISPATCHER
import com.afollestad.nocknock.utilities.Qualifiers.MAIN_DISPATCHER
import com.afollestad.nocknock.utilities.providers.RealStringProvider
import com.afollestad.nocknock.utilities.providers.StringProvider
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.Dispatchers
import org.koin.dsl.module.module
object Qualifiers {
const val MAIN_DISPATCHER = "main_dispatcher"
const val IO_DISPATCHER = "io_dispatcher"
}
/** @author Aidan Follestad (@afollestad) */
val commonModule = module {
factory<CoroutineDispatcher>(name = MAIN_DISPATCHER) { Dispatchers.Main }
factory(name = IO_DISPATCHER) { Dispatchers.IO }
factory { RealStringProvider(get()) } bind StringProvider::class
}

View file

@ -1,74 +0,0 @@
/**
* Designed and developed by Aidan Follestad (@afollestad)
*
* 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 com.afollestad.nocknock.utilities
import com.afollestad.nocknock.utilities.Qualifiers.IO_DISPATCHER
import com.afollestad.nocknock.utilities.Qualifiers.MAIN_ACTIVITY_CLASS
import com.afollestad.nocknock.utilities.Qualifiers.MAIN_DISPATCHER
import com.afollestad.nocknock.utilities.providers.BitmapProvider
import com.afollestad.nocknock.utilities.providers.BundleProvider
import com.afollestad.nocknock.utilities.providers.IntentProvider
import com.afollestad.nocknock.utilities.providers.JobInfoProvider
import com.afollestad.nocknock.utilities.providers.NotificationChannelProvider
import com.afollestad.nocknock.utilities.providers.NotificationProvider
import com.afollestad.nocknock.utilities.providers.RealBitmapProvider
import com.afollestad.nocknock.utilities.providers.RealBundleProvider
import com.afollestad.nocknock.utilities.providers.RealIntentProvider
import com.afollestad.nocknock.utilities.providers.RealJobInfoProvider
import com.afollestad.nocknock.utilities.providers.RealNotificationChannelProvider
import com.afollestad.nocknock.utilities.providers.RealNotificationProvider
import com.afollestad.nocknock.utilities.providers.RealSdkProvider
import com.afollestad.nocknock.utilities.providers.RealStringProvider
import com.afollestad.nocknock.utilities.providers.SdkProvider
import com.afollestad.nocknock.utilities.providers.StringProvider
import kotlinx.coroutines.Dispatchers
import org.koin.dsl.module.module
const val UTILITIES_MODULE = "utilities"
object Qualifiers {
const val MAIN_ACTIVITY_CLASS = "main.main_activity_class"
const val MAIN_DISPATCHER = "main.main_dispatcher"
const val IO_DISPATCHER = "main.io_dispatcher"
}
/** @author Aidan Follestad (@afollestad) */
val utilitiesModule = module(UTILITIES_MODULE) {
factory(name = MAIN_DISPATCHER) { Dispatchers.Main }
factory(name = IO_DISPATCHER) { Dispatchers.IO }
factory { RealSdkProvider() } bind SdkProvider::class
factory { RealBitmapProvider(get()) } bind BitmapProvider::class
factory { RealStringProvider(get()) } bind StringProvider::class
factory {
RealIntentProvider(get(), get(name = MAIN_ACTIVITY_CLASS))
} bind IntentProvider::class
factory {
RealNotificationChannelProvider(get())
} bind NotificationChannelProvider::class
factory { RealNotificationProvider(get()) } bind NotificationProvider::class
factory { RealBundleProvider() } bind BundleProvider::class
factory { RealJobInfoProvider(get()) } bind JobInfoProvider::class
}

View file

@ -1,37 +0,0 @@
/**
* Designed and developed by Aidan Follestad (@afollestad)
*
* 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 com.afollestad.nocknock.utilities.providers
import android.content.Context
import android.graphics.Bitmap
import android.graphics.BitmapFactory.decodeResource
import androidx.annotation.DrawableRes
/** @author Aidan Follestad (@afollestad) */
interface BitmapProvider {
fun get(@DrawableRes res: Int): Bitmap
}
/** @author Aidan Follestad (@afollestad) */
class RealBitmapProvider(
private val context: Context
) : BitmapProvider {
override fun get(res: Int): Bitmap {
return decodeResource(context.resources, res)
}
}

View file

@ -31,7 +31,7 @@ interface NotificationProvider {
content: String,
intent: PendingIntent,
smallIcon: Int,
largeIcon: Bitmap
largeIcon: Bitmap? = null
): Notification
}
@ -46,7 +46,7 @@ class RealNotificationProvider(
content: String,
intent: PendingIntent,
smallIcon: Int,
largeIcon: Bitmap
largeIcon: Bitmap?
): Notification {
return NotificationCompat.Builder(context, channelId)
.setContentTitle(title)

View file

@ -19,10 +19,8 @@ import com.afollestad.nocknock.engine.validation.RealValidationManager
import com.afollestad.nocknock.engine.validation.ValidationManager
import org.koin.dsl.module.module
const val ENGINE_MODULE = "engine"
/** @author Aidan Follestad (@afollestad) */
val engineModule = module(ENGINE_MODULE) {
val engineModule = module {
single {
RealValidationManager(get(), get(), get(), get(), get(), get())

View file

@ -19,7 +19,6 @@ import android.annotation.TargetApi
import android.app.NotificationManager
import android.os.Build.VERSION_CODES
import com.afollestad.nocknock.notifications.Channel.CheckFailures
import com.afollestad.nocknock.utilities.providers.BitmapProvider
import com.afollestad.nocknock.utilities.providers.CanNotifyModel
import com.afollestad.nocknock.utilities.providers.IntentProvider
import com.afollestad.nocknock.utilities.providers.NotificationChannelProvider
@ -44,9 +43,7 @@ interface NockNotificationManager {
/** @author Aidan Follestad (@afollestad) */
class RealNockNotificationManager(
private val appIconRes: Int,
private val stockManager: NotificationManager,
private val bitmapProvider: BitmapProvider,
private val stringProvider: StringProvider,
private val intentProvider: IntentProvider,
private val channelProvider: NotificationChannelProvider,
@ -78,8 +75,7 @@ class RealNockNotificationManager(
title = model.notifyName(),
content = stringProvider.get(R.string.something_wrong),
intent = intent,
smallIcon = R.drawable.ic_notification,
largeIcon = bitmapProvider.get(appIconRes)
smallIcon = R.drawable.ic_notification
)
stockManager.notify(model.notifyTag(), model.notificationId(), newNotification)

View file

@ -15,21 +15,45 @@
*/
package com.afollestad.nocknock.notifications
import com.afollestad.nocknock.notifications.Qualifiers.APP_ICON_RES
import com.afollestad.nocknock.notifications.Qualifiers.MAIN_ACTIVITY_CLASS
import com.afollestad.nocknock.utilities.providers.BundleProvider
import com.afollestad.nocknock.utilities.providers.IntentProvider
import com.afollestad.nocknock.utilities.providers.JobInfoProvider
import com.afollestad.nocknock.utilities.providers.NotificationChannelProvider
import com.afollestad.nocknock.utilities.providers.NotificationProvider
import com.afollestad.nocknock.utilities.providers.RealBundleProvider
import com.afollestad.nocknock.utilities.providers.RealIntentProvider
import com.afollestad.nocknock.utilities.providers.RealJobInfoProvider
import com.afollestad.nocknock.utilities.providers.RealNotificationChannelProvider
import com.afollestad.nocknock.utilities.providers.RealNotificationProvider
import com.afollestad.nocknock.utilities.providers.RealSdkProvider
import com.afollestad.nocknock.utilities.providers.SdkProvider
import org.koin.dsl.module.module
const val NOTIFICATIONS_MODULE = "notifications"
object Qualifiers {
const val APP_ICON_RES = "main.app_icon_res"
const val MAIN_ACTIVITY_CLASS = "main_activity_class"
}
val notificationsModule = module(NOTIFICATIONS_MODULE) {
val notificationsModule = module {
factory {
RealIntentProvider(get(), get(name = MAIN_ACTIVITY_CLASS))
} bind IntentProvider::class
factory { RealSdkProvider() } bind SdkProvider::class
factory {
RealNotificationChannelProvider(get())
} bind NotificationChannelProvider::class
factory { RealNotificationProvider(get()) } bind NotificationProvider::class
factory { RealBundleProvider() } bind BundleProvider::class
factory { RealJobInfoProvider(get()) } bind JobInfoProvider::class
single {
RealNockNotificationManager(
get(name = APP_ICON_RES),
get(),
get(),
get(),
get(),

View file

@ -19,11 +19,8 @@ import android.app.Notification
import android.app.NotificationChannel
import android.app.NotificationManager
import android.app.PendingIntent
import android.graphics.Bitmap
import com.afollestad.nocknock.data.legacy.ServerModel
import com.afollestad.nocknock.data.model.ValidationMode.STATUS_CODE
import com.afollestad.nocknock.notifications.Channel.CheckFailures
import com.afollestad.nocknock.utilities.providers.BitmapProvider
import com.afollestad.nocknock.utilities.providers.CanNotifyModel
import com.afollestad.nocknock.utilities.providers.IntentProvider
import com.afollestad.nocknock.utilities.providers.NotificationChannelProvider
import com.afollestad.nocknock.utilities.providers.NotificationProvider
@ -48,10 +45,6 @@ class NockNotificationManagerTest {
private val somethingWentWrong = "something went wrong"
private val stockManager = mock<NotificationManager>()
private val appIcon = mock<Bitmap>()
private val bitmapProvider = mock<BitmapProvider> {
on { get(appIconRes) } doReturn appIcon
}
private val stringProvider = mock<StringProvider> {
on { get(R.string.something_wrong) } doReturn somethingWentWrong
}
@ -60,9 +53,7 @@ class NockNotificationManagerTest {
private val notificationProvider = mock<NotificationProvider>()
private val manager = RealNockNotificationManager(
appIconRes,
stockManager,
bitmapProvider,
stringProvider,
intentProvider,
channelProvider,
@ -121,19 +112,18 @@ class NockNotificationManagerTest {
whenever(
notificationProvider.create(
CheckFailures.id,
model.name,
"Testing",
somethingWentWrong,
pendingIntent,
R.drawable.ic_notification,
appIcon
R.drawable.ic_notification
)
).doReturn(notification)
manager.postStatusNotification(model)
verify(stockManager).notify(
model.url,
BASE_NOTIFICATION_REQUEST_CODE + model.id,
"https://hello.com",
BASE_NOTIFICATION_REQUEST_CODE + 1,
notification
)
verifyNoMoreInteractions(stockManager)
@ -142,7 +132,7 @@ class NockNotificationManagerTest {
@Test fun cancelStatusNotification() {
val model = fakeModel()
manager.cancelStatusNotification(model)
verify(stockManager).cancel(BASE_NOTIFICATION_REQUEST_CODE + model.id)
verify(stockManager).cancel(BASE_NOTIFICATION_REQUEST_CODE + 1)
verifyNoMoreInteractions(stockManager)
}
@ -152,10 +142,11 @@ class NockNotificationManagerTest {
verifyNoMoreInteractions(stockManager)
}
private fun fakeModel() = ServerModel(
id = 1,
url = "https://hello.com",
name = "Testing",
validationMode = STATUS_CODE
)
private fun fakeModel() = object : CanNotifyModel {
override fun notifyId() = 1
override fun notifyName() = "Testing"
override fun notifyTag() = "https://hello.com"
}
}