Skip to content

Commit

Permalink
Merge branch 'release/3.0' into update-develop-update-3.0
Browse files Browse the repository at this point in the history
Signed-off-by: andresmr <[email protected]>

# Conflicts:
#	app/src/main/AndroidManifest.xml
#	app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureActivity.kt
#	app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCaptureContract.kt
#	app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCapturePagerAdapter.java
#	app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventCapture/EventCapturePresenterImpl.kt
#	app/src/main/java/org/dhis2/usescases/eventsWithoutRegistration/eventInitial/EventInitialActivity.java
#	app/src/main/java/org/dhis2/usescases/main/program/ProgramUi.kt
#	app/src/main/java/org/dhis2/usescases/searchTrackEntity/SearchTEUi.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/DashboardViewModel.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/TeiDashboardMobileActivity.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TEIDataContracts.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TEIDataFragment.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/TEIDataPresenter.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/dashboardfragments/teidata/teievents/EventAdapter.kt
#	app/src/main/java/org/dhis2/usescases/teiDashboard/teiProgramList/ui/EnrollToProgram.kt
#	app/src/main/java/org/dhis2/utils/granularsync/GranularSyncPresenter.kt
#	app/src/main/java/org/dhis2/utils/granularsync/GranularSyncRepository.kt
#	app/src/main/java/org/dhis2/utils/granularsync/SyncStatusDialog.kt
#	app/src/test/java/org/dhis2/usescases/teiDashboard/DashboardViewModelTest.kt
#	app/src/test/java/org/dhis2/utils/granularsync/GranularSyncPresenterTest.kt
#	compose-table/src/main/java/org/dhis2/composetable/ui/MultiOptionSelector.kt
#	gradle/libs.versions.toml
  • Loading branch information
andresmr committed May 2, 2024
2 parents 6999185 + c1be4e2 commit 08ecd9e
Show file tree
Hide file tree
Showing 22 changed files with 179 additions and 106 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ import org.dhis2.usescases.searchTrackEntity.SearchTEActivity
import org.dhis2.usescases.searchte.robot.searchTeiRobot
import org.dhis2.usescases.teidashboard.robot.eventRobot
import org.dhis2.usescases.teidashboard.robot.teiDashboardRobot
import org.junit.Ignore
import org.hisp.dhis.android.core.mockwebserver.ResponseController.GET
import org.junit.Rule
import org.junit.Test
import org.junit.runner.RunWith
Expand Down Expand Up @@ -48,12 +48,15 @@ class SyncFlowTest : BaseTest() {

override fun setUp() {
super.setUp()
setupMockServer()
workInfoStatusLiveData =
ApplicationProvider.getApplicationContext<AppTest>().mutableWorkInfoStatuses
}

@Test
fun shouldShowErrorWhenTEISyncFails() {
mockWebServerRobot.addResponse(GET, "/api/system/ping", API_PING_RESPONSE_OK)

val teiName = "Lars"
val teiLastName = "Overland"

Expand Down Expand Up @@ -95,6 +98,8 @@ class SyncFlowTest : BaseTest() {

@Test
fun shouldSuccessfullySyncSavedEvent() {
mockWebServerRobot.addResponse(GET, "/api/system/ping", API_PING_RESPONSE_OK)

prepareMalariaEventIntentAndLaunchActivity(ruleEventWithoutRegistration)

eventWithoutRegistrationRobot(composeTestRule) {
Expand All @@ -118,6 +123,8 @@ class SyncFlowTest : BaseTest() {

@Test
fun shouldShowErrorWhenSyncEventFails() {
mockWebServerRobot.addResponse(GET, "/api/system/ping", API_PING_RESPONSE_OK)

prepareMalariaEventIntentAndLaunchActivity(ruleEventWithoutRegistration)

eventWithoutRegistrationRobot(composeTestRule) {
Expand All @@ -141,6 +148,8 @@ class SyncFlowTest : BaseTest() {

@Test
fun shouldSuccessfullySyncSavedDataSet() {
mockWebServerRobot.addResponse(GET, "/api/system/ping", API_PING_RESPONSE_OK)

prepareFacilityDataSetIntentAndLaunchActivity(ruleDataSet)

dataSetRobot {
Expand Down Expand Up @@ -223,5 +232,6 @@ class SyncFlowTest : BaseTest() {

companion object {
const val LAB_MONITORING_EVENT_DATE = "28/6/2020"
const val API_PING_RESPONSE_OK = "mocks/systeminfo/ping.txt"
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -15,14 +15,6 @@ class MockedWorkManagerController(private val workInfoStatuses: LiveData<List<Wo

}

override fun syncDataForWorkers(
metadataWorkerTag: String,
dataWorkerTag: String,
workName: String
) {

}

override fun syncMetaDataForWorker(metadataWorkerTag: String, workName: String) {
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@ fun enrollmentRobot(enrollmentRobot: EnrollmentRobot.() -> Unit) {
class EnrollmentRobot : BaseRobot() {

fun clickOnAProgramForEnrollment(composeTestRule: ComposeTestRule, program: String) {
composeTestRule.onNodeWithTag(PROGRAM_TO_ENROLL.format(program))
composeTestRule.onNodeWithTag(PROGRAM_TO_ENROLL.format(program), useUnmergedTree = true)
.performClick()
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,19 +60,22 @@ class GranularSyncModule(
view,
repository,
schedulerProvider,
object : DispatcherProvider {
override fun io() = Dispatchers.IO

override fun computation() = Dispatchers.Default

override fun ui() = Dispatchers.Main
},
provideDispatchers(),
syncContext,
workManagerController,
smsSyncProvider,
)
}

@Provides
fun provideDispatchers() = object : DispatcherProvider {
override fun io() = Dispatchers.IO

override fun computation() = Dispatchers.Default

override fun ui() = Dispatchers.Main
}

@Provides
fun granularSyncRepository(
d2: D2,
Expand All @@ -87,6 +90,7 @@ class GranularSyncModule(
dhisProgramUtils,
periodUtils,
resourceManager,
provideDispatchers(),
)

@Provides
Expand Down
1 change: 1 addition & 0 deletions app/src/dhisUITesting/assets/mocks/systeminfo/ping.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
pong
Original file line number Diff line number Diff line change
Expand Up @@ -80,13 +80,15 @@ class GranularSyncModule(
periodUtils: DhisPeriodUtils,
preferenceProvider: PreferenceProvider,
resourceManager: ResourceManager,
dispatcherProvider: DispatcherProvider,
): GranularSyncRepository = GranularSyncRepository(
d2,
syncContext,
preferenceProvider,
dhisProgramUtils,
periodUtils,
resourceManager,
dispatcherProvider,
)

@Provides
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,6 @@ import androidx.work.WorkInfo
interface WorkManagerController {

fun syncDataForWorker(workerItem: WorkerItem)
fun syncDataForWorkers(metadataWorkerTag: String, dataWorkerTag: String, workName: String)
fun syncMetaDataForWorker(metadataWorkerTag: String, workName: String)
fun syncDataForWorker(metadataWorkerTag: String, workName: String)
fun beginUniqueWork(workerItem: WorkerItem)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,9 +30,7 @@ package org.dhis2.data.service.workManager

import androidx.lifecycle.LiveData
import androidx.lifecycle.MediatorLiveData
import androidx.work.Constraints
import androidx.work.ExistingWorkPolicy
import androidx.work.NetworkType
import androidx.work.OneTimeWorkRequest
import androidx.work.PeriodicWorkRequest
import androidx.work.WorkInfo
Expand All @@ -56,38 +54,10 @@ class WorkManagerControllerImpl(private val workManager: WorkManager) : WorkMana
}
}

override fun syncDataForWorkers(
metadataWorkerTag: String,
dataWorkerTag: String,
workName: String,
) {
val workerOneBuilder = OneTimeWorkRequest.Builder(SyncMetadataWorker::class.java)
workerOneBuilder
.addTag(metadataWorkerTag)
.setConstraints(
Constraints.Builder().setRequiredNetworkType(NetworkType.CONNECTED).build(),
)

val workerTwoBuilder = OneTimeWorkRequest.Builder(SyncDataWorker::class.java)
workerTwoBuilder
.addTag(dataWorkerTag)
.setConstraints(
Constraints.Builder().setRequiredNetworkType(NetworkType.CONNECTED).build(),
)

workManager
.beginUniqueWork(workName, ExistingWorkPolicy.KEEP, workerOneBuilder.build())
.then(workerTwoBuilder.build())
.enqueue()
}

override fun syncMetaDataForWorker(metadataWorkerTag: String, workName: String) {
val workerOneBuilder = OneTimeWorkRequest.Builder(SyncMetadataWorker::class.java)
workerOneBuilder
.addTag(metadataWorkerTag)
.setConstraints(
Constraints.Builder().setRequiredNetworkType(NetworkType.CONNECTED).build(),
)

workManager
.beginUniqueWork(workName, ExistingWorkPolicy.KEEP, workerOneBuilder.build())
Expand All @@ -98,9 +68,6 @@ class WorkManagerControllerImpl(private val workManager: WorkManager) : WorkMana
val workerTwoBuilder = OneTimeWorkRequest.Builder(SyncDataWorker::class.java)
workerTwoBuilder
.addTag(dataWorkerTag)
.setConstraints(
Constraints.Builder().setRequiredNetworkType(NetworkType.CONNECTED).build(),
)

workManager
.beginUniqueWork(workName, ExistingWorkPolicy.KEEP, workerTwoBuilder.build())
Expand Down Expand Up @@ -163,9 +130,6 @@ class WorkManagerControllerImpl(private val workManager: WorkManager) : WorkMana

syncBuilder.apply {
addTag(workerItem.workerName)
setConstraints(
Constraints.Builder().setRequiredNetworkType(NetworkType.CONNECTED).build(),
)
workerItem.delayInSeconds?.let {
setInitialDelay(it, TimeUnit.SECONDS)
}
Expand Down Expand Up @@ -218,9 +182,6 @@ class WorkManagerControllerImpl(private val workManager: WorkManager) : WorkMana

syncBuilder.apply {
addTag(workerItem.workerName)
setConstraints(
Constraints.Builder().setRequiredNetworkType(NetworkType.CONNECTED).build(),
)
workerItem.data?.let {
setInputData(it)
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -240,11 +240,9 @@ public void setProgram(@NonNull Program program) {
private void setUpActivityTitle() {
String activityTitle;
if (eventCreationType == EventCreationType.REFERAL) {
activityTitle = program.displayName() + " - " + getString(R.string.referral);
activityTitle = getString(R.string.referral);
} else {

activityTitle = eventUid == null ?
program.displayName() + " - " +
resourceManager.formatWithEventLabel(R.string.new_event_label, programStageUid, 1, false)
: program.displayName();
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,6 @@ class TEIDataContracts {

fun showProgramRuleErrorMessage()
fun goToEventInitial(eventCreationType: EventCreationType, programStage: ProgramStage)
fun updateEnrollment(update: Boolean)
fun displayOrgUnitSelectorForNewEvent(programUid: String, programStageUid: String)

fun goToEventDetails(
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -133,9 +133,6 @@ class TEIDataFragment : FragmentGlobalAbstract(), TEIDataContracts.View {

with(dashboardViewModel) {
eventUid().observe(viewLifecycleOwner, ::displayGenerateEvent)
updateEnrollment.observe(viewLifecycleOwner) { update ->
updateEnrollment(update)
}
noEnrollmentSelected.observe(viewLifecycleOwner) { noEnrollmentSelected ->
if (noEnrollmentSelected) {
showLegacyCard(dashboardModel.value as DashboardTEIModel)
Expand Down Expand Up @@ -383,7 +380,7 @@ class TEIDataFragment : FragmentGlobalAbstract(), TEIDataContracts.View {
programStageUid,
),
)
presenter.fetchEvents(true)
presenter.fetchEvents()
},
).show(parentFragmentManager, SCHEDULING_DIALOG)
}
Expand Down Expand Up @@ -458,18 +455,18 @@ class TEIDataFragment : FragmentGlobalAbstract(), TEIDataContracts.View {

override fun openEventDetails(intent: Intent, options: ActivityOptionsCompat) =
contractHandler.scheduleEvent(intent, options).observe(viewLifecycleOwner) {
updateEnrollment(true)
presenter.fetchEvents()
}

override fun openEventInitial(intent: Intent) =
contractHandler.editEvent(intent).observe(viewLifecycleOwner) {
updateEnrollment(true)
presenter.fetchEvents()
}

override fun openEventCapture(intent: Intent) {
if (dashboardActivity is TeiDashboardMobileActivity) {
contractHandler.editEvent(intent).observe(viewLifecycleOwner) {
updateEnrollment(true)
presenter.fetchEvents()
}
}
if (dashboardActivity is EventCaptureActivity) {
Expand Down Expand Up @@ -570,13 +567,6 @@ class TEIDataFragment : FragmentGlobalAbstract(), TEIDataContracts.View {
dashboardActivity.executeOnUIThread()
}

override fun updateEnrollment(update: Boolean) {
if (update) {
presenter.fetchEvents(update)
dashboardViewModel.updateDashboard()
}
}

companion object {
const val RC_EVENTS_COMPLETED = 1601
const val PREF_COMPLETED_EVENT = "COMPLETED_EVENT"
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -285,7 +285,7 @@ class TEIDataPresenter(
val intent = Intent(view.context, ProgramStageSelectionActivity::class.java)
intent.putExtras(bundle)
contractHandler.createEvent(intent).observe(view.viewLifecycleOwner()) {
view.updateEnrollment(true)
fetchEvents()
}
}

Expand Down Expand Up @@ -395,10 +395,8 @@ class TEIDataPresenter(
return options?.let { eventCreationOptionsMapper.mapToEventsByStage(it) } ?: emptyList()
}

fun fetchEvents(updateEnrollment: Boolean) {
if (updateEnrollment) {
groupingProcessor.onNext(dashboardRepository.getGrouping())
}
fun fetchEvents() {
groupingProcessor.onNext(dashboardRepository.getGrouping())
}

fun getEnrollment(): Enrollment? {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -89,6 +89,9 @@ class GranularSyncPresenter(
workerName = workerName()
}

private val _serverAvailability = MutableLiveData<Boolean>()
val serverAvailability: LiveData<Boolean> = _serverAvailability

private fun loadSyncInfo(forcedState: State? = null) {
viewModelScope.launch(dispatcher.io()) {
val syncState = async {
Expand Down Expand Up @@ -424,4 +427,15 @@ class GranularSyncPresenter(
}
}
}

fun checkServerAvailability() {
viewModelScope.launch {
try {
repository.checkServerAvailability()
_serverAvailability.value = true
} catch (error: RuntimeException) {
_serverAvailability.value = false
}
}
}
}
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
package org.dhis2.utils.granularsync

import io.reactivex.Single
import kotlinx.coroutines.withContext
import org.dhis2.R
import org.dhis2.commons.bindings.categoryOptionCombo
import org.dhis2.commons.bindings.countEventImportConflicts
Expand Down Expand Up @@ -41,6 +42,7 @@ import org.dhis2.commons.sync.ConflictType
import org.dhis2.commons.sync.SyncContext
import org.dhis2.commons.sync.SyncStatusItem
import org.dhis2.commons.sync.SyncStatusType
import org.dhis2.commons.viewmodel.DispatcherProvider
import org.dhis2.data.dhislogic.DhisProgramUtils
import org.hisp.dhis.android.core.D2
import org.hisp.dhis.android.core.common.State
Expand All @@ -57,6 +59,7 @@ class GranularSyncRepository(
private val dhisProgramUtils: DhisProgramUtils,
private val periodUtils: DhisPeriodUtils,
private val resourceManager: ResourceManager,
private val dispatcher: DispatcherProvider,
) {

fun getUiState(forcedState: State? = null): SyncUiState {
Expand Down Expand Up @@ -554,7 +557,7 @@ class GranularSyncRepository(

val teiMainAttribute = tei.let {
d2.teiMainAttributes(it.uid(), programUid)
} ?: emptyList()
}

val label = teiMainAttribute.firstOrNull()?.let { (attributeName, value) ->
"$attributeName: $value"
Expand Down Expand Up @@ -980,6 +983,10 @@ class GranularSyncRepository(
.map { it.displayName() }
}
}

suspend fun checkServerAvailability() = withContext(dispatcher.io()) {
d2.systemInfoModule().ping().blockingGet()
}
}

fun List<SyncStatusItem>.sortedByState(): List<SyncStatusItem> {
Expand Down
Loading

0 comments on commit 08ecd9e

Please sign in to comment.