【发布时间】:2023-02-24 00:47:39
【问题描述】:
我正在为一项周期性任务实施自定义 WorkManager(使用 AppStartup 和 Hilt),但经过大量修补、研究和等待后,任务并未启动。
下面是我的设置
工人阶级
覆盖 doWork() 返回 Result.success() 或 Result.error()。我有一个 Companion 使用静态 schedule() 来设置约束条件,要求并打电话WorkManager.getInstance(context)
class ScoresWorker @AssistedInject constructor(
@Assisted private val context: Context,
@Assisted params: WorkerParameters,
private val db: ScoresDatabase,
private val api: ScoresAPI
) : CoroutineWorker(context, params) {
private val dao = db.dao
override suspend fun doWork(): Result {
Timber.i("DoWork Called")
return try {
val response = api.getFixturesByDate()
dao.clearFixtures()
dao.insertFixtures(response.response.map { it.toEntity() })
Result.success()
} catch (e: Exception) {
Timber.i("WorKError - Exception")
Result.failure(workDataOf(SCORES_WORKER_ERROR_KEY to e.localizedMessage))
}
}
companion object {
private const val SCORES_WORKER_ID = "scores_worker"
fun schedule(context: Context) {
Timber.i("companion Obj schedule() called")
val constraints = Constraints.Builder()
.setRequiredNetworkType(NetworkType.CONNECTED)
.build()
val request = PeriodicWorkRequestBuilder<ScoresWorker>(
15, TimeUnit.MINUTES, 5, TimeUnit.MINUTES
).setConstraints(constraints)
.build()
WorkManager.getInstance(context)
.enqueueUniquePeriodicWork(
SCORES_WORKER_ID, ExistingPeriodicWorkPolicy.KEEP, request
)
}
}
}
助手类
单例助手类调用上面的ScoresWorker.schedule(context) 并确保 WorkManager 只初始化一次并且只有一个实例。
@Singleton
class WorkManagerInitializer @Inject constructor(
@ApplicationContext private val context: Context, ) {
private var isInitialized: Boolean = false
fun initializeWorkManager() {
Timber.i("initialization called - value: $isInitialized")
if (isInitialized) return
isInitialized = true
ScoresWorker.schedule(context)
}
}
启动时
为了提高应用程序启动性能,我从应用程序启动序列中删除了诸如调度 WorkManager 之类的繁重内容,将其移至 onStart()。
@AndroidEntryPoint
class MainActivity : ComponentActivity() {
@Inject
lateinit var initializationHelper: WorkManagerInitializer
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContent { .... }
}
override fun onStart() {
super.onStart()
initializationHelper.initializeWorkManager()
}
}
应用类和
应用程序类实现Configuration.Provider界面
@HiltAndroidApp
class InstantScoreApp : Application(), Configuration.Provider {
override fun onCreate() { ... }
@Inject
lateinit var workerFactory: HiltWorkerFactory
override fun getWorkManagerConfiguration(): Configuration {
return Configuration.Builder()
.setWorkerFactory(workerFactory)
.build()
}
}
显现
首先按照 Docs 中的描述尝试这种方法
...
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
tools:node="remove"
>
</provider>-->
</application>
这也没有用。
<provider
android:name="androidx.startup.InitializationProvider"
android:authorities="${applicationId}.androidx-startup"
android:exported="false"
tools:node="merge">
<meta-data
android:name="androidx.work.WorkManagerInitializer"
android:value="androidx.startup"
tools:node="remove" />
</provider>
我在work-runtime-ktx v 2.8.0和startup-runtime v1.1.
我需要帮助了解我可能缺少什么才能使此设置正常工作。请帮助。
【问题讨论】:
-
logcat 中是否显示任何错误并检查互联网是否可用?
-
另请检查您是否在清单文件中添加了 InstantScoreApp 应用程序类。
-
嗨 Tausif,到目前为止没有发现任何错误,并且已经在模拟器和物理设备上都进行了尝试。互联网已开启并已申请互联网许可。通过
android:name=".InstantScoreApp"标签将应用程序类添加到清单中。 -
请检查以下库是否已添加到您的 gradle 文件中。实施“androidx.work:work-runtime-ktx:2.7.0”实施(“androidx.hilt:hilt-work:1.0.0”)kapt(“androidx.hilt:hilt-compiler:1.0.0”)kapt“ com.google.dagger:hilt-android-compiler:2.39.1"
-
您似乎在 ScoresWorker 类中扩展了 CoroutineWorker。您可以尝试使用 worker 类而不是 CoroutineWorker。我还在答案部分提供了详细信息。
标签: android android-workmanager