Skip to content

Commit dcf4816

Browse files
committed
Merge branch 'release/0.2.1' into main
2 parents 141cac7 + 53785aa commit dcf4816

File tree

1,026 files changed

+2219
-2488
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

1,026 files changed

+2219
-2488
lines changed

CHANGES.md

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,23 @@
1+
Changes in Element X v0.2.1 (2023-09-20)
2+
========================================
3+
4+
Features ✨
5+
----------
6+
- Bump Rust SDK to `v0.1.56`
7+
- [Rich text editor] Add link support to rich text editor ([#1309](https://github.com/vector-im/element-x-android/issues/1309))
8+
- Let the SDK figure the best scheme given an homeserver URL (thus allowing HTTP homeservers) ([#1382](https://github.com/vector-im/element-x-android/issues/1382))
9+
10+
Bugfixes 🐛
11+
----------
12+
- Fix ANR on RoomList when notification settings change. ([#1370](https://github.com/vector-im/element-x-android/issues/1370))
13+
14+
Other changes
15+
-------------
16+
- Element Call: support scheme `io.element.call` ([#1377](https://github.com/vector-im/element-x-android/issues/1377))
17+
- [DI] Rework how dagger components are created and provided. ([#1378](https://github.com/vector-im/element-x-android/issues/1378))
18+
- Remove usage of async-uniffi as it leads to a deadlocks and memory leaks. ([#1381](https://github.com/vector-im/element-x-android/issues/1381))
19+
20+
121
Changes in Element X v0.2.0 (2023-09-18)
222
========================================
323

app/src/main/kotlin/io/element/android/x/MainActivity.kt

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -34,8 +34,8 @@ import com.bumble.appyx.core.integrationpoint.NodeComponentActivity
3434
import com.bumble.appyx.core.plugin.NodeReadyObserver
3535
import io.element.android.libraries.architecture.bindings
3636
import io.element.android.libraries.core.log.logger.LoggerTag
37-
import io.element.android.libraries.theme.ElementTheme
3837
import io.element.android.libraries.designsystem.utils.LocalSnackbarDispatcher
38+
import io.element.android.libraries.theme.ElementTheme
3939
import io.element.android.x.di.AppBindings
4040
import io.element.android.x.intent.SafeUriHandler
4141
import timber.log.Timber
@@ -74,7 +74,6 @@ class MainActivity : NodeComponentActivity() {
7474
NodeHost(integrationPoint = appyxIntegrationPoint) {
7575
MainNode(
7676
it,
77-
appBindings.mainDaggerComponentOwner(),
7877
plugins = listOf(
7978
object : NodeReadyObserver<MainNode> {
8079
override fun init(node: MainNode) {
@@ -83,7 +82,8 @@ class MainActivity : NodeComponentActivity() {
8382
mainNode.handleIntent(intent)
8483
}
8584
}
86-
)
85+
),
86+
context = applicationContext
8787
)
8888
}
8989
}

app/src/main/kotlin/io/element/android/x/MainNode.kt

Lines changed: 7 additions & 38 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@
1616

1717
package io.element.android.x
1818

19+
import android.content.Context
1920
import android.content.Intent
2021
import android.os.Parcelable
2122
import androidx.compose.runtime.Composable
@@ -27,24 +28,17 @@ import com.bumble.appyx.core.navigation.model.permanent.PermanentNavModel
2728
import com.bumble.appyx.core.node.Node
2829
import com.bumble.appyx.core.node.ParentNode
2930
import com.bumble.appyx.core.plugin.Plugin
30-
import io.element.android.appnav.LoggedInAppScopeFlowNode
3131
import io.element.android.appnav.RootFlowNode
32-
import io.element.android.appnav.room.RoomLoadedFlowNode
33-
import io.element.android.libraries.architecture.bindings
3432
import io.element.android.libraries.architecture.createNode
33+
import io.element.android.libraries.di.ApplicationContext
3534
import io.element.android.libraries.di.DaggerComponentOwner
36-
import io.element.android.libraries.matrix.api.MatrixClient
37-
import io.element.android.libraries.matrix.api.room.MatrixRoom
38-
import io.element.android.x.di.MainDaggerComponentsOwner
39-
import io.element.android.x.di.RoomComponent
40-
import io.element.android.x.di.SessionComponent
4135
import kotlinx.coroutines.launch
4236
import kotlinx.parcelize.Parcelize
4337

4438
class MainNode(
4539
buildContext: BuildContext,
46-
private val mainDaggerComponentOwner: MainDaggerComponentsOwner,
4740
plugins: List<Plugin>,
41+
@ApplicationContext context: Context,
4842
) : ParentNode<MainNode.RootNavTarget>(
4943
navModel = PermanentNavModel(
5044
navTargets = setOf(RootNavTarget),
@@ -53,38 +47,12 @@ class MainNode(
5347
buildContext = buildContext,
5448
plugins = plugins,
5549
),
56-
DaggerComponentOwner by mainDaggerComponentOwner {
50+
DaggerComponentOwner {
5751

58-
private val loggedInFlowNodeCallback = object : LoggedInAppScopeFlowNode.LifecycleCallback {
59-
override fun onFlowCreated(identifier: String, client: MatrixClient) {
60-
val component = bindings<SessionComponent.ParentBindings>().sessionComponentBuilder().client(client).build()
61-
mainDaggerComponentOwner.addComponent(identifier, component)
62-
}
63-
64-
override fun onFlowReleased(identifier: String, client: MatrixClient) {
65-
mainDaggerComponentOwner.removeComponent(identifier)
66-
}
67-
}
68-
69-
private val roomFlowNodeCallback = object : RoomLoadedFlowNode.LifecycleCallback {
70-
override fun onFlowCreated(identifier: String, room: MatrixRoom) {
71-
val component = bindings<RoomComponent.ParentBindings>().roomComponentBuilder().room(room).build()
72-
mainDaggerComponentOwner.addComponent(identifier, component)
73-
}
74-
75-
override fun onFlowReleased(identifier: String, room: MatrixRoom) {
76-
mainDaggerComponentOwner.removeComponent(identifier)
77-
}
78-
}
52+
override val daggerComponent = (context as DaggerComponentOwner).daggerComponent
7953

8054
override fun resolve(navTarget: RootNavTarget, buildContext: BuildContext): Node {
81-
return createNode<RootFlowNode>(
82-
context = buildContext,
83-
plugins = listOf(
84-
loggedInFlowNodeCallback,
85-
roomFlowNodeCallback,
86-
)
87-
)
55+
return createNode<RootFlowNode>(context = buildContext)
8856
}
8957

9058
@Composable
@@ -100,4 +68,5 @@ class MainNode(
10068

10169
@Parcelize
10270
object RootNavTarget : Parcelable
71+
10372
}

app/src/main/kotlin/io/element/android/x/di/AppBindings.kt

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,6 @@ import io.element.android.libraries.matrix.api.tracing.TracingService
2424

2525
@ContributesTo(AppScope::class)
2626
interface AppBindings {
27-
fun mainDaggerComponentOwner(): MainDaggerComponentsOwner
2827
fun snackbarDispatcher(): SnackbarDispatcher
2928
fun tracingService(): TracingService
3029
fun bugReporter(): BugReporter
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
/*
2+
* Copyright (c) 2023 New Vector Ltd
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package io.element.android.x.di
18+
19+
import com.squareup.anvil.annotations.ContributesBinding
20+
import io.element.android.appnav.di.RoomComponentFactory
21+
import io.element.android.libraries.di.SessionScope
22+
import io.element.android.libraries.matrix.api.room.MatrixRoom
23+
import javax.inject.Inject
24+
25+
@ContributesBinding(SessionScope::class)
26+
class DefaultRoomComponentFactory @Inject constructor(
27+
private val roomComponentBuilder: RoomComponent.Builder
28+
) : RoomComponentFactory {
29+
30+
override fun create(room: MatrixRoom): Any {
31+
return roomComponentBuilder.room(room).build()
32+
}
33+
}
Lines changed: 33 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,33 @@
1+
/*
2+
* Copyright (c) 2023 New Vector Ltd
3+
*
4+
* Licensed under the Apache License, Version 2.0 (the "License");
5+
* you may not use this file except in compliance with the License.
6+
* You may obtain a copy of the License at
7+
*
8+
* http://www.apache.org/licenses/LICENSE-2.0
9+
*
10+
* Unless required by applicable law or agreed to in writing, software
11+
* distributed under the License is distributed on an "AS IS" BASIS,
12+
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13+
* See the License for the specific language governing permissions and
14+
* limitations under the License.
15+
*/
16+
17+
package io.element.android.x.di
18+
19+
import com.squareup.anvil.annotations.ContributesBinding
20+
import io.element.android.appnav.di.SessionComponentFactory
21+
import io.element.android.libraries.di.AppScope
22+
import io.element.android.libraries.matrix.api.MatrixClient
23+
import javax.inject.Inject
24+
25+
@ContributesBinding(AppScope::class)
26+
class DefaultSessionComponentFactory @Inject constructor(
27+
private val sessionComponentBuilder: SessionComponent.Builder
28+
) : SessionComponentFactory {
29+
30+
override fun create(client: MatrixClient): Any {
31+
return sessionComponentBuilder.client(client).build()
32+
}
33+
}

app/src/main/kotlin/io/element/android/x/di/MainDaggerComponentsOwner.kt

Lines changed: 0 additions & 47 deletions
This file was deleted.

appnav/src/main/kotlin/io/element/android/appnav/LoggedInAppScopeFlowNode.kt

Lines changed: 7 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -31,12 +31,13 @@ import com.bumble.appyx.core.plugin.plugins
3131
import dagger.assisted.Assisted
3232
import dagger.assisted.AssistedInject
3333
import io.element.android.anvilannotations.ContributesNode
34+
import io.element.android.appnav.di.SessionComponentFactory
3435
import io.element.android.libraries.architecture.NodeInputs
3536
import io.element.android.libraries.architecture.bindings
3637
import io.element.android.libraries.architecture.createNode
3738
import io.element.android.libraries.architecture.inputs
38-
import io.element.android.libraries.architecture.waitForChildAttached
3939
import io.element.android.libraries.di.AppScope
40+
import io.element.android.libraries.di.DaggerComponentOwner
4041
import io.element.android.libraries.matrix.api.MatrixClient
4142
import io.element.android.libraries.matrix.ui.di.MatrixUIBindings
4243
import kotlinx.parcelize.Parcelize
@@ -50,44 +51,36 @@ import kotlinx.parcelize.Parcelize
5051
class LoggedInAppScopeFlowNode @AssistedInject constructor(
5152
@Assisted buildContext: BuildContext,
5253
@Assisted plugins: List<Plugin>,
54+
sessionComponentFactory: SessionComponentFactory,
5355
) : ParentNode<LoggedInAppScopeFlowNode.NavTarget>(
5456
navModel = PermanentNavModel(
5557
navTargets = setOf(NavTarget),
5658
savedStateMap = buildContext.savedStateMap,
5759
),
5860
buildContext = buildContext,
5961
plugins = plugins
60-
) {
62+
), DaggerComponentOwner {
6163
interface Callback : Plugin {
6264
fun onOpenBugReport()
6365
}
6466

6567
@Parcelize
6668
object NavTarget : Parcelable
6769

68-
interface LifecycleCallback : NodeLifecycleCallback {
69-
fun onFlowCreated(identifier: String, client: MatrixClient)
70-
71-
fun onFlowReleased(identifier: String, client: MatrixClient)
72-
}
73-
7470
data class Inputs(
7571
val matrixClient: MatrixClient
7672
) : NodeInputs
7773

7874
private val inputs: Inputs = inputs()
75+
override val daggerComponent = sessionComponentFactory.create(inputs.matrixClient)
7976

8077
override fun onBuilt() {
8178
super.onBuilt()
8279
lifecycle.subscribe(
8380
onCreate = {
84-
plugins<LifecycleCallback>().forEach { it.onFlowCreated(id, inputs.matrixClient) }
8581
val imageLoaderFactory = bindings<MatrixUIBindings>().loggedInImageLoaderFactory()
8682
Coil.setImageLoader(imageLoaderFactory)
8783
},
88-
onDestroy = {
89-
plugins<LifecycleCallback>().forEach { it.onFlowReleased(id, inputs.matrixClient) }
90-
}
9184
)
9285
}
9386

@@ -97,13 +90,10 @@ class LoggedInAppScopeFlowNode @AssistedInject constructor(
9790
plugins<Callback>().forEach { it.onOpenBugReport() }
9891
}
9992
}
100-
val nodeLifecycleCallbacks = plugins<NodeLifecycleCallback>()
101-
return createNode<LoggedInFlowNode>(buildContext, nodeLifecycleCallbacks + callback)
93+
return createNode<LoggedInFlowNode>(buildContext, listOf(callback))
10294
}
10395

104-
suspend fun attachSession(): LoggedInFlowNode {
105-
return waitForChildAttached { _ -> true }
106-
}
96+
suspend fun attachSession(): LoggedInFlowNode = waitForChildAttached()
10797

10898
@Composable
10999
override fun View(modifier: Modifier) {

appnav/src/main/kotlin/io/element/android/appnav/LoggedInFlowNode.kt

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -227,14 +227,13 @@ class LoggedInFlowNode @AssistedInject constructor(
227227
.build()
228228
}
229229
is NavTarget.Room -> {
230-
val nodeLifecycleCallbacks = plugins<NodeLifecycleCallback>()
231230
val callback = object : RoomLoadedFlowNode.Callback {
232231
override fun onForwardedToSingleRoom(roomId: RoomId) {
233232
coroutineScope.launch { attachRoom(roomId) }
234233
}
235234
}
236235
val inputs = RoomFlowNode.Inputs(roomId = navTarget.roomId, initialElement = navTarget.initialElement)
237-
createNode<RoomFlowNode>(buildContext, plugins = listOf(inputs, callback) + nodeLifecycleCallbacks)
236+
createNode<RoomFlowNode>(buildContext, plugins = listOf(inputs, callback))
238237
}
239238
NavTarget.Settings -> {
240239
val callback = object : PreferencesEntryPoint.Callback {

appnav/src/main/kotlin/io/element/android/appnav/RootFlowNode.kt

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,6 @@ import com.bumble.appyx.core.modality.BuildContext
2929
import com.bumble.appyx.core.node.Node
3030
import com.bumble.appyx.core.node.node
3131
import com.bumble.appyx.core.plugin.Plugin
32-
import com.bumble.appyx.core.plugin.plugins
3332
import com.bumble.appyx.core.state.MutableSavedStateMap
3433
import com.bumble.appyx.navmodel.backstack.BackStack
3534
import com.bumble.appyx.navmodel.backstack.operation.pop
@@ -196,8 +195,7 @@ class RootFlowNode @AssistedInject constructor(
196195
backstack.push(NavTarget.BugReport)
197196
}
198197
}
199-
val nodeLifecycleCallbacks = plugins<NodeLifecycleCallback>()
200-
createNode<LoggedInAppScopeFlowNode>(buildContext, plugins = listOf(inputs, callback) + nodeLifecycleCallbacks)
198+
createNode<LoggedInAppScopeFlowNode>(buildContext, plugins = listOf(inputs, callback))
201199
}
202200
NavTarget.NotLoggedInFlow -> createNode<NotLoggedInFlowNode>(buildContext)
203201
NavTarget.SplashScreen -> splashNode(buildContext)

appnav/src/main/kotlin/io/element/android/appnav/NodeLifecycleCallback.kt renamed to appnav/src/main/kotlin/io/element/android/appnav/di/RoomComponentFactory.kt

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -14,8 +14,10 @@
1414
* limitations under the License.
1515
*/
1616

17-
package io.element.android.appnav
17+
package io.element.android.appnav.di
1818

19-
import com.bumble.appyx.core.plugin.Plugin
19+
import io.element.android.libraries.matrix.api.room.MatrixRoom
2020

21-
interface NodeLifecycleCallback : Plugin
21+
interface RoomComponentFactory {
22+
fun create(room: MatrixRoom): Any
23+
}

0 commit comments

Comments
 (0)