https://kotlinlang.org logo
#android
Title
# android
i

iex

01/31/2020, 4:17 PM
I've this code in a `ViewModel`:
Copy code
private val testSingle = Single.just("item1")

private val foo = testPublishSubject.startWith(testSingle.toObservable().doOnNext {
    Timber.i(">>> single on next: $it")
}).doOnNext {
    Timber.i(">>> PS on next: $it")
}

fun onSomeEvent() {
    testPublishSubject.onNext("item2")
}
So it's a
PublishSubject
that gets initialized with a
Single
. On certain event, I push a new value to the subject. So far so good! The problem: I navigate to next screen and navigate back. Then the subject is reset to the initial
Single
value ("item1"). Why? The
ViewModel
is not reinitialized.
s

stantronic

01/31/2020, 4:34 PM
is the viewmodel in an activity or fragment?
h

Hitender Pannu

01/31/2020, 4:34 PM
Could you confirm again the lifecycle of the viewModel by logs inside init.
i

iex

01/31/2020, 4:35 PM
actually, the reason is that the fragment subscribes to
foo
again. (It's in a fragment and it subscribes in
onCreateView
)
But my use case is a bit more complex; The
Single
is fetching data from preferences, and it doesn't re-fetch it when going back for some reason.
okay I guess this is because the
Single
's result is cached... 🤔
so how do I fix this? I want that
Single
is executed again
s

stantronic

01/31/2020, 4:37 PM
yeah, the question is why the other value wasnt cached
turn it from a
val
to a
fun
i

iex

01/31/2020, 4:38 PM
because the fragment disposes the subscription and subscribes again
s

stantronic

01/31/2020, 4:38 PM
that should do it
i

iex

01/31/2020, 4:38 PM
probably yeah
trying it out
yeah it fixes it. Thanks @stantronic!
I want to understand it too though 😛
the code actually looks more like this:
Copy code
private val foo = testPublishSubject.startWith(myRepo.mySingleCall().toObservable())
Why is it basically reinitializing the
PublishSubject
but not calling the
Single
again?
I'd expect that this is called
myRepo.mySingleCall()
when reinitializing the subject
s

stantronic

01/31/2020, 4:43 PM
what does the mySingleCall() function look like - it sounds like something has been cached at that level
i

iex

01/31/2020, 4:44 PM
not really...
Copy code
fun selectedModel(): Single<Optional<Model>> =
    (preferences.getString(SELECTED_MODEL)?.let {
        Some(Model(it))
    } ?: None).let{ Single.just(it) }
it just accesses preferences
s

stantronic

01/31/2020, 4:45 PM
hmm. strange
i

iex

01/31/2020, 4:48 PM
that code can actually be simplified to
fun selectedModel() = Single.just("foo")
s

stantronic

01/31/2020, 5:01 PM
if that was the one that was a “val” earlier, then it would capture the value at that point. You could rewrite as
Copy code
Single.fromCallable { /* fetch from preferences here */  }
and that should also fetch each time.
i

iex

01/31/2020, 5:05 PM
but it's not a
val
. I posted this snippet above:
Copy code
private val foo = testPublishSubject.startWith(myRepo.mySingleCall().toObservable())
I mean the
Single
is not a
val
where
mySingleCall()
is implemented basically like this:
fun mySingleCall() = Single.just("foo")
(it fetches from preferences instead but it comes down to the same)