Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

update: dependencies graphs in Multiplatform #4297

Open
wants to merge 6 commits into
base: master
Choose a base branch
from

Conversation

zamulla
Copy link
Contributor

@zamulla zamulla commented Jun 17, 2024

No description provided.

@zamulla zamulla requested a review from antohaby June 17, 2024 15:34
### Aligning versions of common dependencies across source sets

Common dependencies need to be aligned across source sets to make sure that common code is always compiled against
the version of a library that satisfies all source sets.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'd say "common code is always compiled against the same version of a library when it compiles for different targets".

version of a library that satisfies all source set

It can have different meanings, IMO.

So the invariant is that common code should be compiled against "the same" version. But what exact version is to be defined by the gradle dependency resolution rules.

`androidMain` source set. Your project explicitly declares the `kotlinx-coroutines-core:1.7.3` dependency for the `commonMain`
source set, but the Compose Navigation library with the version 2.7.7 requires Kotlin coroutines 1.8.0 or newer.

Resolving this, Gradle applies `kotlinx-coroutines-core:1.8.0` to the `commonMain` source set. But to make the common code

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Gradle applies ... to the commonMain source set.

It is unclear why Gradle does that? i mean reader can struggle to infer that information from the sentence above.
So maybe it worth adding some explanation. Something like that:

Since commonMain source set is compiled together with androidMain, it means that commonMain should see the same version of kotlinx-coroutines-core as androidMain. Despite the fact that its direct dependency was just kotlinx-coroutines-core:1.7.3.

source set, but the Compose Navigation library with the version 2.7.7 requires Kotlin coroutines 1.8.0 or newer.

Resolving this, Gradle applies `kotlinx-coroutines-core:1.8.0` to the `commonMain` source set. But to make the common code
compile consistently across targets, the iOS source sets also need to be constrained to the same dependency version.

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not an english guru, just asking.

what's the difference between across targets vs across all targets in this context?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"targets" refers to an undetermined set of targets, and "all targets" — to a determined set (not necessarily defined explicitly).

To me "all targets" seems to implicitly refer to all KMP-supported targets, not all project targets. But looking at this fragment again, I do think it's better to clarify, for example, "across all configured targets."

@zamulla zamulla requested a review from antohaby June 20, 2024 14:39
@zamulla zamulla marked this pull request as ready for review June 27, 2024 15:44
@zamulla zamulla requested a review from a team as a code owner June 27, 2024 15:44
@@ -168,6 +168,36 @@ There are three important concepts in dependency resolution:

![Error on JVM-specific API in common code](dependency-resolution-error.png){width=700}

### Aligning versions of common dependencies across source sets

In Kotlin Multiplatform projects, the common source set is compiled several times: to produce a klib, and as a part of each
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
In Kotlin Multiplatform projects, the common source set is compiled several times: to produce a klib, and as a part of each
In Kotlin Multiplatform projects, the common source set is compiled several times to produce a klib and as a part of each

### Aligning versions of common dependencies across source sets

In Kotlin Multiplatform projects, the common source set is compiled several times: to produce a klib, and as a part of each
configured [compilation](multiplatform-configure-compilations.md). To produces consistent binaries, common code
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
configured [compilation](multiplatform-configure-compilations.md). To produces consistent binaries, common code
configured [compilation](multiplatform-configure-compilations.md). To produce consistent binaries, common code

In Kotlin Multiplatform projects, the common source set is compiled several times: to produce a klib, and as a part of each
configured [compilation](multiplatform-configure-compilations.md). To produces consistent binaries, common code
should be compiled against the same versions of multiplatform dependencies each time.
Kotlin Gradle plugin helps to align these dependencies, making sure that the effective dependency version
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Kotlin Gradle plugin helps to align these dependencies, making sure that the effective dependency version
The Kotlin Gradle plugin helps align these dependencies, ensuring the effective dependency version

`androidMain` source set. Your project explicitly declares the `kotlinx-coroutines-core:1.7.3` dependency for the `commonMain`
source set, but the Compose Navigation library with the version 2.7.7 requires Kotlin coroutines 1.8.0 or newer.

Since `commonMain` and `androidMain` are compiled together, Kotlin Gradle plugin chooses between the two version of the
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
Since `commonMain` and `androidMain` are compiled together, Kotlin Gradle plugin chooses between the two version of the
Since `commonMain` and `androidMain` are compiled together, the Kotlin Gradle plugin chooses between the two versions of the

So you can test your project with newer library versions without affecting your main code.

For example, you have the Kotlin coroutines 1.7.3 dependency in your main source set group, propagated to every source set
of the group. But in the `iosTest` source set you decide to up the version to 1.8.0 to test out the new library release.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
of the group. But in the `iosTest` source set you decide to up the version to 1.8.0 to test out the new library release.
of the group. However, in the `iosTest` source set, you decide to upgrade the version to 1.8.0 to test out the new library release.


Since `commonMain` and `androidMain` are compiled together, Kotlin Gradle plugin chooses between the two version of the
coroutines library and applies `kotlinx-coroutines-core:1.8.0` to the `commonMain` source set. But to make the common code
compile consistently across all configured targets, the iOS source sets also need to be constrained to the same dependency version.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Suggested change
compile consistently across all configured targets, the iOS source sets also need to be constrained to the same dependency version.
compile consistently across all configured targets, iOS source sets also need to be constrained to the same dependency version.


![Alignment of dependencies in a group of source sets](multiplatform-source-set-dependency-alignment.svg){width=700}

Dependencies are aligned across source sets of each group: the `*Main` source sets and the [`*Test` source sets](multiplatform-discover-project.md#integration-with-tests).
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We haven't previously used the term 'group of source sets', and I found it a bit confusing, because 'the group of test source sets' sounds like a part of all test source sets

I'd recommend to write it explicitly each time:

The Gradle configuration for *Test source sets includes all dependencies of *Main source sets but not vice versa.

For example, you have the Kotlin coroutines 1.7.3 dependency in your *Main source sets, propagated to every project source set.

@@ -168,6 +168,36 @@ There are three important concepts in dependency resolution:

![Error on JVM-specific API in common code](dependency-resolution-error.png){width=700}

### Aligning versions of common dependencies across source sets
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm not sure if the new section fits under Dependencies and dependsOn. The existing section describes kinds of dependencies and that's it. so the new one should be a separate section on the second level or be under the Compilations (or closer to it), since it's more concerned with having consistent binaries after the compilation and less with how dependencies are set up

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
3 participants