Канал сопрограмм и тестирование - PullRequest
0 голосов
/ 07 апреля 2020

Я пытаюсь использовать kotlin ConflatedBroadcastChannel, чтобы уведомить «слушателя» об изменениях состояния.

Итак, у меня есть StatusRepository

class StatusRepository {

    private val channel = ConflatedBroadcastChannel(Status.DISCONNECTED)

    suspend fun updateStatus(status: Status) {
        channel.send(status)
    }

    suspend fun getStatus() = getStatusFlow().first()

    fun getStatusFlow() = channel.asFlow()
}

Тогда у меня есть класс Client, его можно упростить следующим образом:

class Client {

    private val statusRepository = StatusRepository()
    private val statusFlow = statusRepository.getStatusFlow()

    suspend fun connect(): Boolean {

        updateStatus(Status.CONNECTING)

        subscribeToStatus()

        val connected = someSocketAdapter.connectAsync()

        when {
            connected -> {
                updateStatus(Status.CONNECTED)
            }
            else -> {
                updateStatus(Status.DISCONNECTED)
            }
        }
        return connected
    }

    private suspend fun subscribeToStatus() {
        coroutineScope {
            launch {
                statusFlow.collectLatest {
                    when (it) {
                        Status.CONNECTING -> { } // not dealing with connecting
                        Status.CONNECTED -> onConnected()
                        Status.DISCONNECTED -> onDisconnected()
                    }
                }
            }
        }
    }

    suspend fun disconnectSocket() {
        updateStatus(Status.DISCONNECTED)
        someSocketAdapter.disconnect()
    }

    suspend fun login(wsRequest: WsRequest? = null): Boolean {
        // some login logic, return success        
        return true
    }

    suspend fun getStatus(): Status {
        return statusRepository.getStatus()
    }

    private suspend fun onConnected() {
        // perform onConnected logic
    }

    private suspend fun onDisconnected() {
        // perform onDisconnected logic
    }

    private suspend fun updateStatus(status: Status) {
        statusRepository.updateStatus(status)
    }
}

Итак, мои вопросы:

1)

, если этот метод внутри Client

        suspend fun disconnectSocket() {
            updateStatus(Status.DISCONNECTED)
            someSocketAdapter.disconnect()
        }

вызывается, поскольку Client отслеживает channel статуса, будет ли он запускать onDisconnected?

Если он не будет вызывать onDisconnected, что это подходящий способ для Client подписаться на channel изменения?

2) как правильно проверить Client метод connect?

Я пытался высмеивать возвращение someSocketAdapter.connectAsync() и надеемся проверить, что onConnected и onDisconnected вызывают, однако я получу

 java.lang.IllegalStateException: This job has not completed yet

, в котором, я считаю, что-то не так с подпиской на канал или как я подхожу к тесту.

Спасибо

...