From 71e8088260bf5e87fa7ae0d3e1fc9e03728f09a7 Mon Sep 17 00:00:00 2001 From: Goooler Date: Wed, 26 Aug 2026 21:03:31 +0800 Subject: [PATCH 1/4] Introduce mkdocs-callouts and use GitHub-style alerts https://github.com/sondregronas/mkdocs-callouts --- .github/workflows/deploy.yml | 2 +- .github/workflows/links.yml | 2 +- CHANGELOG.md | 84 ++++++++++------------- CONTRIBUTING.md | 2 +- README.md | 2 +- docs/README.md | 18 ++--- docs/configuration/README.md | 7 +- docs/configuration/dependencies/README.md | 36 +++++----- docs/configuration/merging/README.md | 68 +++++++++--------- docs/configuration/minimizing/README.md | 55 +++++++-------- docs/configuration/relocation/README.md | 37 +++++----- docs/getting-started/README.md | 7 +- docs/multi-project/README.md | 7 +- mkdocs.yml | 3 +- 14 files changed, 157 insertions(+), 173 deletions(-) diff --git a/.github/workflows/deploy.yml b/.github/workflows/deploy.yml index f8926a89f..8cbd553a7 100644 --- a/.github/workflows/deploy.yml +++ b/.github/workflows/deploy.yml @@ -23,7 +23,7 @@ jobs: - name: Build Site run: | # Don't cache it to track updates. - pip install mkdocs-material mdx_truly_sane_lists + pip install mkdocs-material mdx_truly_sane_lists mkdocs-callouts mkdocs build - uses: actions/upload-pages-artifact@v5 with: diff --git a/.github/workflows/links.yml b/.github/workflows/links.yml index 1a464fa88..6b93d7aeb 100644 --- a/.github/workflows/links.yml +++ b/.github/workflows/links.yml @@ -35,7 +35,7 @@ jobs: - name: Mkdocs build validation run: | # Don't cache it to track updates. - pip install mkdocs-material mdx_truly_sane_lists + pip install mkdocs-material mdx_truly_sane_lists mkdocs-callouts mkdocs build --strict - uses: umbrelladocs/action-linkspector@v1 with: diff --git a/CHANGELOG.md b/CHANGELOG.md index 8d9090831..76907ec7c 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -85,22 +85,21 @@ ## [9.5.0](https://github.com/GradleUp/shadow/releases/tag/9.5.0) - 2026-07-06 -!!! note - - With the introduction of `DuplicatesStrategy` checking for transformers, you may see warnings like: - - ``` - 'META-INF/...kotlin_module' is matched by com.github.jengelman.gradle.plugins.shadow.transformers.KotlinModuleMetadataTransformer but its DuplicatesStrategy is EXCLUDE — duplicates may be silently dropped before the transformer processes them. - ``` - - If you do not need Kotlin module metadata remapping, you can disable it: - - ``` - tasks.shadowJar { - @Suppress("DEPRECATION") // This flag will be disabled and removed in the next major version of Shadow. - enableKotlinModuleRemapping = false - } - ``` +> [!NOTE] +> With the introduction of `DuplicatesStrategy` checking for transformers, you may see warnings like: +> +> ``` +> 'META-INF/...kotlin_module' is matched by com.github.jengelman.gradle.plugins.shadow.transformers.KotlinModuleMetadataTransformer but its DuplicatesStrategy is EXCLUDE — duplicates may be silently dropped before the transformer processes them. +> ``` +> +> If you do not need Kotlin module metadata remapping, you can disable it: +> +> ``` +> tasks.shadowJar { +> @Suppress("DEPRECATION") // This flag will be disabled and removed in the next major version of Shadow. +> enableKotlinModuleRemapping = false +> } +> ``` ### Added @@ -342,14 +341,12 @@ ## [9.0.1](https://github.com/GradleUp/shadow/releases/tag/9.0.1) - 2025-08-09 -!!! note - - If you are upgrading from 8.x versions, please read 9.0.0 release notes first. - -!!! tip +> [!NOTE] +> If you are upgrading from 8.x versions, please read 9.0.0 release notes first. - You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). - If there are any things missing in the changelog or the doc site, please report them to us. +> [!TIP] +> You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). +> If there are any things missing in the changelog or the doc site, please report them to us. ### Changed @@ -367,23 +364,20 @@ ## [9.0.0](https://github.com/GradleUp/shadow/releases/tag/9.0.0) - 2025-08-07 -!!! warning +> [!WARNING] +> This release is a major update from the 8.x series. The plugin has been fully rewritten in Kotlin, bringing +> significant improvements to maintainability, performance, and future extensibility. It introduces many new features, +> enhancements, and bug fixes, and includes several breaking changes. Please review the changelog carefully and consult +> the [new doc site](https://gradleup.com/shadow/) before upgrading. +> +> *If you really don't want to upgrade, you can still use the 8.3.x, which is also Gradle 9 compatible. But no additional features or crucial bug fixes will be included in the 8.x line.* - This release is a major update from the 8.x series. The plugin has been fully rewritten in Kotlin, bringing - significant improvements to maintainability, performance, and future extensibility. It introduces many new features, - enhancements, and bug fixes, and includes several breaking changes. Please review the changelog carefully and consult - the [new doc site](https://gradleup.com/shadow/) before upgrading. +> [!TIP] +> You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). +> If there are any things missing in the changelog or the doc site, please report them to us. - *If you really don't want to upgrade, you can still use the 8.3.x, which is also Gradle 9 compatible. But no additional features or crucial bug fixes will be included in the 8.x line.* - -!!! tip - - You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). - If there are any things missing in the changelog or the doc site, please report them to us. - -!!! note - - Release notes for 9.0.0 beta and rc versions are available on [GitHub Releases](https://github.com/GradleUp/shadow/releases). +> [!NOTE] +> Release notes for 9.0.0 beta and rc versions are available on [GitHub Releases](https://github.com/GradleUp/shadow/releases). ### Added @@ -567,10 +561,9 @@ See more details about the fixed `DuplicatesStrategy` behaviors at [Handling Dup ## [8.3.11](https://github.com/GradleUp/shadow/releases/tag/8.3.11) - 2026-05-28 -!!! warning - - Only Gradle 9 support is being backported to this version. No additional features or crucial bug fixes will be - included in the 8.x line. Please migrate to Shadow 9 as soon as possible. +> [!WARNING] +> Only Gradle 9 support is being backported to this version. No additional features or crucial bug fixes will be +> included in the 8.x line. Please migrate to Shadow 9 as soon as possible. ### Changed @@ -700,10 +693,9 @@ See more details about the fixed `DuplicatesStrategy` behaviors at [Handling Dup ## [8.1.1](https://github.com/GradleUp/shadow/releases/tag/8.1.1) - 2023-03-20 -!!! note - - As of this version, the GitHub repository has migrated to the `main` branch as the default branch for - releases. +> [!NOTE] +> As of this version, the GitHub repository has migrated to the `main` branch as the default branch for +> releases. ### What's Changed diff --git a/CONTRIBUTING.md b/CONTRIBUTING.md index 35f5ccf98..671a5a491 100644 --- a/CONTRIBUTING.md +++ b/CONTRIBUTING.md @@ -60,7 +60,7 @@ Shadow uses [Android Lint](https://developer.android.com/studio/write/lint) to c Shadow's user guide is built using [MkDocs Material](https://squidfunk.github.io/mkdocs-material/). You can build and preview the documentation website locally: -- **Install MkDocs dependencies**: `pip install mkdocs-material mdx_truly_sane_lists` +- **Install MkDocs dependencies**: `pip install mkdocs-material mdx_truly_sane_lists mkdocs-callouts` - **Preview documentation locally**: `mkdocs serve` (then navigate to `http://127.0.0.1:8000/`) - **Build the static site**: `mkdocs build` diff --git a/README.md b/README.md index 4262ac816..f8d5e351d 100644 --- a/README.md +++ b/README.md @@ -8,7 +8,7 @@ with R8/ProGuard. The Gradle counterpart to Maven Shade Plugin. [![CI](https://github.com/GradleUp/shadow/actions/workflows/build.yml/badge.svg?branch=main&event=push)](https://github.com/GradleUp/shadow/actions/workflows/build.yml?query=branch:main+event:push) [![License](https://img.shields.io/github/license/GradleUp/shadow.svg)](LICENSE) -> [!NOTE]\ +> [!NOTE] > Previously this plugin was developed by [@johnrengelman](https://github.com/johnrengelman) and published under the > ID [`com.github.johnrengelman.shadow`][johnrengelman's] before maintenance was transferred to the > [GradleUp organization](https://github.com/GradleUp) to ensure future development, see diff --git a/docs/README.md b/docs/README.md index 67e5fdffe..8e43a40a0 100644 --- a/docs/README.md +++ b/docs/README.md @@ -7,15 +7,15 @@ A Gradle plugin for creating fat/uber JARs, transforming files, relocating packages, and optimizing applications with R8/ProGuard. The Gradle counterpart to Maven Shade Plugin. -!!! warning "Plugin ID Change" - - Previously this plugin was developed by [@johnrengelman][johnrengelman] and published under the ID - [`com.github.johnrengelman.shadow`][johnrengelman's] before maintenance was transferred to the - [GradleUp organization][GradleUp] to ensure future development, see [#908]. - - If you are still using the old plugin ID in your build script, we recommend to switch to the new plugin ID - [`com.gradleup.shadow`][gradleup's] and update to the latest version to receive all the latest bug fixes and - improvements. +> [!WARNING] Plugin ID Change +> +> Previously this plugin was developed by [@johnrengelman][johnrengelman] and published under the ID +> [`com.github.johnrengelman.shadow`][johnrengelman's] before maintenance was transferred to the +> [GradleUp organization][GradleUp] to ensure future development, see [#908]. +> +> If you are still using the old plugin ID in your build script, we recommend to switch to the new plugin ID +> [`com.gradleup.shadow`][gradleup's] and update to the latest version to receive all the latest bug fixes and +> improvements. | Shadow Version | Min Gradle Version | Min Java Version | Plugin ID | |----------------|--------------------|------------------|------------------------------------------------------| diff --git a/docs/configuration/README.md b/docs/configuration/README.md index 8f235adb3..07f3475eb 100644 --- a/docs/configuration/README.md +++ b/docs/configuration/README.md @@ -134,10 +134,9 @@ Inspecting the `META-INF/MANIFEST.MF` entry in the JAR file will reveal the foll Class-Path: junit-3.8.2.jar ``` -!!! important - - When deploying a shadowed JAR as an execution JAR, any non-bundled runtime dependencies **must** be deployed in the - location specified in the `Class-Path` entry in the manifest. +> [!IMPORTANT] +> When deploying a shadowed JAR as an execution JAR, any non-bundled runtime dependencies **must** be deployed in the +> location specified in the `Class-Path` entry in the manifest. ## Configuring the JAR Manifest diff --git a/docs/configuration/dependencies/README.md b/docs/configuration/dependencies/README.md index 32736197f..168e3c022 100644 --- a/docs/configuration/dependencies/README.md +++ b/docs/configuration/dependencies/README.md @@ -25,15 +25,15 @@ The above code sample would configure the [`ShadowJar`][ShadowJar] task to merge `compileClasspath` configuration. This means any dependency declared in the `runtimeOnly` configuration would be **not** be included in the final JAR. -!!! warning "Required Configuration" - - Note the literal use of [`project.configurations`][Project.configurations] when setting the - [`configurations`][ShadowJar.configurations] attribute of a [`ShadowJar`][ShadowJar] task. - - This is **required**. It may be tempting to specify `configurations = [configurations.compileClasspath]` but - this will not have the intended effect, as `configurations.compile` will try to delegate to the - [`configurations`][ShadowJar.configurations] property of the [`ShadowJar`][ShadowJar] task instead of the - `project`. +> [!WARNING] Required Configuration +> +> Note the literal use of [`project.configurations`][Project.configurations] when setting the +> [`configurations`][ShadowJar.configurations] attribute of a [`ShadowJar`][ShadowJar] task. +> +> This is **required**. It may be tempting to specify `configurations = [configurations.compileClasspath]` but +> this will not have the intended effect, as `configurations.compile` will try to delegate to the +> [`configurations`][ShadowJar.configurations] property of the [`ShadowJar`][ShadowJar] task instead of the +> `project`. ## Embedding Local Jar Files into Your Shadowed JAR @@ -205,11 +205,10 @@ Individual dependencies can be filtered from the final JAR by using the `depende [`ShadowJar`][ShadowJar] task. Dependency filtering does **not** apply to transitive dependencies. That is, excluding a dependency does not exclude any of its dependencies from the final JAR. -!!! note - - Excluding a dependency via `dependencies { exclude(...) }` removes it entirely from the shadow JAR. If you instead - want the dependency to be bundled into the shadow JAR but prevented from having its unused classes stripped during - minimization, see [`minimize { exclude(...) }`][minimizing]. +> [!NOTE] +> Excluding a dependency via `dependencies { exclude(...) }` removes it entirely from the shadow JAR. If you instead +> want the dependency to be bundled into the shadow JAR but prevented from having its unused classes stripped during +> minimization, see [`minimize { exclude(...) }`][minimizing]. The `dependency` blocks provides a number of methods for resolving dependencies using the notations familiar from Gradle's [`project.configurations`][Project.configurations] block. @@ -270,11 +269,10 @@ Gradle's [`project.configurations`][Project.configurations] block. } ``` -!!! note - - While not being able to filter entire transitive dependency graphs might seem like an oversight, it is necessary - because it would not be possible to intelligently determine the build author's intended results when there is a - common dependency between two 1st level dependencies when one is excluded and the other is not. +> [!NOTE] +> While not being able to filter entire transitive dependency graphs might seem like an oversight, it is necessary +> because it would not be possible to intelligently determine the build author's intended results when there is a +> common dependency between two 1st level dependencies when one is excluded and the other is not. ### Using Regex Patterns to Filter Dependencies diff --git a/docs/configuration/merging/README.md b/docs/configuration/merging/README.md index 6d56e7ef8..97b8e2468 100644 --- a/docs/configuration/merging/README.md +++ b/docs/configuration/merging/README.md @@ -6,16 +6,16 @@ Maven Shade implementation. A [`ResourceTransformer`][ResourceTransformer] is in being written to the final output JAR. This allows a [`ResourceTransformer`][ResourceTransformer] to determine if it should process a particular entry and apply any modifications before writing the stream to the output. -!!! important "Guaranteed Processing Order" - - [`ResourceTransformer`][ResourceTransformer] follows a guaranteed processing order: - - 1. **Project files first**: All files in projects are processed before any dependency files. - 2. **Dependency files second**: Files from configurations (runtime dependencies) or added via - [`ShadowJar.from`][ShadowJar.from] are processed after project files. - - This ordering is crucial when merging configuration files where you want to preserve project-specific values while - merging in additional data from dependencies. +> [!IMPORTANT] Guaranteed Processing Order +> +> [`ResourceTransformer`][ResourceTransformer] follows a guaranteed processing order: +> +> 1. **Project files first**: All files in projects are processed before any dependency files. +> 2. **Dependency files second**: Files from configurations (runtime dependencies) or added via +> [`ShadowJar.from`][ShadowJar.from] are processed after project files. +> +> This ordering is crucial when merging configuration files where you want to preserve project-specific values while +> merging in additional data from dependencies. ## Handling Duplicates Strategy @@ -59,13 +59,13 @@ Different strategies will lead to different results for `foo/bar` files in the J exception like `Entry .* is a duplicate but no duplicate handling strategy has been set`. - `WARN`: **Warn** about duplicates in the build log; this behaves exactly as `INCLUDE` otherwise. -!!! note "Precedence of DuplicatesStrategy" - - The `duplicatesStrategy` evaluation takes precedence over transforming and relocating. - Because `ShadowJar` is a subclass of Gradle's `AbstractCopyTask`, duplicate filtering configured via - `duplicatesStrategy` is performed at Gradle's `CopySpec` processing layer **before** entries are passed to Shadow's - internal [`ResourceTransformer`][ResourceTransformer] engine. - See the [ShadowJar Execution Flow][shadowjar-execution-flow] for the complete lifecycle diagram. +> [!NOTE] Precedence of DuplicatesStrategy +> +> The `duplicatesStrategy` evaluation takes precedence over transforming and relocating. +> Because `ShadowJar` is a subclass of Gradle's `AbstractCopyTask`, duplicate filtering configured via +> `duplicatesStrategy` is performed at Gradle's `CopySpec` processing layer **before** entries are passed to Shadow's +> internal [`ResourceTransformer`][ResourceTransformer] engine. +> See the [ShadowJar Execution Flow][shadowjar-execution-flow] for the complete lifecycle diagram. If you mix the usages of `duplicatesStrategy = DuplicatesStrategy.EXCLUDE` and [`ResourceTransformer`][ResourceTransformer] like below: @@ -120,10 +120,10 @@ Alternatively, you can follow these steps: [`filesMatching`][Jar.filesMatching], [`filesNotMatching`][Jar.filesNotMatching], or [`eachFile`][Jar.eachFile] functions to set their `duplicatesStrategy` to `INCLUDE` or `WARN`. -!!! warning "Build Cache Impact" - - Functions inherited from [`CopySpec`][CopySpec], such as [`filesMatching`][Jar.filesMatching], - [`filesNotMatching`][Jar.filesNotMatching], [`eachFile`][Jar.eachFile], or others, disable the output caching. +> [!WARNING] Build Cache Impact +> +> Functions inherited from [`CopySpec`][CopySpec], such as [`filesMatching`][Jar.filesMatching], +> [`filesNotMatching`][Jar.filesNotMatching], [`eachFile`][Jar.eachFile], or others, disable the output caching. Optional steps: @@ -358,14 +358,14 @@ the [`ServiceFileTransformer`][ServiceFileTransformer]: } ``` -!!! note "Groovy Extension Modules" - - Groovy Extension Module descriptor files (located at - `META-INF/services/org.codehaus.groovy.runtime.ExtensionModule`) are ignored by the - [`ServiceFileTransformer`][ServiceFileTransformer]. - This is due to these files having a different syntax than standard service descriptor files. - Use the [`mergeGroovyExtensionModules()`][mergeGroovyExtensionModules] method to merge these files if your - dependencies contain them. +> [!NOTE] Groovy Extension Modules +> +> Groovy Extension Module descriptor files (located at +> `META-INF/services/org.codehaus.groovy.runtime.ExtensionModule`) are ignored by the +> [`ServiceFileTransformer`][ServiceFileTransformer]. +> This is due to these files having a different syntax than standard service descriptor files. +> Use the [`mergeGroovyExtensionModules()`][mergeGroovyExtensionModules] method to merge these files if your +> dependencies contain them. ### Configuring the Location of Service Descriptor Files @@ -877,11 +877,11 @@ If certain duplicate resources at the same path legitimately have different cont or `pom.xml` files from different dependency versions), you can exclude those paths from being checked using `exclude(...)`: -!!! warning "Do Not Combine with PreserveFirstFoundResourceTransformer" - - Do not combine [`PreserveFirstFoundResourceTransformer`][PreserveFirstFoundResourceTransformer] with - [`DeduplicatingResourceTransformer`][DeduplicatingResourceTransformer], as they handle duplicates differently and - combining them leads to redundant or unexpected behavior. +> [!WARNING] Do Not Combine with PreserveFirstFoundResourceTransformer +> +> Do not combine [`PreserveFirstFoundResourceTransformer`][PreserveFirstFoundResourceTransformer] with +> [`DeduplicatingResourceTransformer`][DeduplicatingResourceTransformer], as they handle duplicates differently and +> combining them leads to redundant or unexpected behavior. === ":material-language-kotlin: build.gradle.kts" diff --git a/docs/configuration/minimizing/README.md b/docs/configuration/minimizing/README.md index 1de79ba5e..f01d16d4b 100644 --- a/docs/configuration/minimizing/README.md +++ b/docs/configuration/minimizing/README.md @@ -44,10 +44,9 @@ loaded dynamically via `Class.forName(String)`. Each of the `group`, `name` and } ``` -!!! note - - Dependencies scoped as `api` will be automatically excluded from minimization and used as "entry points" on - minimization. +> [!NOTE] +> Dependencies scoped as `api` will be automatically excluded from minimization and used as "entry points" on +> minimization. Similar to [`ShadowJar.dependencies`][ShadowJar.dependencies], projects can also be excluded. @@ -71,22 +70,20 @@ Similar to [`ShadowJar.dependencies`][ShadowJar.dependencies], projects can also } ``` -!!! note - - When excluding a `project`, all dependencies of the excluded `project` are automatically excluded from - minimization as well. - -!!! tip "Difference between `dependencies` filter and `minimize` filter" - - Both `dependencies { ... }` and `minimize { ... }` implement [`DependencyFilter`][DependencyFilter], sharing the - same `include` / `exclude` syntax, but they control completely different operations: - - - **`shadowJar.dependencies` (Packaging filter)**: - - `exclude(...)`: Excludes matching dependencies from being bundled into the shadow JAR at all. - - `include(...)`: Bundles *only* matching dependencies into the shadow JAR, discarding all other dependencies. - - **`shadowJar.minimize` (Shrinking filter)**: - - `exclude(...)`: Excludes matching dependencies from *minimization / code shrinking*. The dependencies are still bundled into the shadow JAR, and all of their classes and methods are fully preserved without being stripped. - - `include(...)`: Applies code shrinking *only* to matching dependencies. All other dependencies are bundled and fully preserved. +> [!NOTE] +> When excluding a `project`, all dependencies of the excluded `project` are automatically excluded from +> minimization as well. + +> [!TIP] Difference between `dependencies` filter and `minimize` filter +> Both `dependencies { ... }` and `minimize { ... }` implement [`DependencyFilter`][DependencyFilter], sharing the +> same `include` / `exclude` syntax, but they control completely different operations: +> +> - **`shadowJar.dependencies` (Packaging filter)**: +> - `exclude(...)`: Excludes matching dependencies from being bundled into the shadow JAR at all. +> - `include(...)`: Bundles *only* matching dependencies into the shadow JAR, discarding all other dependencies. +> - **`shadowJar.minimize` (Shrinking filter)**: +> - `exclude(...)`: Excludes matching dependencies from *minimization / code shrinking*. The dependencies are still bundled into the shadow JAR, and all of their classes and methods are fully preserved without being stripped. +> - `include(...)`: Applies code shrinking *only* to matching dependencies. All other dependencies are bundled and fully preserved. ## Minimizing with R8 @@ -97,15 +94,15 @@ descriptors in `META-INF/services` are used to keep service providers. The default R8 configuration only shrinks unused code. It disables name minification and optimization. R8 also applies rules published in dependency JARs, for example under `META-INF/proguard`. -!!! note "Relocating Embedded ProGuard Rules" - - If you relocate classes using Shadow's `relocate` configuration from a dependency that publishes embedded R8/ProGuard - rules (for example under `META-INF/proguard`), those rules are not rewritten automatically. Add - [`ProGuardFilesResourceTransformer`][ProGuardFilesResourceTransformer] so class names and package patterns inside - embedded rules are updated to match your relocations. - - Alternatively, if you use [R8 Repackaging][r8-repackaging] (e.g. `-repackageclasses`), R8 applies embedded rules - natively without needing rule rewriting. +> [!NOTE] Relocating Embedded ProGuard Rules +> +> If you relocate classes using Shadow's `relocate` configuration from a dependency that publishes embedded R8/ProGuard +> rules (for example under `META-INF/proguard`), those rules are not rewritten automatically. Add +> [`ProGuardFilesResourceTransformer`][ProGuardFilesResourceTransformer] so class names and package patterns inside +> embedded rules are updated to match your relocations. +> +> Alternatively, if you use [R8 Repackaging][r8-repackaging] (e.g. `-repackageclasses`), R8 applies embedded rules +> natively without needing rule rewriting. === ":material-language-kotlin: build.gradle.kts" diff --git a/docs/configuration/relocation/README.md b/docs/configuration/relocation/README.md index 74bbbf223..a11d37395 100644 --- a/docs/configuration/relocation/README.md +++ b/docs/configuration/relocation/README.md @@ -4,9 +4,8 @@ Shadow is capable of scanning a project's classes and relocating specific depend required when one of the dependencies is susceptible to breaking changes in versions or to classpath pollution in a downstream project. -!!! tip - - Google's Guava and the ASM library are typical cases where package relocation can come in handy. +> [!TIP] +> Google's Guava and the ASM library are typical cases where package relocation can come in handy. Shadow uses the ASM library to modify class byte code to replace the package name and any import statements for a class. Any non-class files that are stored within a package structure are also relocated to the new location. @@ -31,14 +30,14 @@ The code snippet will rewrite the location for any class in the `junit.framework class `junit.framework.TestCase` becomes `shadow.junit.TestCase`. In the resulting JAR, the class file is relocated from `junit/framework/TestCase.class` to `shadow/junit/TestCase.class`. -!!! warning "Scope of Relocation" - - Relocation operates at a package level. - It is not necessary to specify any patterns for matching, it will operate simply on the prefix provided. - - Relocation will be applied globally to all instances of the matched prefix. - That is, it does **not** scope to _only_ the dependencies being shadowed. - Be specific as possible when configuring relocation as to avoid unintended relocations. +> [!WARNING] Scope of Relocation +> +> Relocation operates at a package level. +> It is not necessary to specify any patterns for matching, it will operate simply on the prefix provided. +> +> Relocation will be applied globally to all instances of the matched prefix. +> That is, it does **not** scope to _only_ the dependencies being shadowed. +> Be specific as possible when configuring relocation as to avoid unintended relocations. ## Filtering Relocation @@ -206,14 +205,14 @@ To configure automatic dependency relocation, set `enableAutoRelocation = true` } ``` -!!! warning "Performance & Transitive Dependencies" - - Configuring package auto relocation can add significant time to the shadow process as it will process all - dependencies in the configurations declared to be shadowed. By default, this is the `runtime` or `runtimeClasspath` - configurations. - - Be mindful that some Gradle plugins will automatically add dependencies to your class path. You may need to remove - these dependencies if you do not intend to shadow them into your library. +> [!WARNING] Performance & Transitive Dependencies +> +> Configuring package auto relocation can add significant time to the shadow process as it will process all +> dependencies in the configurations declared to be shadowed. By default, this is the `runtime` or `runtimeClasspath` +> configurations. +> +> Be mindful that some Gradle plugins will automatically add dependencies to your class path. You may need to remove +> these dependencies if you do not intend to shadow them into your library. ## Relocating Kotlin Standard Library diff --git a/docs/getting-started/README.md b/docs/getting-started/README.md index c53896161..f75096494 100644 --- a/docs/getting-started/README.md +++ b/docs/getting-started/README.md @@ -106,10 +106,9 @@ Alternatively, the plugin can be added to the buildscript classpath and applied:

-!!! note - - The correct maven coordinates for each version of Shadow can be found by referencing the Gradle Plugin - documentation [here][gradle-plugin-portal]. +> [!NOTE] +> The correct maven coordinates for each version of Shadow can be found by referencing the Gradle Plugin +> documentation [here][gradle-plugin-portal]. Shadow is a reactive plugin. This means that applying Shadow by itself will perform no configuration on your project. Instead, Shadow _reacts_ diff --git a/docs/multi-project/README.md b/docs/multi-project/README.md index 0c6be3195..58c921c38 100644 --- a/docs/multi-project/README.md +++ b/docs/multi-project/README.md @@ -84,10 +84,9 @@ the shadowed JAR by default, preventing accidental consumption of the unshadowed } ``` -!!! important - - Clearing `outgoing.variants` ensures Gradle doesn't select the unshadowed `classes` variant by default during - compilation. +> [!IMPORTANT] +> Clearing `outgoing.variants` ensures Gradle doesn't select the unshadowed `classes` variant by default during +> compilation. **Consuming projects can then depend on `:api` without specifying the `shadow` configuration:** diff --git a/mkdocs.yml b/mkdocs.yml index a8639b42d..da1a414ea 100644 --- a/mkdocs.yml +++ b/mkdocs.yml @@ -1,5 +1,5 @@ # pipx install mkdocs --include-deps -# pipx inject mkdocs mkdocs-material mdx_truly_sane_lists +# pipx inject mkdocs mkdocs-material mdx_truly_sane_lists mkdocs-callouts # mkdocs serve site_name: Shadow Gradle Plugin @@ -63,6 +63,7 @@ theme: plugins: - search: separator: '[\s\u200b\-_,:!=\[\]()"`/]+|\.(?!\d)|&[lg]t;|(?!\b)(?=[A-Z][a-z])' + - callouts # TODO: https://github.com/mkdocs/mkdocs/issues/3997 markdown_extensions: - smarty From e865ca8bcaa4e8ab5e2b2c26b78c0f861f14f35a Mon Sep 17 00:00:00 2001 From: Goooler Date: Wed, 26 Aug 2026 21:14:31 +0800 Subject: [PATCH 2/4] Format alerts with standalone headers for GitHub rendering https://docs.github.com/en/get-started/writing-on-github/getting-started-with-writing-and-formatting-on-github/basic-writing-and-formatting-syntax#alerts --- docs/README.md | 3 ++- docs/configuration/dependencies/README.md | 3 ++- docs/configuration/merging/README.md | 15 ++++++++++----- docs/configuration/minimizing/README.md | 7 +++++-- docs/configuration/relocation/README.md | 6 ++++-- 5 files changed, 23 insertions(+), 11 deletions(-) diff --git a/docs/README.md b/docs/README.md index 8e43a40a0..35e494ce8 100644 --- a/docs/README.md +++ b/docs/README.md @@ -7,7 +7,8 @@ A Gradle plugin for creating fat/uber JARs, transforming files, relocating packages, and optimizing applications with R8/ProGuard. The Gradle counterpart to Maven Shade Plugin. -> [!WARNING] Plugin ID Change +> [!WARNING] +> **Plugin ID Change** > > Previously this plugin was developed by [@johnrengelman][johnrengelman] and published under the ID > [`com.github.johnrengelman.shadow`][johnrengelman's] before maintenance was transferred to the diff --git a/docs/configuration/dependencies/README.md b/docs/configuration/dependencies/README.md index 168e3c022..6ff120ecf 100644 --- a/docs/configuration/dependencies/README.md +++ b/docs/configuration/dependencies/README.md @@ -25,7 +25,8 @@ The above code sample would configure the [`ShadowJar`][ShadowJar] task to merge `compileClasspath` configuration. This means any dependency declared in the `runtimeOnly` configuration would be **not** be included in the final JAR. -> [!WARNING] Required Configuration +> [!WARNING] +> **Required Configuration** > > Note the literal use of [`project.configurations`][Project.configurations] when setting the > [`configurations`][ShadowJar.configurations] attribute of a [`ShadowJar`][ShadowJar] task. diff --git a/docs/configuration/merging/README.md b/docs/configuration/merging/README.md index 97b8e2468..e1a7830fb 100644 --- a/docs/configuration/merging/README.md +++ b/docs/configuration/merging/README.md @@ -6,7 +6,8 @@ Maven Shade implementation. A [`ResourceTransformer`][ResourceTransformer] is in being written to the final output JAR. This allows a [`ResourceTransformer`][ResourceTransformer] to determine if it should process a particular entry and apply any modifications before writing the stream to the output. -> [!IMPORTANT] Guaranteed Processing Order +> [!IMPORTANT] +> **Guaranteed Processing Order** > > [`ResourceTransformer`][ResourceTransformer] follows a guaranteed processing order: > @@ -59,7 +60,8 @@ Different strategies will lead to different results for `foo/bar` files in the J exception like `Entry .* is a duplicate but no duplicate handling strategy has been set`. - `WARN`: **Warn** about duplicates in the build log; this behaves exactly as `INCLUDE` otherwise. -> [!NOTE] Precedence of DuplicatesStrategy +> [!NOTE] +> **Precedence of DuplicatesStrategy** > > The `duplicatesStrategy` evaluation takes precedence over transforming and relocating. > Because `ShadowJar` is a subclass of Gradle's `AbstractCopyTask`, duplicate filtering configured via @@ -120,7 +122,8 @@ Alternatively, you can follow these steps: [`filesMatching`][Jar.filesMatching], [`filesNotMatching`][Jar.filesNotMatching], or [`eachFile`][Jar.eachFile] functions to set their `duplicatesStrategy` to `INCLUDE` or `WARN`. -> [!WARNING] Build Cache Impact +> [!WARNING] +> **Build Cache Impact** > > Functions inherited from [`CopySpec`][CopySpec], such as [`filesMatching`][Jar.filesMatching], > [`filesNotMatching`][Jar.filesNotMatching], [`eachFile`][Jar.eachFile], or others, disable the output caching. @@ -358,7 +361,8 @@ the [`ServiceFileTransformer`][ServiceFileTransformer]: } ``` -> [!NOTE] Groovy Extension Modules +> [!NOTE] +> **Groovy Extension Modules** > > Groovy Extension Module descriptor files (located at > `META-INF/services/org.codehaus.groovy.runtime.ExtensionModule`) are ignored by the @@ -877,7 +881,8 @@ If certain duplicate resources at the same path legitimately have different cont or `pom.xml` files from different dependency versions), you can exclude those paths from being checked using `exclude(...)`: -> [!WARNING] Do Not Combine with PreserveFirstFoundResourceTransformer +> [!WARNING] +> **Do Not Combine with PreserveFirstFoundResourceTransformer** > > Do not combine [`PreserveFirstFoundResourceTransformer`][PreserveFirstFoundResourceTransformer] with > [`DeduplicatingResourceTransformer`][DeduplicatingResourceTransformer], as they handle duplicates differently and diff --git a/docs/configuration/minimizing/README.md b/docs/configuration/minimizing/README.md index f01d16d4b..782ee90e2 100644 --- a/docs/configuration/minimizing/README.md +++ b/docs/configuration/minimizing/README.md @@ -74,7 +74,9 @@ Similar to [`ShadowJar.dependencies`][ShadowJar.dependencies], projects can also > When excluding a `project`, all dependencies of the excluded `project` are automatically excluded from > minimization as well. -> [!TIP] Difference between `dependencies` filter and `minimize` filter +> [!TIP] +> **Difference between `dependencies` filter and `minimize` filter** +> > Both `dependencies { ... }` and `minimize { ... }` implement [`DependencyFilter`][DependencyFilter], sharing the > same `include` / `exclude` syntax, but they control completely different operations: > @@ -94,7 +96,8 @@ descriptors in `META-INF/services` are used to keep service providers. The default R8 configuration only shrinks unused code. It disables name minification and optimization. R8 also applies rules published in dependency JARs, for example under `META-INF/proguard`. -> [!NOTE] Relocating Embedded ProGuard Rules +> [!NOTE] +> **Relocating Embedded ProGuard Rules** > > If you relocate classes using Shadow's `relocate` configuration from a dependency that publishes embedded R8/ProGuard > rules (for example under `META-INF/proguard`), those rules are not rewritten automatically. Add diff --git a/docs/configuration/relocation/README.md b/docs/configuration/relocation/README.md index a11d37395..8358ca62a 100644 --- a/docs/configuration/relocation/README.md +++ b/docs/configuration/relocation/README.md @@ -30,7 +30,8 @@ The code snippet will rewrite the location for any class in the `junit.framework class `junit.framework.TestCase` becomes `shadow.junit.TestCase`. In the resulting JAR, the class file is relocated from `junit/framework/TestCase.class` to `shadow/junit/TestCase.class`. -> [!WARNING] Scope of Relocation +> [!WARNING] +> **Scope of Relocation** > > Relocation operates at a package level. > It is not necessary to specify any patterns for matching, it will operate simply on the prefix provided. @@ -205,7 +206,8 @@ To configure automatic dependency relocation, set `enableAutoRelocation = true` } ``` -> [!WARNING] Performance & Transitive Dependencies +> [!WARNING] +> **Performance & Transitive Dependencies** > > Configuring package auto relocation can add significant time to the shadow process as it will process all > dependencies in the configurations declared to be shadowed. By default, this is the `runtime` or `runtimeClasspath` From 524c1a46bccfc1768a3a02f8403ebec2ef130ae5 Mon Sep 17 00:00:00 2001 From: Goooler Date: Wed, 26 Aug 2026 21:24:20 +0800 Subject: [PATCH 3/4] Symlink CHANGELOG.md to docs/changes/README.md for mkdocs callouts support --- docs/changes/README.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) mode change 100644 => 120000 docs/changes/README.md diff --git a/docs/changes/README.md b/docs/changes/README.md deleted file mode 100644 index 786b75d5a..000000000 --- a/docs/changes/README.md +++ /dev/null @@ -1 +0,0 @@ ---8<-- "CHANGELOG.md" diff --git a/docs/changes/README.md b/docs/changes/README.md new file mode 120000 index 000000000..699cc9e7b --- /dev/null +++ b/docs/changes/README.md @@ -0,0 +1 @@ +../../CHANGELOG.md \ No newline at end of file From 6d1e8b8f9ef80dce6bc74fdebc0ac312347cd01f Mon Sep 17 00:00:00 2001 From: Goooler Date: Wed, 26 Aug 2026 21:40:00 +0800 Subject: [PATCH 4/4] Remove trailing whitespace in CHANGELOG.md --- CHANGELOG.md | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 76907ec7c..3656ff404 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -345,7 +345,7 @@ > If you are upgrading from 8.x versions, please read 9.0.0 release notes first. > [!TIP] -> You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). +> You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). > If there are any things missing in the changelog or the doc site, please report them to us. ### Changed @@ -368,12 +368,12 @@ > This release is a major update from the 8.x series. The plugin has been fully rewritten in Kotlin, bringing > significant improvements to maintainability, performance, and future extensibility. It introduces many new features, > enhancements, and bug fixes, and includes several breaking changes. Please review the changelog carefully and consult -> the [new doc site](https://gradleup.com/shadow/) before upgrading. +> the [new doc site](https://gradleup.com/shadow/) before upgrading. > > *If you really don't want to upgrade, you can still use the 8.3.x, which is also Gradle 9 compatible. But no additional features or crucial bug fixes will be included in the 8.x line.* > [!TIP] -> You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). +> You can diff the shadowed JARs when upgrading from 8.x to 9.x by using [Diffuse](https://github.com/JakeWharton/diffuse). > If there are any things missing in the changelog or the doc site, please report them to us. > [!NOTE]