Einführung in Abläufe

Die Kotlin-Version der Home APIs verwendet Abläufe, eine Funktion der Kotlin-Sprache, die leistungsstarke Funktionen für die Verarbeitung asynchroner Datenstreams bietet, z. B. Transformation, Filterung, Zuordnung, Konvertierung in und aus Sammlungen usw.

Coroutinen sind eng mit Abläufen verbunden und bieten eine elegante Abstraktion zum Schreiben asynchronen Codes. So müssen Entwickler nicht explizit Rückrufroutinen schreiben. Abläufe funktionieren Hand in Hand mit coroutines und dienen als Möglichkeit, Daten asynchron aus coroutines abzurufen, ohne auf den Abschluss einer Funktion oder eines Threads warten zu müssen.

Daten werden vom Verbraucher in einem Prozess abgerufen, der als Erhebung bezeichnet wird. Kotlin-Abläufe haben eine collect()-Funktion, die für diesen Zweck verwendet werden kann. Was bei der Erhebung in einem Fluss passiert, hängt vom jeweiligen Flusstyp ab.

Kotlin-Abläufe (Flow<T>) sind standardmäßig kalt. Das bedeutet, dass der Code des Ablauf-Builders nur dann Daten generiert, wenn collect() aufgerufen wird. Bei einem Hot-Flow werden Daten dagegen sofort generiert und im Arbeitsspeicher wie in einer Warteschlange zwischengespeichert, bis sie verwendet werden. Da bei einem Hot-Flow Daten im Arbeitsspeicher beibehalten werden, gilt er als zustandsorientiert.

Mit dem Operator shareIn können Sie einen kalten Fluss in einen heißen Fluss umwandeln (siehe Kalte Flüsse mit shareIn in heiße Flüsse umwandeln). Sie können auch SharedFlow oder StateFlow verwenden, um einen kalten Fluss in einen heißen Fluss umzuwandeln.

Verwendung von Aufrufabfolgen in der Beispielanwendung

Die Beispiel-App verwendet Ansichtsmodelle in Jetpack Compose, die mit den Abläufen in den Home APIs verbunden sind. Viele der UI-Elemente der Beispiel-App werden vom Status gesteuert, können aber interaktiv genutzt werden. In der Beispiel-App wird der Status von Geräten mit einem „optimistischen“ Status in der Benutzeroberfläche kombiniert, um eine Echtzeit-Nutzererfahrung zu ermöglichen. Der Begriff „optimistisch“ bedeutet, dass die App davon ausgeht, dass eine bestimmte Aktion erfolgreich war, und die Benutzeroberfläche sofort aktualisiert, um das erwartete Ergebnis widerzuspiegeln, ohne auf eine Bestätigung zu warten. Wenn die Aktion fehlschlägt, wird die Benutzeroberfläche aktualisiert, um den tatsächlichen Status widerzuspiegeln.

In der Beispielanwendung werden für jede Ebene des Ansichtsmodells (Gebäude, Räume, Geräte) Aufrufabfolgen erstellt. Das ist beispielsweise bei Strukturen mit dem folgenden Aufruf in GlobalViewModel.kt der Fall:

  fun getStructuresState(): StateFlow<List<StructureModel>?> =
    homeClient
      .structures()
      .map { structures -> structures.map { StructureModel(it.name, it) }.sortedBy { it.name } }
      .handleErrors()
      .flowOn(Dispatchers.IO)
      .stateIn(scope = viewModelScope, started = SharingStarted.WhileSubscribed(), null)

emitAll() erfasst alle Werte aus dem angegebenen Fluss und sendet sie an den Aggregator. stateIn() gibt den zuletzt gesendeten Wert aus einer einzelnen laufenden Instanz des Upstream-Flows für mehrere Downstream-Abonnenten frei. Weitere Informationen finden Sie in der Referenz kotlinx.coroutines.flow.

Jetpack Compose

Wenn Sie Ablaufobjekte im lokalen Speicher speichern und verhindern möchten, dass sie beendet werden, verwenden Sie die Kotlin-API remember.

Wenn Sie in Jetpack Compose collectAsStateWithLifecycle() verwenden, verwaltet Jetpack automatisch das Abonnieren und Abbestellen von Abläufen, je nachdem, ob die Anwendungs-UI, in der dieser Status angezeigt wird, sich im Vordergrund befindet oder nicht.

Dies geschieht über einen einfachen Aufruf in der Beispielanwendung. Mit der oben gezeigten Funktion getStructuresState():

val structuresList by
    remember(globalViewModel) { globalViewModel.getStructuresState() }.collectAsStateWithLifecycle()

Wenn sich nun ein Status für die Struktur ändert (z. B. der name), wird dieser aktualisierte Status automatisch in der zusammensetzbaren Funktion berücksichtigt, in der er verwendet wird. In der Beispielanwendung ist das die HomeActivityContent()-Funktion.

Ressourcen

Weitere Informationen zu Kotlin, Abläufen, Coroutinen und Jetpack Compose finden Sie in den folgenden Ressourcen: