Fixed: Remaining InjectDispatcher detekt issues.

This commit is contained in:
MohitMaliFtechiz 2025-02-24 17:20:47 +05:30
parent 649da61523
commit 6e804384a9
31 changed files with 96 additions and 38 deletions

View File

@ -171,7 +171,6 @@ class CustomPageIndicator @JvmOverloads constructor(
val left = paddingLeft
val top = paddingTop
val right = width - paddingRight
val bottom = height - paddingBottom
val requiredWidth = getRequiredWidth()
val startLeft = left + (right - left - requiredWidth) / 2 + dotRadius
dotCenterX = FloatArray(pageCount)

View File

@ -17,7 +17,6 @@
*/
package org.kiwix.kiwixmobile.language.viewmodel
import android.annotation.SuppressLint
import androidx.appcompat.app.AppCompatActivity
import io.reactivex.Flowable
import io.reactivex.android.schedulers.AndroidSchedulers
@ -26,7 +25,7 @@ import org.kiwix.kiwixmobile.core.base.SideEffect
import org.kiwix.kiwixmobile.core.dao.NewLanguagesDao
import org.kiwix.kiwixmobile.core.zim_manager.Language
@SuppressLint("CheckResult")
@Suppress("IgnoredReturnValue")
data class SaveLanguagesAndFinish(
val languages: List<Language>,
val languageDao: NewLanguagesDao

View File

@ -44,6 +44,8 @@ import java.net.Socket
*/
abstract class PeerGroupHandshake(private var groupInfo: WifiP2pInfo) {
private val handshakeMessage = "Request Kiwix File Sharing"
@Suppress("InjectDispatcher")
suspend fun handshake(): InetAddress? =
withContext(Dispatchers.IO) {
Log.d(TAG, "Handshake in progress")

View File

@ -38,6 +38,7 @@ import java.net.ServerSocket
* many times as the no. of files).
*/
internal class ReceiverDevice(private val wifiDirectManager: WifiDirectManager) {
@Suppress("InjectDispatcher")
suspend fun receive(): Boolean {
return try {
withContext(Dispatchers.IO) {

View File

@ -48,6 +48,7 @@ internal class SenderDevice(
private val wifiDirectManager: WifiDirectManager,
private val fileReceiverDeviceAddress: InetAddress
) {
@Suppress("InjectDispatcher")
suspend fun send(fileItems: List<FileItem?>) =
withContext(Dispatchers.IO) {
// Delay trying to connect with receiver, to allow slow receiver devices to setup server

View File

@ -22,5 +22,5 @@ import org.kiwix.kiwixmobile.core.base.adapter.BaseDelegateAdapter
internal class WifiPeerListAdapter(wifiP2pDelegate: WifiP2pDelegate) :
BaseDelegateAdapter<WifiP2pDevice>(wifiP2pDelegate) {
override fun getIdFor(item: WifiP2pDevice) = item.deviceAddress.hashCode().toLong() ?: 0L
override fun getIdFor(item: WifiP2pDevice) = item.deviceAddress.hashCode().toLong()
}

View File

@ -449,6 +449,7 @@ class CopyMoveFileHandler @Inject constructor(
}
}
@Suppress("InjectDispatcher")
suspend fun deleteSourceFile(uri: Uri) = withContext(Dispatchers.IO) {
try {
DocumentsContract.deleteDocument(activity.applicationContext.contentResolver, uri)
@ -458,7 +459,7 @@ class CopyMoveFileHandler @Inject constructor(
}
}
@Suppress("MagicNumber")
@Suppress("MagicNumber", "InjectDispatcher")
private suspend fun copyFile(sourceUri: Uri, destinationFile: File) =
withContext(Dispatchers.IO) {
val contentResolver = activity.contentResolver

View File

@ -484,6 +484,7 @@ class LocalLibraryFragment : BaseFragment(), CopyMoveFileHandler.FileCopyMoveCal
}
}
@Suppress("InjectDispatcher")
private fun navigateToReaderFragment(file: File) {
if (!file.canRead()) {
activity.toast(string.unable_to_read_zim_file)

View File

@ -43,7 +43,7 @@ class KiwixServer @Inject constructor(
private val context: Context,
private val zimReaderContainer: ZimReaderContainer
) {
@Suppress("NestedBlockDepth")
@Suppress("NestedBlockDepth", "InjectDispatcher")
suspend fun createKiwixServer(selectedBooksPath: ArrayList<String>): KiwixServer =
withContext(Dispatchers.IO) {
val kiwixLibrary = Library()

View File

@ -73,7 +73,7 @@ class HotspotService :
super.onDestroy()
}
@Suppress("NestedBlockDepth")
@Suppress("NestedBlockDepth", "InjectDispatcher")
override fun onStartCommand(intent: Intent, flags: Int, startId: Int): Int {
when (intent.action) {
ACTION_START_SERVER -> {

View File

@ -17,7 +17,6 @@
*/
package org.kiwix.kiwixmobile.zimManager
import android.annotation.SuppressLint
import android.os.Build
import android.os.FileObserver
import io.reactivex.Flowable
@ -34,7 +33,7 @@ import org.kiwix.kiwixmobile.zimManager.FileSystemCapability.CAN_WRITE_4GB
import org.kiwix.kiwixmobile.zimManager.FileSystemCapability.INCONCLUSIVE
import java.io.File
@SuppressLint("CheckResult")
@Suppress("IgnoredReturnValue")
class Fat32Checker constructor(
sharedPreferenceUtil: SharedPreferenceUtil,
private val fileSystemCheckers: List<FileSystemChecker>

View File

@ -45,6 +45,7 @@ data class DeleteFiles(private val booksOnDiskListItems: List<BookOnDisk>) :
@Inject lateinit var zimReaderContainer: ZimReaderContainer
@Suppress("InjectDispatcher")
override fun invokeWith(activity: AppCompatActivity) {
(activity as BaseActivity).cachedComponent.inject(this)

View File

@ -31,6 +31,7 @@ import org.kiwix.kiwixmobile.core.zim_manager.fileselect_view.adapter.BooksOnDis
import org.kiwix.kiwixmobile.main.KiwixMainActivity
import org.kiwix.kiwixmobile.nav.destination.library.LocalLibraryFragmentDirections.actionNavigationLibraryToNavigationReader
@Suppress("InjectDispatcher")
data class OpenFileWithNavigation(private val bookOnDisk: BooksOnDiskListItem.BookOnDisk) :
SideEffect<Unit> {
override fun invokeWith(activity: AppCompatActivity) {

View File

@ -22,6 +22,7 @@ import android.content.Context
import android.content.ContextWrapper
import android.os.Build
import android.os.Environment
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import org.kiwix.kiwixmobile.core.utils.SharedPreferenceUtil
@ -31,10 +32,12 @@ import java.io.RandomAccessFile
object StorageDeviceUtils {
@JvmStatic
suspend fun getWritableStorage(context: Context) =
withContext(Dispatchers.IO) {
validate(externalMediaFilesDirsDevices(context), true)
}
suspend fun getWritableStorage(
context: Context,
dispatcher: CoroutineDispatcher = Dispatchers.IO
) = withContext(dispatcher) {
validate(externalMediaFilesDirsDevices(context), true)
}
@JvmStatic
fun getReadableStorage(context: Context): List<StorageDevice> {

View File

@ -22,6 +22,7 @@ import io.reactivex.Flowable
import io.reactivex.Single
import io.reactivex.functions.BiFunction
import io.reactivex.schedulers.Schedulers
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
@ -43,13 +44,14 @@ class StorageObserver @Inject constructor(
private val libkiwixBookmarks: LibkiwixBookmarks
) {
fun getBooksOnFileSystem(
scanningProgressListener: ScanningProgressListener
scanningProgressListener: ScanningProgressListener,
dispatcher: CoroutineDispatcher = Dispatchers.IO
): Flowable<List<BookOnDisk>> {
return scanFiles(scanningProgressListener)
.withLatestFrom(downloadRoomDao.downloads(), BiFunction(::toFilesThatAreNotDownloading))
.flatMapSingle { files ->
Single.create { emitter ->
CoroutineScope(Dispatchers.IO).launch {
CoroutineScope(dispatcher).launch {
try {
emitter.onSuccess(files.mapNotNull { convertToBookOnDisk(it) })
} catch (ignore: Exception) {

View File

@ -26,6 +26,7 @@ import io.reactivex.BackpressureStrategy.LATEST
import io.reactivex.Flowable
import io.reactivex.schedulers.Schedulers
import io.reactivex.subjects.BehaviorSubject
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
@ -219,10 +220,13 @@ class LibkiwixBookmarks @Inject constructor(
return libraryBooksList.any { it == bookId }
}
fun deleteBookmarks(bookmarks: List<LibkiwixBookmarkItem>) {
fun deleteBookmarks(
bookmarks: List<LibkiwixBookmarkItem>,
dispatcher: CoroutineDispatcher = Dispatchers.IO
) {
bookmarks.map { library.removeBookmark(it.zimId, it.bookmarkUrl) }
.also {
CoroutineScope(Dispatchers.IO).launch {
CoroutineScope(dispatcher).launch {
writeBookMarksAndSaveLibraryToFile()
updateFlowableBookmarkList()
}

View File

@ -22,6 +22,7 @@ import io.objectbox.kotlin.inValues
import io.objectbox.kotlin.query
import io.objectbox.query.QueryBuilder
import io.reactivex.rxjava3.core.Completable
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
@ -55,10 +56,10 @@ class NewBookDao @Inject constructor(private val box: Box<BookOnDiskEntity>) {
.toList()
.toFlowable()
.flatMap { booksList ->
completableFromCoroutine {
completableFromCoroutine(block = {
removeBooksThatAreInTrashFolder(booksList)
removeBooksThatDoNotExist(booksList.toMutableList())
}
})
.andThen(io.reactivex.rxjava3.core.Flowable.just(booksList))
}
}
@ -80,10 +81,13 @@ class NewBookDao @Inject constructor(private val box: Box<BookOnDiskEntity>) {
}
.map { it.map(::BookOnDisk) }
private fun completableFromCoroutine(block: suspend () -> Unit): Completable {
private fun completableFromCoroutine(
block: suspend () -> Unit,
dispatcher: CoroutineDispatcher = Dispatchers.IO
): Completable {
return Completable.defer {
Completable.create { emitter ->
CoroutineScope(Dispatchers.IO).launch {
CoroutineScope(dispatcher).launch {
try {
block()
emitter.onComplete()

View File

@ -23,6 +23,7 @@ import androidx.room.Insert
import androidx.room.OnConflictStrategy
import androidx.room.Query
import io.reactivex.Flowable
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
@ -88,8 +89,11 @@ abstract class NotesRoomDao : PageDao {
* the associated file should also be removed from storage,
* as it is no longer needed.
*/
private fun removeNoteFileFromStorage(noteFilePath: String) {
CoroutineScope(Dispatchers.IO).launch {
private fun removeNoteFileFromStorage(
noteFilePath: String,
dispatcher: CoroutineDispatcher = Dispatchers.IO
) {
CoroutineScope(dispatcher).launch {
val noteFile = File(noteFilePath)
if (noteFile.isFileExist()) {
noteFile.deleteFile()

View File

@ -58,6 +58,7 @@ import com.tonyodev.fetch2.R.drawable
import com.tonyodev.fetch2.R.string
import com.tonyodev.fetch2.Status
import com.tonyodev.fetch2.util.DEFAULT_NOTIFICATION_TIMEOUT_AFTER_RESET
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
@ -209,14 +210,19 @@ class FetchDownloadNotificationManager @Inject constructor(
}
}
fun showDownloadPauseNotification(fetch: Fetch, download: Download) {
CoroutineScope(Dispatchers.IO).launch {
fun showDownloadPauseNotification(
fetch: Fetch,
download: Download,
dispatcher: CoroutineDispatcher = Dispatchers.IO
) {
CoroutineScope(dispatcher).launch {
val notificationBuilder = getNotificationBuilder(download.id, download.id)
val cancelNotification = getCancelNotification(fetch, download, notificationBuilder)
downloadNotificationManager.notify(download.id, cancelNotification)
}
}
@Suppress("InjectDispatcher")
fun getCancelNotification(
fetch: Fetch,
download: Download,

View File

@ -18,16 +18,22 @@
package org.kiwix.kiwixmobile.core.extensions
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import java.io.File
suspend fun File.isFileExist(): Boolean = withContext(Dispatchers.IO) { exists() }
suspend fun File.isFileExist(dispatcher: CoroutineDispatcher = Dispatchers.IO): Boolean =
withContext(dispatcher) { exists() }
suspend fun File.freeSpace(): Long = withContext(Dispatchers.IO) { freeSpace }
suspend fun File.freeSpace(dispatcher: CoroutineDispatcher = Dispatchers.IO): Long =
withContext(dispatcher) { freeSpace }
suspend fun File.totalSpace(): Long = withContext(Dispatchers.IO) { totalSpace }
suspend fun File.totalSpace(dispatcher: CoroutineDispatcher = Dispatchers.IO): Long =
withContext(dispatcher) { totalSpace }
suspend fun File.canReadFile(): Boolean = withContext(Dispatchers.IO) { canRead() }
suspend fun File.canReadFile(dispatcher: CoroutineDispatcher = Dispatchers.IO): Boolean =
withContext(dispatcher) { canRead() }
suspend fun File.deleteFile(): Boolean = withContext(Dispatchers.IO) { delete() }
suspend fun File.deleteFile(dispatcher: CoroutineDispatcher = Dispatchers.IO): Boolean =
withContext(dispatcher) { delete() }

View File

@ -112,6 +112,7 @@ abstract class CoreMainActivity : BaseActivity(), WebViewProvider {
@Inject
lateinit var downloadMonitor: DownloadMonitor
@Suppress("InjectDispatcher")
override fun onCreate(savedInstanceState: Bundle?) {
setTheme(R.style.KiwixTheme)
super.onCreate(savedInstanceState)

View File

@ -1008,6 +1008,7 @@ abstract class CoreReaderFragment :
loadUrlWithCurrentWebview(navigationHistoryListItem.pageUrl)
}
@Suppress("InjectDispatcher")
override fun clearHistory() {
getCurrentWebView()?.clearHistory()
CoroutineScope(Dispatchers.IO).launch {
@ -2497,6 +2498,7 @@ abstract class CoreReaderFragment :
* openSearch("", isOpenedFromTabView = isInTabSwitcher, false)
* }
*/
@Suppress("InjectDispatcher")
private fun saveTabStates(onComplete: () -> Unit = {}) {
CoroutineScope(Dispatchers.Main).launch {
savingTabsMutex.withLock {

View File

@ -27,6 +27,7 @@ import org.kiwix.kiwixmobile.core.dao.PageDao
import org.kiwix.kiwixmobile.core.page.adapter.Page
import org.kiwix.kiwixmobile.core.page.viewmodel.PageState
@Suppress("InjectDispatcher")
data class DeletePageItems(
private val state: PageState<*>,
private val pageDao: PageDao,

View File

@ -25,6 +25,7 @@ import androidx.core.net.toUri
import eu.mhutti1.utils.storage.KB
import io.reactivex.Completable
import io.reactivex.schedulers.Schedulers
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.withContext
import org.kiwix.kiwixmobile.core.CoreApp
@ -67,6 +68,7 @@ class ZimFileReader constructor(
class Impl @Inject constructor(
private val darkModeConfig: DarkModeConfig
) : Factory {
@Suppress("InjectDispatcher")
override suspend fun create(zimReaderSource: ZimReaderSource): ZimFileReader? =
withContext(Dispatchers.IO) { // Bug Fix #3805
try {
@ -192,12 +194,15 @@ class ZimFileReader constructor(
}
@Suppress("UnreachableCode")
suspend fun load(uri: String): InputStream? =
withContext(Dispatchers.IO) {
suspend fun load(
uri: String,
dispatcher: CoroutineDispatcher = Dispatchers.IO
): InputStream? =
withContext(dispatcher) {
val extension = uri.substringAfterLast(".")
if (assetExtensions.any { it == extension }) {
try {
return@withContext loadAsset(uri)
return@withContext loadAsset(uri, dispatcher)
} catch (ioException: IOException) {
Log.e(TAG, "failed to write video for $uri", ioException)
}
@ -273,8 +278,12 @@ class ZimFileReader constructor(
throw IOException("Could not open pipe for $uri", ioException)
}
private suspend fun loadAsset(uri: String): InputStream? =
withContext(Dispatchers.IO) {
@Suppress("InjectDispatcher")
private suspend fun loadAsset(
uri: String,
dispatcher: CoroutineDispatcher
): InputStream? =
withContext(dispatcher) {
val item =
try {
jniKiwixReader.getEntryByPath(uri.filePath).getItem(true)

View File

@ -34,6 +34,7 @@ class ZimReaderContainer @Inject constructor(private val zimFileReaderFactory: F
field = value
}
@Suppress("InjectDispatcher")
suspend fun setZimReaderSource(zimReaderSource: ZimReaderSource?) {
if (zimReaderSource == zimFileReader?.zimReaderSource) {
return

View File

@ -305,6 +305,7 @@ class SearchFragment : BaseFragment() {
it.value.equals(query, ignoreCase = true)
}
@Suppress("InjectDispatcher")
suspend fun render(state: SearchState) {
renderingJob?.apply {
// cancel the children job. Since we are getting the result on IO thread

View File

@ -33,6 +33,7 @@ interface SearchResultGenerator {
}
class ZimSearchResultGenerator @Inject constructor() : SearchResultGenerator {
@Suppress("InjectDispatcher")
override suspend fun generateSearchResults(searchTerm: String, zimFileReader: ZimFileReader?) =
withContext(Dispatchers.IO) {
if (searchTerm.isNotEmpty()) {

View File

@ -26,6 +26,7 @@ import org.kiwix.kiwixmobile.core.base.SideEffect
import org.kiwix.kiwixmobile.core.dao.RecentSearchRoomDao
import org.kiwix.kiwixmobile.core.search.adapter.SearchListItem
@Suppress("InjectDispatcher")
data class DeleteRecentSearch(
private val searchListItem: SearchListItem,
private val recentSearchRoomDao: RecentSearchRoomDao,

View File

@ -27,6 +27,7 @@ import org.kiwix.kiwixmobile.core.dao.RecentSearchRoomDao
import org.kiwix.kiwixmobile.core.reader.addContentPrefix
import org.kiwix.kiwixmobile.core.search.adapter.SearchListItem
@Suppress("InjectDispatcher")
data class SaveSearchToRecents(
private val recentSearchRoomDao: RecentSearchRoomDao,
private val searchListItem: SearchListItem,

View File

@ -32,6 +32,7 @@ import android.provider.DocumentsContract
import android.provider.MediaStore
import android.webkit.URLUtil
import androidx.annotation.RequiresApi
import kotlinx.coroutines.CoroutineDispatcher
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
@ -65,8 +66,11 @@ object FileUtils {
@JvmStatic
@Synchronized
fun deleteCachedFiles(context: Context) {
CoroutineScope(Dispatchers.IO).launch {
fun deleteCachedFiles(
context: Context,
dispatcher: CoroutineDispatcher = Dispatchers.IO
) {
CoroutineScope(dispatcher).launch {
getFileCacheDir(context)?.deleteRecursively()
}
}
@ -84,7 +88,8 @@ object FileUtils {
fileloop@ while (alphabetFirst <= 'z') {
var alphabetSecond = 'a'
while (alphabetSecond <= 'z') {
val chunkPath = filePath.substring(0, filePath.length - 2) + alphabetFirst + alphabetSecond
val chunkPath =
filePath.substring(0, filePath.length - 2) + alphabetFirst + alphabetSecond
val fileChunk = File(chunkPath)
if (fileChunk.isFileExist()) {
fileChunk.deleteFile()

View File

@ -129,6 +129,7 @@ class CustomFileValidator @Inject constructor(private val context: Context) {
}
}
@Suppress("UseOrEmpty")
private fun scanDirs(dirs: Array<out File?>?, extensionToMatch: String): List<File> =
dirs?.filterNotNull()?.fold(listOf()) { acc, dir ->
acc + dir.walk().filter { it.extension.startsWith(extensionToMatch) }.toList()