Skip to content

The plugin changes constants with values similar to package names #232

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

Open
sergeykad opened this issue Aug 4, 2016 · 17 comments · May be fixed by #1401
Open

The plugin changes constants with values similar to package names #232

sergeykad opened this issue Aug 4, 2016 · 17 comments · May be fixed by #1401
Labels

Comments

@sergeykad
Copy link

Shadow Version 1.2.3

Gradle Version 2.14

Expected Behavior: There will be an option to control this behavior, preferably using filters

Actual Behavior: All constants are changed

For example
Before Shadow:
public static final String AttributePrefix = "org.mypackage";
After Shadow
public static final String AttributePrefix = "shadow.mypackage";

@johnrengelman
Copy link
Collaborator

Yeah, the relocation code is ported from Maven Shade which exhibits this same problem:
https://issues.apache.org/jira/browse/MSHADE-156
https://issues.apache.org/jira/browse/MSHADE-153

I'll have to think about how best to tackle this. Those tickets have been open for 3 years and they haven't come up with a better solution.

So, this might take a while for me to get something I'm happy with.

@sergeykad
Copy link
Author

I see.
Will not ability to exclude classes from this constants substitution solve the issue?
Maybe it is not a perfect solution, but it should work in vast majority of cases.

@johnrengelman johnrengelman added this to the 3.0.0 milestone Nov 18, 2016
@johnrengelman johnrengelman removed this from the 5.0.0 milestone Jan 20, 2019
@pietrobraione
Copy link

Are there updates on this issue? Is there any workaround for it?

@eli-darkly
Copy link

I'm having a similar issue, but it's worse because the strings in question are very clearly NOT package names - they just happen to start with something that could be a package name.

The package is "redis" (the root package of the Jedis client - it's nonstandard, but unfortunately that's what they chose) and the string is a Redis URL string, "redis://localhost:6379". When I shade the Jedis dependency using a prefix of "xxx.shaded", my string becomes "xxx/shaded/redis://localhost:6379". Surely it ought to be possible to know that that wasn't a class/package path, given the double slash.

@johnrengelman
Copy link
Collaborator

I see two ways of addressing this that I would be happy to accept PRs for.

  1. change the relocation code to do an explicit match of the String against the JVM spec for package names. We’d have to be careful about perf here, perhaps we can only eval against the pattern when the value we are looking to replace is a String (an not a class declaration or package statement)
  2. extend the relocation classes to also accept a set of exclude patterns which can be used to skip certain matches. (This could actually be how the first option is implemented with the default set configured to have patterns that match the JVM spec)

@eli-darkly
Copy link

I think 2 sounds good— someone's inevitably going to have some strings in their code that will look like valid class names but aren't (the original reporter of this issue had some).

@martinbonnin
Copy link
Member

martinbonnin commented Mar 26, 2021

That would be super helpful. We're doing a Gradle plugin that generates code so it contains a lot of Strings that look exactly like package names... Because well, they actually are package names! And renaming them will break at runtime. For our use cases, I would actually prefer to have a set of include patterns than excludes since there is very little use of reflection.

Ultimately, something like GraalVM native image reflection support would be nice albeit considerably more work

@mahmoudyusuf94
Copy link

I am facing a similar problem:
in my build.gradle I have the following:

relocate 'io.netty','thirdparty.io.netty'

I found string literals affected by this shading which caused some runtime errors with the netty dependency.

The following string literal is defined in the original dependency:
String staticLibName = "netty_tcnative"

In the shaded jar, this string literal is changed to:
String staticLibName = "thirdparty.netty_tcnative";

Is there any way I can prevent this behavior of changing the string literals?

@eli-darkly
Copy link

Based on previous responses, it sounds like a workaround won't be implemented until someone contributes a PR.

@martinbonnin
Copy link
Member

martinbonnin commented Mar 20, 2023

@johnrengelman can you give more details where that was fixed? Nevermind, looks like it wasn't

@EliteMasterEric
Copy link

I am still experiencing this bug with my project, which uses Gradle 7.5.1 and Shadow 7.1.2.

bitspittle added a commit to varabyte/kobweb that referenced this issue Nov 7, 2023
We now understand the root problem thanks to DennisTsar's
investigation. The shadow plugin was by chance affecting a
private variable deep inside the coroutine library (named
completedExpandBuffersAndPauseFlag) which matched "com",
even though we only expected relocations to work on packages.

As a result, we add the "com" relocation back in, plus trailing
"." suffixes to prevent accidental matching.

See also: GradleUp/shadow#232
And also: https://issues.apache.org/jira/browse/MSHADE-156
@capitaorev
Copy link

Hi folks,

Joining the party late :)

I'm having a similar/same issue trying to relocate google-cloud-logging with a config like this:

plugins {
    id 'com.github.johnrengelman.shadow' version '7.1.2'
}

dependencies {
    implementation("com.google.cloud:google-cloud-logging:${googleCloudLoggingVersion}")
}

def shadedPrefix = 'com.mycompany.common.internal.shade.gcloud'
shadowJar {
    relocate 'com', "${shadedPrefix}.com"
    relocate 'io', "${shadedPrefix}.io"
    relocate 'javax.annotation', "${shadedPrefix}.javax.annotation"
    relocate 'org', "${shadedPrefix}.org"

    archiveClassifier.set('')
    mergeServiceFiles()
}

With this I ended up having strings like /computeMetadata/v1/instance/service-accounts/default/token being renamed to /com/mycompany/common/internal/shade/gcloud/computeMetadata/v1/instance/service-accounts/default/token, which breaks GCE authentication.

I believe this is the exact same problem (maybe more like this), so just adding more info for future reference.

@weijiii
Copy link

weijiii commented Sep 16, 2024

Having a similar issue here

public static final String ITEMS_KEY = "items";

is interpreted as

public static final String ITEMS_KEY = "xxx.shaded.items";

I am curious though when is this going to be triggered; I tried excluding the package containing this static field but it did not work

relocate ('xxx', 'xxx.shaded') {
  exclude 'xxx.yyy'
}

@cputnam-a11y
Copy link

I am also having this issue

@xjose97x
Copy link

No update so far?

This issue was opened in 2016.

@cputnam-a11y
Copy link

cputnam-a11y commented Apr 15, 2025

No update so far?

This issue was opened in 2016.

I would assume the transition to gradleup probably didn't help visibility to the devs. I'm hoping for a solution, but the solution I've received from peers is just to use something other than shadow. Would be glad to return once this gets fixed
Edit: the upstream dev of the library I'm having trouble with is willing to obfuscate the part of his code shadow is breaking. It looks like encoding the problematic string in base64 can help.

@Goooler Goooler linked a pull request Apr 16, 2025 that will close this issue
1 task
@cputnam-a11y
Copy link

cputnam-a11y commented Apr 16, 2025

No update so far?
This issue was opened in 2016.

I would assume the transition to gradleup probably didn't help visibility to the devs. I'm hoping for a solution, but the solution I've received from peers is just to use something other than shadow. Would be glad to return once this gets fixed Edit: the upstream dev of the library I'm having trouble with is willing to obfuscate the part of his code shadow is breaking. It looks like encoding the problematic string in base64 can help.

for anyone who is struggling, I managed to disable the remapping of the one constant causing me trouble by creating a custom relocator and returning the original value only for that constant.

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

Successfully merging a pull request may close this issue.