Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Gradle: Distributing Executable, Obfuscated Jar File

I'm trying to use gradle with proguard to obfuscate the code then generate a zip file to distribute. I'd like to use the distribution plugin, but it always includes the jar that is generated by the jar task. Is there some way to force the distribution plugin to omit the original (non-obfuscated) jar and only include the obfuscated jar? I can easily add the obfuscated jar in addition to the original, but I want to distribute the obfuscated jar instead of the original so the generated execution scripts run against the obfuscated version.

Here's my abridged build.gradle file:

buildscript {
    repositories {
        mavenCentral()
    }
    dependencies {
        classpath 'net.sf.proguard:proguard-gradle:5.3.3'
    }
}

apply plugin: 'java'
apply plugin: 'application'

task obfuscate(type: proguard.gradle.ProGuardTask) {
    configuration 'proguard.txt'

    injars "build/libs/${rootProject.name}.jar"
    outjars "build/libs/${rootProject.name}-release.jar"
}

jar.finalizedBy(project.tasks.obfuscate)

distributions {
    main {
        contents {
            from(obfuscate) {
                into "lib"
            }
            from(jar) {
                exclude "*.jar"
            }
        }
    }
}

I've tried a number of things in the distributions block to try to exclude the original jar, but nothing seems to work.

Any ideas would be greatly appreciated.

like image 674
desilvai Avatar asked Sep 11 '25 19:09

desilvai


1 Answers

This isn't the best solution, but I was able to work around the issue by renaming the jars at the end of the obfuscation step. Now, I name the original jar something like <JAR_NAME>-original.jar and I give the obfuscated jar the original jar's name. I still wish there was a better way to do it, but this seems to work.

Here is the updated, abridged build.gradle file:

import java.nio.file.Paths

buildscript {
    repositories {
        mavenCentral()
    }
    dependencies {
        classpath 'net.sf.proguard:proguard-gradle:5.3.3'
    }
}

apply plugin: 'java'
apply plugin: 'application'

def jarNameWithoutExtension = jar.archiveName.with { it.take(it.lastIndexOf(".")) }
def obfuscatedJarName = "${jarNameWithoutExtension}-release.jar"
def jarFileLocation = jar.archivePath.parent
def obfuscatedFilePath = Paths.get(jarFileLocation, obfuscatedJarName)

task obfuscate(type: proguard.gradle.ProGuardTask) {
    configuration 'proguard.txt'

    injars jar.archivePath
    outjars obfuscatedFilePath.toString()

    // Rename the original and obfuscated jars.  We want the obfuscated jar to
    // have the original jar's name so it will get included in the distributable
    // package (generated by installDist / distZip / distTar / assembleDist).
    doLast {
        jar.archivePath.renameTo(Paths.get(jarFileLocation, "$jarNameWithoutExtension-original.jar").toFile())

        obfuscatedFilePath.toFile().renameTo(jar.archivePath)
    }
}

jar.finalizedBy(project.tasks.obfuscate)
like image 81
desilvai Avatar answered Sep 13 '25 15:09

desilvai