{"id":22707553,"url":"https://github.com/xvik/gradle-java-lib-plugin","last_synced_at":"2025-04-13T12:31:34.150Z","repository":{"id":38375289,"uuid":"46704673","full_name":"xvik/gradle-java-lib-plugin","owner":"xvik","description":"Gradle maven publishing configuration for Java or Groovy library or gradle plugin","archived":false,"fork":false,"pushed_at":"2025-01-31T04:29:34.000Z","size":580,"stargazers_count":19,"open_issues_count":0,"forks_count":1,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-03-27T03:35:12.786Z","etag":null,"topics":["gradle","gradle-plugin","java","maven-publish"],"latest_commit_sha":null,"homepage":"","language":"Groovy","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/xvik.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2015-11-23T07:48:26.000Z","updated_at":"2025-01-31T04:29:32.000Z","dependencies_parsed_at":"2023-11-18T06:25:25.788Z","dependency_job_id":"83ef0ce2-245a-42f5-bc44-1764a184b628","html_url":"https://github.com/xvik/gradle-java-lib-plugin","commit_stats":null,"previous_names":[],"tags_count":19,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xvik%2Fgradle-java-lib-plugin","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xvik%2Fgradle-java-lib-plugin/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xvik%2Fgradle-java-lib-plugin/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/xvik%2Fgradle-java-lib-plugin/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/xvik","download_url":"https://codeload.github.com/xvik/gradle-java-lib-plugin/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":248714371,"owners_count":21149873,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["gradle","gradle-plugin","java","maven-publish"],"created_at":"2024-12-10T10:13:24.411Z","updated_at":"2025-04-13T12:31:34.113Z","avatar_url":"https://github.com/xvik.png","language":"Groovy","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Gradle Java-lib plugin\n[![License](https://img.shields.io/badge/license-MIT-blue.svg?style=flat)](http://www.opensource.org/licenses/MIT)\n[![CI](https://github.com/xvik/gradle-java-lib-plugin/actions/workflows/CI.yml/badge.svg)](https://github.com/xvik/gradle-java-lib-plugin/actions/workflows/CI.yml)\n[![Appveyor build status](https://ci.appveyor.com/api/projects/status/github/xvik/gradle-java-lib-plugin?svg=true)](https://ci.appveyor.com/project/xvik/gradle-java-lib-plugin)\n[![codecov](https://codecov.io/gh/xvik/gradle-java-lib-plugin/branch/master/graph/badge.svg)](https://codecov.io/gh/xvik/gradle-java-lib-plugin)\n\n\n### About\n\nPlugin do all boilerplate of maven publication configuration (using [maven-publish](https://docs.gradle.org/current/userguide/publishing_maven.html)) \nfor java (or groovy) library or gradle plugin. Simplifies POM configuration and dependencies management (BOM).\nAlso, changes some defaults common for java projects (like UTF-8 usage).\n\nMakes gradle more \"maven\" (in sense of simplicity, some behaviours and for [multi-module projects](#maven-like-multi-module-project)).\n\nFeatures:\n\n* Maven-like `jar` configuration\n    - put `pom.xml` and `pom.properties` inside jar\n    - fill manifest properties \n* Configure javadoc and sources artifacts (required for maven central publish)\n  (with native gradle integrations)\n* Prepare maven publication (`maven-publish` plugin configuration)\n    - `maven` publication configured with all jars (jar, sources javadoc)\n* Applies [pom plugin](https://github.com/xvik/gradle-pom-plugin) which:   \n    - Fix [dependencies scopes](https://github.com/xvik/gradle-pom-plugin/#dependencies) \n    in generated pom\n    - Add `maven.pom` configuration to [simplify pom definition](https://github.com/xvik/gradle-pom-plugin#pom-configuration).\n    - Add `maven.withPomXml` configuration closure to use if you [need manual xml configuration](https://github.com/xvik/gradle-pom-plugin#manual-pom-modification) \n* Add `install` task as shortcut for `publishToMavenLocal` (simpler to use)\n* Apply `UTF-8` encoding for:\n    - compile tasks: `JavaCompile` and `GroovyCompile`\n    - javadoc (encoding, charSet, docEncoding) \n    - test tasks: set `file.encoding=UTF-8` system property (only for test tasks)   \n* Prepares BOM publication for [java-platform](https://docs.gradle.org/current/userguide/java_platform_plugin.html) plugin\n* Test and coverage reports aggregation for multi-module projects\n* Simplifies gradle platforms usage in multi-module projects (avoid \"platform\" leaking in published poms)\n\nIf you need [multiple publications](https://docs.gradle.org/current/userguide/publishing_maven.html#N17EB8) from the same project, \nthen you will have to perform additional configuration or, maybe (depends on case), use only [pom plugin](https://github.com/xvik/gradle-pom-plugin). \n\n**Confusion point**: plugin named almost the same as gradle's own [java-library](https://docs.gradle.org/current/userguide/java_library_plugin.html) plugin,\nbut plugins do *different things* (gradle plugin only provides `api` and `implementation` configurations) and plugins *could* be used together.\n\n##### Summary\n\n* Configuration closures: `maven` (from pom plugin), `javaLib`\n* Tasks: `sourcesJar`, `javadocJar`, `install`, `openDependencyReport`      \n* [Publication](https://docs.gradle.org/current/userguide/publishing_maven.html#publishing_maven:publications): `maven`, `bom`\n* Enable plugins: [maven-publish](https://docs.gradle.org/current/userguide/publishing_maven.html),\n[ru.vyarus.pom](https://github.com/xvik/gradle-pom-plugin)\n  \n### Setup\n\n[![Maven Central](https://img.shields.io/maven-central/v/ru.vyarus/gradle-java-lib-plugin.svg)](https://maven-badges.herokuapp.com/maven-central/ru.vyarus/gradle-java-lib-plugin)\n[![Gradle Plugin Portal](https://img.shields.io/maven-metadata/v/https/plugins.gradle.org/m2/ru/vyarus/java-lib/ru.vyarus.java-lib.gradle.plugin/maven-metadata.xml.svg?colorB=007ec6\u0026label=plugins%20portal)](https://plugins.gradle.org/plugin/ru.vyarus.java-lib)\n\n```groovy\nbuildscript {\n    repositories {\n      gradlePluginPortal()\n    }\n    dependencies {\n        classpath 'ru.vyarus:gradle-java-lib-plugin:3.0.0'\n    }\n}\napply plugin: 'ru.vyarus.java-lib'\n```\n\nOR\n\n```groovy\nplugins {\n    id 'ru.vyarus.java-lib' version '3.0.0'\n}\n```\n\n#### Compatibility\n\nPlugin compiled for java 8, compatible with java 17\n\nGradle | Version\n--------|-------\n7       | 3.0.0\n5.1     | [2.4.0](https://github.com/xvik/gradle-java-lib-plugin/tree/2.4.0)\n4.6     | [1.1.2](https://github.com/xvik/gradle-java-lib-plugin/tree/1.1.2)\nolder   | [1.0.5](https://github.com/xvik/gradle-java-lib-plugin/tree/1.0.5)\n\nNOTE: plugin-publish 1.x would work properly only with gradle 7.6 or above\n\n#### Snapshots\n\n\u003cdetails\u003e\n      \u003csummary\u003eSnapshots may be used through JitPack\u003c/summary\u003e\n\n* Go to [JitPack project page](https://jitpack.io/#ru.vyarus/gradle-java-lib-plugin)\n* Select `Commits` section and click `Get it` on commit you want to use \n    or use `master-SNAPSHOT` to use the most recent snapshot\n\n* Add to `settings.gradle` (top most!) (exact commit hash might be used as version):\n\n  ```groovy\n  pluginManagement {\n      resolutionStrategy {\n          eachPlugin {\n              if (requested.id.id == 'ru.vyarus.java-lib') {\n                  useModule('ru.vyarus:gradle-java-lib-plugin:master-SNAPSHOT')\n              }\n          }\n      }\n      repositories {                        \n          gradlePluginPortal()\n          maven { url 'https://jitpack.io' }                    \n      }\n  }    \n  ``` \n* Use plugin without declaring version: \n\n  ```groovy\n  plugins {\n      id 'ru.vyarus.java-lib'\n  }\n  ```  \n\n\u003c/details\u003e  \n\n### Usage\n\nPlugin activate features based on registered plugins. Plugin support several usage scenarios.\n\nIn case of multi-module projects, plugin activate features only in applied module, ignoring submodules or root module\n(so to apply it in all submodules use `allprojects` or `subprojects` section)\n\nExample projects:\n\n* [Java library](https://github.com/xvik/dropwizard-guicey), published to maven central\n* [Multi-module java library](https://github.com/xvik/dropwizard-guicey-ext) (with BOM), published to maven central\n* [Simple multi-module library](https://github.com/xvik/yaml-updater) (without BOM), published to maven central\n* [This project](https://github.com/xvik/gradle-java-lib-plugin/blob/master/build.gradle) is an example of gradle plugin publication to maven central and plugins portal\n\n\n#### Java module\n\n```groovy\nplugins {\n  id 'java' // groovy or java-library\n  // id 'signing'\n  // id 'project-report'\n  id 'ru.vyarus.java-lib'\n}\n\ngroup = 'your.group'                    \nversion = '1.0.0'                       \ndescription = 'My project description'\n\n// configure target pom\nmaven.pom {\n  name = 'Project Name'\n  description = 'My awesome project'\n  ...\n}\n\nrepositories { mavenLocal(); mavenCentral() }\ndependencies {\n  ...\n}\n\njavaLib {\n  // withoutJavadoc()\n  // withoutSources()\n  withoutGradleMetadata()\n  \n  // autoModuleName = 'project-module-name'\n  \n  pom {\n    // removeDependencyManagement()\n    // forceVersions()\n    // disableScopesCorrection()\n    // disableBomsReorder()\n  }\n}\n\n```\n\nActivates with [java](https://docs.gradle.org/current/userguide/java_plugin.html),\n[groovy](https://docs.gradle.org/current/userguide/groovy_plugin.html) or \n[java-library](https://docs.gradle.org/current/userguide/java_library_plugin.html) plugin.  \nTypical usage: single-module gradle project which must be published to maven central (or any other maven repo) \n\n* Adds `javadoc` and `sources` for publication\n* Registers `maven` publication for pom, jar, javadoc and sources artifacts\n* Applies UTF-8 encoding for java/groovy compile, javadoc/groovydoc and test executions\n* If [signing](https://docs.gradle.org/current/userguide/signing_plugin.html) plugin active, [configures publication signing](#signing) (required for maven central publication)\n* Adds `install` task for installation into local repository (like maven; simply shortcut for `publishToMavenLocal` task)\n* Enables xml jacoco reports (if jacoco enabled; required for coverage services)\n* Register [ru.vyarus.pom](https://github.com/xvik/gradle-pom-plugin) plugin which:\n    - adds `optional` and `provided` configurations (in maven sense)\n    - fixes dependency scopes in the generated pom\n    - moves up dependencyManagement section in the generated pom (if platforms used)\n    - adds `maven.pom` extension for pom declaration (`maven.withPomXml` might be used for low-level modification)\n* Utilities:\n  - simple Auto-Module-Name declaration (java 9 modules)\n  - option to disable gradle metadata publication (maven central fails on it sometimes)\n  - option to remove dependencyManagement section in the generated pom (appears if platforms used): use resolved dependencies versions instead (pom plugin feature)\n* Adds [openDependencyReport](#dependency-report) task added if [project-report](https://docs.gradle.org/current/userguide/project_report_plugin.html) plugin enabled  \n  (opens `htmlDependencyReport` directly in browser)\n\n#### BOM module\n\n```groovy\nplugins {\n  id 'java-platform' \n  // id 'signing'\n  // id 'project-report'\n  id 'ru.vyarus.java-lib'\n}\n\ngroup = 'your.group'                    \nversion = '1.0.0'                       \ndescription = 'My project description'\n\nmaven.pom {\n  ...\n}\n\nrepositories { mavenLocal(); mavenCentral() }\ndependencies {\n  api platform('ru.vyarus.guicey:guicey-bom:5.2.0-1')\n  constraints {\n    api 'org.webjars:webjars-locator:0.40'\n  }\n  // add subprojects to published BOM\n  project.subprojects.each { api it }\n}\n\njavaLib {\n  bom {\n    // change artifact from project name, if required\n    artifactId = 'something-bom'\n    description = 'Different from project description'\n  }\n  withoutGradleMetadata()\n}\n```  \n\nActivates with [java-platform](https://docs.gradle.org/current/userguide/java_platform_plugin.html) plugin.  \nTypical usage: BOM module (might be root project) in multi-module project\n\n* Activates platform dependencies (javaPlatform.allowDependencies()) to allow single dependencies declaration\n* Registers `bom` publication for bom artifact (produced from declared platform)\n* Register [ru.vyarus.pom](https://github.com/xvik/gradle-pom-plugin) plugin (with the same features as above)\n* If [signing](https://docs.gradle.org/current/userguide/signing_plugin.html) plugin active, [configures publication signing](#signing) (required for maven central publication)\n* Adds `install` task for installation into local repository (like maven; simply shortcut for `publishToMavenLocal` task)\n* Utilities:\n  - option to disable gradle metadata publication (maven central fails on it sometimes)\n  - option to change bom artifact id (useful when platform declared in the root module)\n* Adds [openDependencyReport](#dependency-report) task added if [project-report](https://docs.gradle.org/current/userguide/project_report_plugin.html) plugin enabled  \n  (opens `htmlDependencyReport` directly in browser) \n \n#### Root project reports aggregation\n\n```groovy\nplugins {\n  id 'base' \n  id 'jacoco'\n  //id 'project-report'\n  id 'ru.vyarus.java-lib'\n}\n\njavaLib {\n  aggregateReports()\n}\n\n// sub modules - simple java projects\nsubprojects {\n  apply plugin: 'java'\n  \n  ...\n}\n```\n\nActivates with [base](https://docs.gradle.org/current/userguide/base_plugin.html) plugin.  \nUsed to aggregate test and coverage reports from java submodules.\n\nBy default, will only register `openDependencyReport` task added if [project-report](https://docs.gradle.org/current/userguide/project_report_plugin.html) plugin enabled.  \nReports aggregation must be explicitly triggered:\n  - Adds `test` task which would simply aggregate (run if required) java submodules test reports\n  - If jacoco plugin active, add `jacocoMerge` (not for direct usage) and\n`jacocoTestReport` tasks to aggregate jacoco xml and html reports from java submodules\n  - If project-report plugin active, will aggregate dependency reports for submodules\n\nIn short: it adds absolutely the same tasks as in java modules and generates\nreports exactly into the same locations so there would be no difference in paths\nwhen configuring external services (e.g. coveralls).\n\nNOTE: aggregation will work with `java-platform` plugin too if it used in the root module (see [complete multi-module example](#maven-like-multi-module-project)).\n\n### Options\n\n```groovy\njavaLib {\n\n  /**\n   * Do not publish javadoc (groovydoc) with `maven` publication. \n   */\n  withoutJavadoc()\n\n  /**\n   * Do not publish sources with `maven` publication. \n   */\n  withoutSources()\n\n  /**\n   * Do not publish gradle metadata artifact. \n   * Affects all publications (not just registered by plugin).\n   */\n  withoutGradleMetadata()\n\n  /**\n   * Disable all publications. Might be used to disable configured BOM publication or any sub-module publication.\n   */\n  withoutPublication()\n\n  /**\n   * Shortcut for Auto-Module-Name meta-inf header declaration\n   */\n  autoModuleName = 'project-module-name'\n\n  /**\n   * Used ONLY with java-platform plugin if published artifact must differ from\n   * project name (for example, when declared in the root project).\n   */\n  bom {\n    // when not declared, project.name used\n    artifactId = 'name'\n    // when not declared, project.description used\n    description = 'desc'\n  }\n\n  /**\n   * Used in the root project (project with child projects) to aggregate\n   * test, coverage (jacoco) and dependency (project-report) reports. \n   * Requires at least `base` plugin. Will work java-platform plugin\n   * (will not work with java plugin because such module can't aggregate).\n   */\n  aggregateReports()\n}\n```\n\n### POM\n\nYou need to specify general project info:\n\n```groovy\ngroup = 'your.group'                    // maven group\nversion = '1.0.0'                       // project version\ndescription = 'My project description'  // optional (affects jar manifest) \n```\n\nNote: maven `artifactId` will be the same as project name, and the default for project name\nis current directory name. If you need to change name, add in `settings.gradle`:\n\n```\nrootProject.name = 'the-name-you-want'\n```\n\nFor maven-central publication you need to fill all required pom sections:\n\n```groovy\nmaven.pom {\n    // name and desciption set automatically from project, but you can override them here\n    //name 'Project Name'\n    //description 'My awesome project'\n    licenses {\n        license {\n            name = \"The MIT License\"\n            url = \"http://www.opensource.org/licenses/MIT\"\n            distribution = 'repo'\n        }\n    }\n    scm {\n        url = 'https://github.com/me/my-repo'\n        connection = 'scm:git@github.com:me/my-repo.git'\n        developerConnection = 'scm:git@github.com:me/my-repo.git'\n    }\n    developers {\n        developer {\n            id = \"dev1\"\n            name = \"Dev1 Name\"\n            email = \"dev1@email.com\"\n        }\n    }\n}\n``` \n\nRead more about pom configuration in the [pom plugin's docs](https://github.com/xvik/gradle-pom-plugin#pom-configuration). \n\nIf your project hosted on github you may use [github-info](https://github.com/xvik/gradle-github-info-plugin) plugin, \nwhich fills most github-related pom sections for you automatically.\n\nUse the following configurations to get correct scopes in the resulted pom:\n\nMaven scope | Gradle configuration\n------------| ----------------\ncompile     | implementation, api\nruntime     | runtimeOnly\nprovided    | provided  (**not** compileOnly!)\noptional    | optional, [feature variants](https://github.com/xvik/gradle-pom-plugin#feature-variants)\n\nSee [pom plugin doc](https://github.com/xvik/gradle-pom-plugin#dependencies) for more details about dependencies scopes in the generated pom\n\n#### Using BOMs\n\nWhen you use BOMs (for dependencies versions management) with spring plugin or gradle platform you'll have \n`dependencyManagement` section generated in the target pom. Often it is not desired:to use only resolved\nversions and avoid `dependencyManagent` use:\n\n```groovy\nmaven.pom.removeDependencyManagement()\n```\n\nRead more in the [pom plugin's docs](https://github.com/xvik/gradle-pom-plugin#improving-boms-usage)\n\n#### BOM declaration\n\nThe simplest way to declare BOM is using [java-platform](https://docs.gradle.org/current/userguide/java_platform_plugin.html)\n\n```groovy\nplugins {\n  id 'java-platform'\n  id 'ru.vyarus.java-lib'\n}\n\nrepositories { mavenLocal(); mavenCentral() }\ndependencies {\n  api platform('ru.vyarus.guicey:guicey-bom:5.2.0-1')\n  constraints {\n    api 'org.webjars:webjars-locator:0.40'\n  }\n  // add subprojects to published BOM\n  project.subprojects.each { api it }\n}\n```\n\nJava-lib plugin would automatically activate dependencies declaration (`constraints` block).\n\nI propose to mix dependencies and modules into single BOM declaration, but you can always split\ndependencies management and modules BOM by declaring two platforms in two different modules.\n\nIf you use `java-platform` in the root project, then you might want to change name of published artifact\n(by default it would be root project name in this case). To change it use:\n\n```groovy\njavaLib {\n  bom {\n    artifactId = 'some-bom'\n    description = 'overridden description'\n  }\n}\n```\n\n### Publication\n\n[maven-publish](https://docs.gradle.org/current/userguide/publishing_maven.html) plugin used for publication.\n\nBy default, plugin configures `maven` publication with javadoc or (and) groovydoc and sources jars for `java` \n(`groovy` or `java-library`) plugins and `bom` publication for `java-platform` plugin. \n\nUse `install` task to deploy everything into local maven repository.\n\n```bash\n$ gradlew install\n``` \n\nIf you don't want to publish everything (jar, sources, javadoc) then you can:\n\n```groovy\njavaLib {\n  withtouSources()\n  withoutJavadoc()\n}\n```\n\nOR override list of publishing artifacts:\n\n```groovy\npublishing.publications.maven.artifacts = [jar, javadocJar]\n```\n\nNOTE that for maven central publication sources and javadocs are required\n\nTo ADD artifacts for publication, configure them directly for publication:\n\n```groovy\npublishing {\n    publications.maven {\n        artifact buildDelivery { archiveClassifier.set('zip') }\n    }\n}\n```\n\nHere the result of `buildDelivery` task (of type `Zip`) **added** to `maven` publication with `zip` classifier.\n\n#### Gradle metadata\n\nSince gradle 6, gradle would always publish its [metadata](https://docs.gradle.org/current/userguide/publishing_gradle_module_metadata.html):\n\n```\nGradle Module Metadata is a unique format aimed at improving dependency resolution by making it multi-platform and variant-aware.\n```\n\nEssentially, it's an additional `.module` file containing json representation of dependencies.\nThis is really necessary only when advanced gradle features used (constraints (not in platform), variants).\n\nBut this would mean that gradle and maven projects would use *different* dependencies\nafter publication: maven use pom, gradle would load .module file with additional dependencies info.\n\nIt would be more honest to publish only pom (especially for public projects) and disable metadata publishing:\n\n```groovy\njavaLib {\n  withoutMavenMetadata()\n}\n```\n\nAlso note, that maven central could complain about metadata file (if published).\n\n#### Publish to repository \n \nYou must configure repository for actual publication [repository](https://docs.gradle.org/current/userguide/publishing_maven.html#publishing_maven:repositories) must be configured:\n\n```groovy\npublishing {\n    repositories {\n        maven {\n            // change to point to your repo, e.g. http://my.org/repo\n            url \"$buildDir/repo\"\n        }\n    }\n}\n```\n\nThen [publish task](https://docs.gradle.org/current/userguide/publishing_maven.html#publishing_maven:publishing) may be used to perform publish. \n\n#### Publish to maven-central\n\nFor maven-central publication use [nexus publish plugin](https://github.com/gradle-nexus/publish-plugin)\nwhich automates full maven central release cycle. \n\n```groovy\nplugins {\n  ...\n  id 'io.github.gradle-nexus.publish-plugin' version '1.1.0'\n}\n\nnexusPublishing {\n  repositories {\n    sonatype {\n      username = findProperty('sonatypeUser')\n      password = findProperty('sonatypePassword')\n    }\n  }\n}\n```\n\nFor release, you would need to call two tasks: `publishToSonatype`, `closeAndReleaseSonatypeStagingRepository`\n\nYou'll need to configure `sonatypeUser` and `sonatypePassword` properties in global gradle file:\n`~/.gradle/gradle.properties`\n\nIMPORTANT artifacts must be [signed](#signing)!\n\n#### Gradle plugin\n\nGradle plugin project will have [java-gradle-plugin](https://docs.gradle.org/current/userguide/java_gradle_plugin.html), \nwhich declares its own maven publication `pluginMaven` (with main jar as artifact). Also, plugin creates one more \npublication per declared plugin to publish [plugin marker artifact](https://docs.gradle.org/current/userguide/plugins.html#sec:plugin_markers)\n(required by gradle plugins dsl).\n\nJava-lib plugin will still create separate publication `maven` and you should use it for publishing with bintray \n(same way as for usual library)\n\n##### Publishing to gradle plugin repository\n\nFor publishing in gradle plugin repository you will use [com.gradle.plugin-publish](https://plugins.gradle.org/docs/publish-plugin)\nplugin.\n\n**IMPORTANT**: plugin-publish 1.x is supported for gradle 7.6 and above, for lower gradle use 0.x\n\nUse `maven` publication for publishing into maven central or other repo (optional). Plugin-publish\nwill use it's `plugin-maven` publication for plugins portal publication. Both publications\nwould contain the same artifacts.\n\nExample for publishing in maven central and plugin portal (gradle 7.6 or above):\n\n```groovy\nplugins {\n  id 'com.gradle.plugin-publish' version '1.2.1'\n  id 'java-gradle-plugin'\n  id 'ru.vyarus.java-lib' version '3.0.0'\n}\n\nrepositories { mavenLocal(); mavenCentral(); gradlePluginPortal() }\n\ngroup = 'com.foo'\ndescription = 'Short description'\n\ngradlePlugin {\n  plugins {\n    myPlugin {\n      id = 'com.foo.plugin'\n      displayName = project.description\n      description = 'Long description'\n      tags.set(['something'])\n      implementationClass = 'com.foo.MyPlugin'\n    }\n  }\n}\n```\n\nHere `publishMavenPublicationToMavenRepository` would publish to repository and `publishPlugins` publish into plugins portal.\n\nAssuming custom `maven` (name!) repository is configured:\n\n```groovy\npublishing {\n  repositories { maven { url \"http://some.repo/\"} }\n}\n```\n\n##### Publishing only to custom repo\n\nThis is in-house plugin case, when plugin is published only into corporate repository.\n\nThe simplest solution is to disable `pluginMaven` publication tasks (but marker artifact publications should remain!)\nand publish only remaining `maven` publication:\n\n```groovy\ntasks.withType(AbstractPublishToMaven) { Task task -\u003e\n    if (task.name.startsWith(\"publishPluginMaven\")) {\n        task.enabled(false)\n    }\n}\n```    \n\nThis will disable: `publishPluginMavenPublicationToMavenLocal` and `publishPluginMavenPublicationToMavenRepository`\n\nAnd you can simply use `publish` task to trigger all required publications without duplicates.\n\nThe same way, `install` will install all required artifacts locally (including markers) and so it is possible\nto use plugins from local maven repository too (with plugin syntax):\n\nadd to settings.gradle:\n\n```groovy\npluginManagement {\n    repositories {\n        mavenLocal()\n        gradlePluginPortal()\n    }\n}\n```\n\n### Encodings\n\nUTF-8 applied to:\n\n* (all `CompileJava` tasks).options.encoding \n* (all `CompileGrovy` tasks).options.encoding\n* (all `Javadoc`).options.\\[encoding, charSet, docEncoding]\n* (all `Test`).systemProperty 'file.encoding'\n\nNote that groovydoc task does not have encoding configuration, but it should use UTF-8 by defautl. \n\nFor tests, encoding is important (especially on windows) because test forked process will not inherit root gradle encoding configuration. \n\n### Tasks \n\nNOTE: for gradle 7.6 and above [native javadoc and sources registration used](https://docs.gradle.org/current/userguide/java_plugin.html#packaging)\n\n- `sourcesJar`  \n- `javadocJar` \n- `openDependencyReport` if `project-report` plugin active - opens html dependency report in browser\n\n`install` task added to simplify publication to local maven repository: this is simply shortcut for\ngradle's [publishToMavenLocal](https://docs.gradle.org/current/userguide/publishing_maven.html#publishing_maven:tasks) task\n(simply shorter to type and more common name after maven).  \n\n### Main Jar\n\nPlugin applies default manifest properties:\n\n```groovy\n'Implementation-Title': project.description ?: project.name,\n'Implementation-Version': project.version,\n'Built-By': System.getProperty('user.name'),\n'Built-Date': new Date(),\n'Built-JDK': System.getProperty('java.version'),\n'Built-Gradle': gradle.gradleVersion,\n'Target-JDK': project.targetCompatibility\n```\n\nYou can override it:\n\n```groovy\njar {\n    manifest {\n        attributes 'Implementation-Title': 'My Custom value',\n            'Built-By': 'Me'\n    }\n}\n```\n\nFor all not specified properties default values will be used.\n\nPlugin will include additional files inside jar (like maven do) into `META-INF/maven/group/artifact/`\n\n* pom.xml\n* pom.properties\n\npom.properties contains:\n\n* version\n* groupId\n* artifactId\n\n### Signing\n\nPlugin will configure signing automatically for *configured publications*: `maven` and `bom` \n(note that in case of gradle plugin, gradle use its own publication for portal publication\nand it would not be signed (no need)).\n\nYou only need to apply [signing](https://docs.gradle.org/current/userguide/signing_plugin.html) plugin:\n\n```groovy\nplugins {\n  id 'java'\n  id 'signing'\n  id 'ru.vyarus.java-lib'\n}\n```\n\nNo additional configuration required, except properties in the global gradle config `~/.gradle/gradle.properties`:\n\n```properties\nsigning.keyId = 78065050\nsigning.password =\nsigning.secretKeyRingFile = /path/to/certs.gpg\n```\n\nIMPORTANT: password property (empty) required even if no password used!\n\nNote that project build will not complain while building snapshot versions\n(version ending with `-SNAPSHOT`) - signing task would be simply ignored.\nBut, on release gradle would fail if signing not configured properly.\n\n#### Signing certificate\n\nCertificate generation described in many articles around the web, for example, sonatype \n[gpg guide](https://central.sonatype.org/publish/requirements/gpg/).\n\nI will just show required commands for generation and obtaining keyring file:\n\nCertificate generation:\n\n```\ngpg --gen-key\n``` \n\n(if you want, you can leave passphrase blank - just hit enter several times)\n\nAlternatively, `gpg --full-gen-key` may be used to set exact algorithm and expiration (by default generated key would expire in few years)\n\nList keys:\n\n```\ngpg --list-keys\ngpg --list-secret-keys\n```\n\nYou can always edit key if required (for example change expiration):\n\n```\ngpg --edit-key (key id)\ngpg\u003e key 1\ngpg\u003e expire\n(follow prompts)\ngpg\u003e save\n```\n\nCreate keyring file:\n\n```\ngpg --export-secret-keys (key id) \u003e cert.gpg\n```\n\nPut `cert.gpg` somewhere and set full path to it in `signing.secretKeyRingFile`\n\nYou also need short key id:\n\n```\ngpg --list-secret-keys --keyid-format SHORT\n\nExample output:\n  sec   rsa3072/78065050 2021-06-06 [SC]\n```\n\nHere `78065050` is your keyid which should be set as `signing.keyId`\n\nIf you set passphrase, set it in `signing.password`, otherwise leave it blank \n\nIMPORTANT: for maven central, you'll need to register your public key with\n\n```\ngpg --keyserver keyserver.ubuntu.com --send-keys (short key id)\n```\n\nThat's all.\n\n### Dependency report\n\nWhen [project-report](https://docs.gradle.org/current/userguide/project_report_plugin.html) plugin active,\n`openDependencyReport` task created. \n\nThis is pure utility task: it calls `htmlDependencyReport` and opens it directly\nin the browser (directly on page with dependencies, instead of index).\n\nThis simply faster: manual `htmlDependencyReport` requires several clicks to open required report. \n\n### Maven-like multi-module project\n\nHere is an example of how plugin could be used in multi-module project to apply\nmaven configuration style: root project manage all dependency versions.\n\n```groovy\nplugins {\n    id 'jacoco'\n    id 'java-platform'\n    id 'ru.vyarus.java-lib'\n}\n\ndescription = 'Maven-like project'\n\n// dependency versions management\ndependencies {\n    api platform(\"ru.vyarus:dropwizard-guicey:$guicey\")\n    constraints {\n        api 'com.h2database:h2:1.4.200'\n\n        // add subprojects to BOM\n        project.subprojects.each { api it }\n    }\n}\n\njavaLib {\n    aggregateReports()\n    // publish root BOM as custom artifact\n    bom {\n        artifactId = 'sample-bom'\n        description = 'Sample project BOM'\n    }\n  \n    // OR disable BOM publication\n    // withoutPublication()\n}\n\n// maven publication related configuration applied to all projects\nallprojects {\n    //apply plugin: 'project-report'\n    //apply plugin: 'signing'\n\n    repositories { mavenCentral(); mavenLocal() }\n\n    group = 'com.test'\n  \n    // such delay is required because java-lib (and java) plugin would be applied only\n    // in the subprojects section and so this would configure root project configuration\n    // without delay\n    plugins.withId('java') {\n        maven.pom {\n            licenses {\n                license {\n                    name = \"The MIT License\"\n                    url = \"http://www.opensource.org/licenses/MIT\"\n                    distribution = 'repo'\n                }\n            }\n            scm {\n                url = 'https://github.com/me/my-repo.git'\n                connection = 'scm:git@github.com:me/my-repo.git'\n                developerConnection = 'scm:git@github.com:me/my-repo.git'\n            }\n            //...\n        }\n    }  \n\n    javaLib.withoutGradleMetadata()\n}\n\n// all sub-modules are normal java modules, using root BOM (like maven)\nsubprojects {\n    apply plugin: 'groovy'\n    apply plugin: 'jacoco'\n    apply plugin: 'ru.vyarus.java-lib'\n\n    sourceCompatibility = 1.8\n\n    // common dependencies for all modules\n    dependencies {\n        implementation platform(project(':'))\n\n        compileOnly 'com.github.spotbugs:spotbugs-annotations:4.2.3'\n        implementation 'ru.vyarus:dropwizard-guicey'\n\n        testImplementation 'org.spockframework:spock-core'\n        testImplementation 'io.dropwizard:dropwizard-testing'\n    }\n\n    javaLib {\n        // java 9 auto module name\n        autoModuleName = \"com.sample.module\"\n    }\n  \n    maven {\n        // use only direct dependencies in the generated pom, removing BOM\n        removeDependencyManagement()\n    }\n}\n```\n\nHere required dependency versions declared in the root project using gradle platform.\nPlatform published as BOM with custom artifact name (dual BOM: both project modules and dependencies).\n\nSub-projects are java modules which use platform declared in the root project for dependency management.\n`maven.removeDependencyManagement()` prevents \"leaking\" platform into module poms\n(generated poms would contain just required dependencies with resolved versions)\n\n`groovy` plugin used just as an example (used for spock tests, main sources might be java-only): it could be `java` or `java-library` plugin.\n\nThe complete multi-module project example could be generated with [java-library generator](https://github.com/xvik/generator-lib-java).\n\n* [dropwizard-guicey-ext](https://github.com/xvik/dropwizard-guicey-ext) - multi-module project with (published) bom\n* [yaml-updater](https://github.com/xvik/yaml-updater) - simple multi-module without bom (simple case)\n\n### APPENDIX: boilerplate plugin removes\n\nSection briefly shows what plugin configures so if plugin defaults didn't fit your needs, you can\neasily reproduce parts of it in your custom build. \n\n#### Java module boilerplate\n\n```groovy\nplugins { id 'java' }\n\napply plugin: 'ru.vyarus.pom'\n\njar {    \n    manifest {\n        attributes 'Implementation-Title': project.description ?: project.name,\n                'Implementation-Version': project.version,\n                'Built-By': System.getProperty('user.name'),\n                'Built-Date': new Date(),\n                'Built-JDK': System.getProperty('java.version'),\n                'Built-Gradle': gradle.gradleVersion,\n                'Target-JDK': project.targetCompatibility\n    }\n}\n\njava {\n    withJavadocJar()\n    withSourcesJar()\n}        \n\ntask generatePomPropertiesFile {\n    inputs.properties ([\n            'version': \"${ -\u003e project.version }\",\n            'groupId': \"${ -\u003e project.group }\",\n            'artifactId': \"${ -\u003e project.name }\"\n    ])\n    outputs.file \"$project.buildDir/generatePomPropertiesFile/pom.properties\"\n    doLast {\n        File file = outputs.files.singleFile\n        file.parentFile.mkdirs()\n        file \u003c\u003c inputs.properties.collect{ key, value -\u003e \"$key: $value\" }.join('\\n')\n    }\n}\n\nmodel {\n    tasks.jar {\n        into(\"META-INF/maven/$project.group/$project.name\") {\n            from generatePomFileForMavenPublication\n            rename \".*.xml\", \"pom.xml\"\n            from generatePomPropertiesFile\n        }\n    }\n}\n\ntasks.withType(JavaCompile).configureEach {\n    it.options.encoding = StandardCharsets.UTF_8\n}\n\ntasks.withType(GroovyCompile).configureEach {\n    it.options.encoding = StandardCharsets.UTF_8\n}\n\ntasks.withType(Test).configureEach {\n   it.systemProperty JvmOptions.FILE_ENCODING_KEY, StandardCharsets.UTF_8\n}\n\ntasks.withType(Javadoc).configureEach {\n  it.with {\n    options.encoding = StandardCharsets.UTF_8\n    // StandardJavadocDocletOptions\n    options.charSet = StandardCharsets.UTF_8\n    options.docEncoding = StandardCharsets.UTF_8\n  }\n}\n\njar.manifest {\n  attributes 'Automatic-Module-Name': 'module-name'\n}  \n\npublishing.publications {\n    maven(MavenPublication) {\n        from components.java\n    }\n}\n\ntask.jacocoTestReport.xml.required.set(true)\n\ntasks.register('install') {\n    dependsOn: publishToMavenLocal \n    group: 'publishing'\n    doLast {\n        logger.warn \"INSTALLED $project.group:$project.name:$project.version\"\n    }\n}\n```\n\n#### Java platform boilerplate\n\n```groovy\nplugins { id 'java-platform' }\n\napply plugin: 'ru.vyarus.pom'\n\njavaPlatform.allowDependencies()\n\nmaven.pom {\n  name = 'custom-name'                // if differs from project name\n  description = 'custom description'\n}\n\npublishing.publications {\n  bom(MavenPublication) {\n    from components.javaPlatform\n    artifactId = 'custom-name'      // if differs from project name\n  }\n}\n\njacocoTestReport.reports.xml.required.set(true)\n\ntasks.register('install') {\n  dependsOn: publishToMavenLocal\n  group: 'publishing'\n  doLast {\n    logger.warn \"INSTALLED $project.group:custom-name:$project.version\"\n  }\n}\n```\n\n#### Reports aggregation boilerplate\n\n```groovy\ntask test (type: TestReport, description: 'Generates aggregated test report') {\n    group = 'verification'\n    destinationDir = project.file(\"${project.buildDir}/reports/tests/test\")\n    reportOn project.subprojects.findAll { it.plugins.hasPlugin(JavaPlugin) }.test\n}\n\ndef projectsWithCoverage = project.subprojects.findAll { it.plugins.hasPlugin(JacocoPlugin) }\n\ntask jacocoTestReport (type: JacocoReport, description: 'Generates aggregated jacoco coverage report') {\n    dependsOn 'test'\n    group = 'verification'\n    executionData project.files(projectsWithCoverage\n            .collect { it.file(\"${it.buildDir}/jacoco/test.exec\") })\n            .filter { it.exists() }\n    sourceDirectories.from = project.files(projectsWithCoverage.sourceSets.main.allSource.srcDirs)\n    classDirectories.from = project.files(projectsWithCoverage.sourceSets.main.output)\n    reports.xml.destination = project.file(\"$project.buildDir/reports/jacoco/test/jacocoTestReport.xml\")\n    reports.xml.required.set(true)\n    reports.html.destination = project.file(\"$project.buildDir/reports/jacoco/test/html/\")\n}\n\nhtmlDependencyReport.projects = project.allprojects\n```\n\n#### Utility boilerplate\n\nSigning:\n\n```groovy\nsigning {\n  sign publishing.publications.maven    // or bom\n  required = { !project.version.toString().endsWith('SNAPSHOT') }\n}\n```\n\nGradle metadata disabling\n\n```groovy\ntasks.withType(GenerateModuleMetadata).configureEach {\n    enabled = false\n}\n```\n\nOpen report:\n\n```groovy\ntask openDependencyReport(description: 'Opens gradle htmlDependencyReport in browser', group: 'help') {\n  dependsOn 'htmlDependencyReport'\n  doLast {\n      java.awt.Desktop.desktop.open(file(\"build/reports/project/dependencies/root.${project.name}.html))\n  }\n}\n```\n\n### Might also like\n\n* [quality-plugin](https://github.com/xvik/gradle-quality-plugin) - java and groovy source quality checks\n* [github-info-plugin](https://github.com/xvik/gradle-github-info-plugin) - pre-configure common plugins with github related info\n* [animalsniffer-plugin](https://github.com/xvik/gradle-animalsniffer-plugin) - java compatibility checks\n* [mkdocs-plugin](https://github.com/xvik/gradle-mkdocs-plugin) - project documentation generator \n* [java-library generator](https://github.com/xvik/generator-lib-java) - java library project generator\n\n---\n[![gradle plugin generator](http://img.shields.io/badge/Powered%20by-%20Gradle%20plugin%20generator-green.svg?style=flat-square)](https://github.com/xvik/generator-gradle-plugin)\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fxvik%2Fgradle-java-lib-plugin","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fxvik%2Fgradle-java-lib-plugin","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fxvik%2Fgradle-java-lib-plugin/lists"}