Всем здравствуйте. Мне стало любопытно как в композе правильно/канонично обрабатывать

следующую ситуацию:
Есть предположим кнопка, при нажатию на которую запускается какой-то запрос на сервер через suspend функцию, и пока запрос идёт кнопка должна быть заблокирована как-то так:
val cs = rememberCoroutineScope()
var buttonEnabled by remember { mutableState(true) }
...
Button(onClick = {
buttonEnabled = false
cs.launch {
myService.callServer();
buttonEnabled = true
}

}, enabled = buttonEnabled )

Если, пока запрос на сервер выполняется, эта композ функция (с кнопкой и скоупом) выйдет из композиции скоуп будет убит и соответственно запрос на сервер будет отменён (по крайней мере частично). Для некоторых ситуаций такое поведение меня не устраивает - т.е. я не хочу чтобы запрос отменялся (особенно если он отменится до посылки на сервер потому что например callServer делает что-то до и это занимает достаточно времени чтобы элемент ушёл из композиции). Для этого я завёл специальный скоуп который живёт на уровне корневой компоуз функции и использую его:
val cs = mySpecialBackgroundScope
// val cs = rememberCoroutineScope()
Непонятно что будет происходить с после myService.callServer();
когда запрос завершится в то время когда функция уже вышла из композиции?

12 ответов

10 просмотров

видимо ничего... отменится саспенд функция и всё

Я бы сделал немного по другому. Я бы сделал чтобы сервис запускал в себе функцию и возвращал бы job. А вы уже делайте job.join и потом включайте кнопку.

Agry-Gami Автор вопроса
Anton Potekhin
Я бы сделал немного по другому. Я бы сделал чтобы ...

Сделал бы что? Чтобы сделать job.join мне в любом случае понадобится скоуп. Чтобы создать job внутри функции сервиса мне тоже нужен какой-то скоуп. Даже если я снаружи буду использовать скоуп из композа а внутри какой-то другой скоуп - это никак не отвечает на мой вопрос... точнее это настолько меняет условия задачи что вопрос теряет смысл :)

а нельзя это всё вынести на уровень вью модели? она работает с suspend функциями и отдаёт нужный стейт наружу через LiveData?

Agry-Gami Автор вопроса
Артём Мельник
а нельзя это всё вынести на уровень вью модели? он...

Да при чём тут это? Ну хорошо, предположим жизненный цикл вью модели привязан к навигации (т.е. уходит экран - убивают вью модель) - тот же самый вопрос, только теперь про вью модели :)

Agry Gami
Да при чём тут это? Ну хорошо, предположим жизненн...

а если умер экран, есть ли смысл думать о кнопках на нём?)

Agry-Gami Автор вопроса
Артём Мельник
а если умер экран, есть ли смысл думать о кнопках ...

Так речь не про кнопки а про взаимодействие с захваченными переменными. Если захвачен не булеан а что-то посложнее и что-то что завязано на компоуз - оно же не сможет отработать.

Agry Gami
Так речь не про кнопки а про взаимодействие с захв...

я не особо силён в компоузе, но кажется, что все запросы должны быть всё же во вью моделе, а из неё торчать наружу стейт и не будет никакого захвата переменных

Agry-Gami Автор вопроса
Артём Мельник
я не особо силён в компоузе, но кажется, что все з...

в моём примере это не "запрос" - т.е. мне не нужны никакие данные от него, это операция что от неё должно торчать из вью модели?

Agry Gami
в моём примере это не "запрос" - т.е. мне не нужны...

так погоди, ты ведь делаешь обращение к myService и, когда он ответит, ты хочешь поменять состояние кнопки, сменить enabled?

Agry Gami
да...

так почему из вью модели на может торчать какой-то стейт а-ля State(val isButtonEnabled: Boolean), который ты обернёшь в LiveData и добавить метод во ViewModel, по типу class SomeViewModel : ViewModel() { private val state: MutableLiveData = ... val state: LiveData = ... fun onSomeButtonClicked() { state.value = state.value!!.copy(isButtonEnabled = false) scope.launch { ..... state.value = state.value!!.copy(isButtonEnabled = true) } }

Похожие вопросы

Обсуждают сегодня

Сonst magicTgHTML = (text, entities) => { let processedText = text; let offsetShift = 0; entities.forEach(entity => { const { offset, length, type, url, ...
Андрей
1
В смысле более затратная? Общая стоимость владения лошадью меньше, чем автомобиля. В среднем.
Sergej R
10
👋🏻3дpaвcтвуйтe 👋🏻 Ищeм 3aинтepecoвaнныx в дoxoде  в cфepe cryрtо!!📈 Oбучeниe Бecплaтнoe!💻 Peзультaт ужe в пepвый дeнь oбучeния!! Moжнo удeлять 1-2 чaca в дeнь!! 3aинтepecoвa...
Руслан Ал
3
Кстати, раз про скачивание файлов разговор зашел) Сделал бота для себя (транскрибирующего и суммаризирующего встречи) но не ожидал что за 2 месяца 10к пользователей набежит😅...
Andrey Obolenskiy
8
коллеги привет. уже второй день бьемся об заклад с одной ошибкой, может вы сталкивались с таки странным поведением? есть тестовый сервер, на который паблишим релизную версию W...
Magzhan
11
t.me/<username> и tg://user?id=<id> отваливаются по понятным причинам
Denis 🐍|👑 | darling! 🥰
7
Вы когда из вики.... копировали, не обратили внимание на года(ы)? 😉 ==== если до 1917 года в Москве было около 15 000 легковых извозчиков, то к 1920 году их осталось 5 000, а ...
Igor Mitin
4
Гайз, кто-нибудь пробовал запустить probe-rs под камень, которого нет в probe-rs? Мб есть какой-нибудь пример у кого... Через target-gen попробовал сгенерировать chip-descript...
Максим Смирнов
2
👋🏻3дpaвcтвуйтe 👋🏻 Ищeм 3aинтepecoвaнныx в дoxoде в cфepe cryрtо!!📈 Oбучeниe Бecплaтнoe!💻 Peзультaт ужe в пepвый дeнь oбучeния!! Moжнo удeлять 1-2 чaca в дeнь!! 3aинтepecoвa...
Рустам Вв
4
На счёт замены разрабов нейронами: Вряд-ли заказчик сможет нормально пояснить нейросети, чё он хочет. Они то человеку нормально пояснить не могут, не то что нейросети. Так что...
Alex Kom
1
Карта сайта