##// END OF EJS Templates
Rework variant artifacts materialization model...
Rework variant artifacts materialization model Refactor VariantArtifactsPlugin around a live outgoing artifacts context and split artifact publication into explicit internal services: outgoing variant registry, assembly binding, materialization policy hooks, primary-slot convention, and slot assembly handling. Introduce variant artifact slots as identity-first public API and expose materialized assembly handles through ArtifactAssemblies. Add replayable configuration hooks for outgoing configurations, outgoing slots, outgoing variants, and registered assemblies. Create consumable outgoing configurations per variant, bind the primary slot to the root outgoing artifact set, and publish non-primary slots as Gradle outgoing configuration variants. Add deterministic injective task names for slot assembly tasks, use Sync for directory assembly, and configure the default assembly output location under build/variant-assemblies. Make primary-slot selection finalize-on-read and provide a single-slot convention that fails when no unique default can be inferred. Mark artifact internal implementation package as non-public API.

File last commit:

r44:ae7ec3f08ac3 default
r51:9db7822cd26c default
Show More
variant_sources_precedence.md
337 lines | 8.1 KiB | text/x-minidsrc | MarkdownLexer
/ variant_sources_precedence.md
cin
WIP almost stable variants model, working on variantSources
r41 # `variantSources`: selectors and precedence
`variantSources` configures source-set materialization over the compile-unit space.
A compile unit is defined as:
- `(variant, layer)`
This means:
- `variant` defines compilation semantics
- `layer` defines compilation partitioning
The `variantSources` DSL does not introduce a separate source model.
Instead, it provides configuration selectors over the existing compile-unit space.
## Selectors
Three selectors are available:
- `variant(...)`
- `layer(...)`
- `unit(...)`
They all target the same set of compile units, but at different levels of specificity.
### `variant(...)`
`variant(...)` applies configuration to all compile units that belong to the given variant.
Example:
```groovy
variantSources {
variant("browser") {
declareOutputs("js", "dts")
}
}
```
This affects all compile units of `browser`, for example:
- `(browser, main)`
- `(browser, rjs)`
- `(browser, test)`
Use this selector for variant-wide conventions.
---
### `layer(...)`
`layer(...)` applies configuration to all compile units that use the given layer.
Example:
```groovy
variantSources {
layer("main") {
set("ts") {
srcDir("src/main/ts")
}
}
}
```
This affects all compile units with layer `main`, for example:
- `(browser, main)`
- `(nodejs, main)`
- `(electron, main)`
Use this selector for cross-variant layer conventions.
---
### `unit(...)`
`unit(...)` applies configuration to one exact compile unit.
Example:
```groovy
variantSources {
unit("browser", "main") {
set("resources") {
srcDir("src/browserMain/resources")
}
}
}
```
This affects only:
- `(browser, main)`
Use this selector for the most specific adjustments.
---
## Precedence
For each compile unit, source-set configuration is applied in the following order:
```text
variant < layer < unit
```
This means:
1. `variant(...)` actions are applied first
2. `layer(...)` actions are applied next
3. `unit(...)` actions are applied last
Each next level is allowed to refine or override the previous one.
### Within the same level
Within the same selector level, actions are applied in registration order.
For example, if two plugins both configure `layer("main")`, their actions are applied in the same order in which they were registered.
cin
Add compile-unit naming policy and late-configuration enforcement to VariantSourcesPlugin
r43 ### Scope of this guarantee
This precedence describes the normal materialization order used by the source-set
materializer.
It is stable for source sets that are configured before they are materialized.
If a selector rule is added after a target source set has already been
materialized, the behavior depends on the selected late-configuration policy.
- in `fail` mode, such late configuration is rejected
- in `warn` and `allow` modes, the late action is applied as an imperative
follow-up step
- in `warn` and `allow` modes, selector precedence is not reconstructed
retroactively for already materialized targets
---
## Late Configuration Policy
`variantSources` exposes a policy switch for selector rules that target already
materialized source sets:
```groovy
variantSources {
lateConfigurationPolicy {
failOnLateConfiguration()
}
}
```
Available modes:
- `failOnLateConfiguration()` rejects such rules
- `warnOnLateConfiguration()` allows them and emits a warning
- `allowLateConfiguration()` allows them silently
Policy rules:
- the policy must be chosen before the first selector rule is added
- selector rules here mean `variant(...)`, `layer(...)`, and `unit(...)`
- once chosen, the policy cannot be changed later
- the policy is single-valued; it is not intended to be switched during further
configuration
cin
more documentation
r44 - the enforcement point is the first selector registration itself; finalization
of `variants` alone does not freeze this policy
cin
Add compile-unit naming policy and late-configuration enforcement to VariantSourcesPlugin
r43
Operationally:
- `fail` preserves the strict precedence contract by rejecting late mutation of
already materialized targets
- `warn` and `allow` keep compatibility with imperative late mutation
- in `warn` and `allow`, already materialized targets observe the late action in
actual registration order, not in reconstructed `variant < layer < unit`
order
cin
WIP almost stable variants model, working on variantSources
r41 ---
cin
more documentation
r44 ## Compile-Unit Naming Policy
`variantSources` also exposes a policy for projecting compile units to symbolic
source-set names:
```groovy
variantSources {
namingPolicy {
failOnNameCollision()
}
}
```
Base projected name:
- `sourceSetName = variantName + capitalize(layerName)`
Example:
- `(browser, main)` -> `browserMain`
- `(browser, rjs)` -> `browserRjs`
Available modes:
- `failOnNameCollision()` rejects finalized compile-unit models that project the
same base name for different compile units
- `resolveNameCollision()` resolves such collisions deterministically
### `resolveNameCollision()` semantics
Conflicting compile units are ordered canonically by:
```text
(variant.name, layer.name)
```
Name assignment in a conflicting group is:
- the first compile unit keeps the base name
- the second gets suffix `2`
- the third gets suffix `3`
- and so on
Example:
- `(foo, variantBar)` and `(fooVariant, bar)` both project to `fooVariantBar`
- after canonical ordering:
- `(foo, variantBar)` -> `fooVariantBar`
- `(fooVariant, bar)` -> `fooVariantBar2`
### Fixation Point
Naming policy is fixed when the finalized `VariantSourcesContext` is created.
Operationally this means:
- policy selection must happen before `variantSources.whenFinalized(...)`
becomes observable
- compile-unit names are projected and validated before queued
`whenFinalized(...)` callbacks are replayed
- changing naming policy from inside a `whenFinalized(...)` callback is too late
---
cin
WIP almost stable variants model, working on variantSources
r41 ## Example
```groovy
variantSources {
variant("browser") {
declareOutputs("js", "dts")
}
layer("main") {
set("ts") {
srcDir("src/main/ts")
}
}
unit("browser", "main") {
set("resources") {
srcDir("src/browserMain/resources")
}
}
}
```
For compile unit `(browser, main)` the effective configuration is built in this order:
1. `variant("browser")`
2. `layer("main")`
3. `unit("browser", "main")`
For compile unit `(browser, rjs)` the effective configuration is built in this order:
1. `variant("browser")`
2. `layer("rjs")` if present
3. `unit("browser", "rjs")` if present
For compile unit `(nodejs, main)` the effective configuration is built in this order:
1. `variant("nodejs")` if present
2. `layer("main")`
3. `unit("nodejs", "main")` if present
---
## Model boundary
These selectors do not define compile units.
Compile units are derived from finalized `variants`.
`variantSources` only configures how source sets are materialized for those units.
This means:
- `variants` is the source of truth for compile-unit existence
- `variantSources` is the source of truth for compile-unit source-set configuration
---
## Operational semantics
The `variantSources` API is exposed through a finalized context.
Conceptually, configuration is registered against finalized model objects, while DSL sugar may still use names for convenience.
cin
Add compile-unit naming policy and late-configuration enforcement to VariantSourcesPlugin
r43 Internally, selector-based configuration is accumulated and later applied by the
source-set materializer when a `GenericSourceSet` is created for a compile unit.
cin
WIP almost stable variants model, working on variantSources
r41
This guarantees that:
cin
Add compile-unit naming policy and late-configuration enforcement to VariantSourcesPlugin
r43 - selector precedence is stable before materialization
cin
WIP almost stable variants model, working on variantSources
r41 - registration order is preserved
cin
Add compile-unit naming policy and late-configuration enforcement to VariantSourcesPlugin
r43 - configuration of already materialized targets is governed by the selected
late-configuration policy
cin
WIP almost stable variants model, working on variantSources
r41 - adapters do not need to depend on raw Gradle lifecycle timing
---
## Summary
- compile unit space is `(variant, layer)`
- `variant(...)`, `layer(...)`, and `unit(...)` are selectors over that space
- precedence is:
```text
variant < layer < unit
```
- registration order is preserved within the same selector level
cin
Add compile-unit naming policy and late-configuration enforcement to VariantSourcesPlugin
r43 - already materialized targets are handled by `lateConfigurationPolicy(...)`
- the late-configuration policy must be selected before the first selector rule
and cannot be changed later
cin
more documentation
r44 - compile-unit naming is governed by `namingPolicy(...)`
- by default, name collisions fail fast during finalized context creation
cin
WIP almost stable variants model, working on variantSources
r41 - `variants` defines what exists
- `variantSources` defines how those compile units are materialized as source sets