diff --git a/.claude/skills/intellij-plugin-development/SKILL.md b/.claude/skills/intellij-plugin-development/SKILL.md new file mode 100644 index 0000000..f1c5161 --- /dev/null +++ b/.claude/skills/intellij-plugin-development/SKILL.md @@ -0,0 +1,47 @@ +--- +name: intellij-plugin-development +description: IntelliJ plugin development reference when working on extension points, decompiling bundled plugin JARs, finding API usage examples, navigating IntelliJ SDK, or investigating how other plugins implement a feature. +--- + +# IntelliJ Plugin Development + +Quick reference for tools, APIs, and resources used when developing or investigating IntelliJ/PhpStorm plugins in this project. + +--- + +## SDK & Documentation + +- **SDK Docs:** https://plugins.jetbrains.com/docs/intellij/ +- **Extension Point List:** https://plugins.jetbrains.com/docs/intellij/extension-point-list.html +- **IntelliJ Community Source:** https://github.com/JetBrains/intellij-community +- **Plugin Template:** https://github.com/JetBrains/intellij-platform-plugin-template + +--- + +## Skills in this folder + +| File | Purpose | +|---|---| +| `references/extension-point-explorer.md` | Find plugins by extension point; search open-source implementations; download plugins for decompilation | +| `references/decompilation.md` | Decompile plugin JARs with Vineflower; locate bundled JARs in Gradle cache; download ZIPs from Marketplace | + +--- + +## Decompilation (quick reference) + +Always use **Vineflower** — not IntelliJ's bundled Fernflower. A local copy is at `decompiled/vineflower.jar`. + +```bash +java -jar decompiled/vineflower.jar input.jar output-src/ +``` + +See [`references/decompilation.md`](./references/decompilation.md) for full usage, bundled JAR paths, and Marketplace ZIP downloads. + +--- + +## Extension Point Explorer (quick reference) + +Use the JetBrains Marketplace API to find plugins implementing a given extension point, get GitHub source search URLs or download plugin releases from the marketplace for decompilation. + +See [`references/extension-point-explorer.md`](./references/extension-point-explorer.md) for step-by-step instructions. + diff --git a/.claude/skills/intellij-plugin-development/references/decompilation.md b/.claude/skills/intellij-plugin-development/references/decompilation.md new file mode 100644 index 0000000..c8bc6ff --- /dev/null +++ b/.claude/skills/intellij-plugin-development/references/decompilation.md @@ -0,0 +1,64 @@ +# Decompilation + +Guide for decompiling IntelliJ plugin JARs to inspect features and implementation details. + +--- + +## Vineflower (recommended) + +Vineflower produces significantly better output than IntelliJ's bundled Fernflower. Always prefer it for decompiling plugin JARs. + +- **GitHub:** https://github.com/Vineflower/vineflower +- **Download:** https://repo1.maven.org/maven2/org/vineflower/vineflower/1.11.2/vineflower-1.11.2.jar +- **Local copy in this project:** `decompiled/vineflower.jar` + +```bash +# Decompile a single JAR into a source directory +java -jar decompiled/vineflower.jar input.jar output-src/ + +# Decompile all JARs in a directory +java -jar decompiled/vineflower.jar input-dir/ output-src/ +``` + +--- + +## Bundled plugin JARs (IntelliJ/PhpStorm) + +Gradle downloads plugin dependencies into the local cache. Typical path: + +``` +~/.gradle/caches//transforms/*/transformed/-//lib/.jar +``` + +Examples: +```bash +# Twig plugin +~/.gradle/caches/9.3.0/transforms/*/transformed/com.jetbrains.twig-253.28294.322/twig/lib/twig.jar + +# PHP plugin +~/.gradle/caches/9.3.0/transforms/*/transformed/com.jetbrains.php-253.*/php/lib/php.jar +``` + +--- + +## Downloading a plugin JAR from the Marketplace + +Use the JetBrains Marketplace API to fetch the latest release ZIP for any plugin ID (see `extension-point-explorer.md` for how to find plugin IDs): + +```bash +PLUGIN_ID="7219" + +# Get the ZIP download path +curl -s "https://plugins.jetbrains.com/api/plugins/${PLUGIN_ID}/updates?size=1" \ + | jq -r '"https://plugins.jetbrains.com/files/" + .[0].file' + +# Download it directly +FILE=$(curl -s "https://plugins.jetbrains.com/api/plugins/${PLUGIN_ID}/updates?size=1" | jq -r '.[0].file') +curl -L -o plugin.zip "https://plugins.jetbrains.com/files/${FILE}" +unzip plugin.zip -d plugin-src/ +``` + +Then decompile the extracted JAR: +```bash +java -jar decompiled/vineflower.jar plugin-src/lib/plugin.jar output-src/ +``` diff --git a/.claude/skills/intellij-plugin-development/references/extension-point-explorer.md b/.claude/skills/intellij-plugin-development/references/extension-point-explorer.md new file mode 100644 index 0000000..4acbd6e --- /dev/null +++ b/.claude/skills/intellij-plugin-development/references/extension-point-explorer.md @@ -0,0 +1,118 @@ +# IntelliJ Extension Point Explorer + +Use this skill to find plugins that implement a given IntelliJ extension point and to get GitHub source code search URLs for usage examples. + +This skill also covers **downloading any plugin for decompilation and feature investigation** — see Section 3. + +> **Important:** Extension point names are **case-sensitive** (e.g., `com.intellij.psi.referenceContributor` ≠ `com.intellij.psi.ReferenceContributor`). Use the exact name as declared in `plugin.xml`. + +--- + +## 1. Search for extension points by keyword + +Before querying for plugins, find the **exact extension point name** by searching the JetBrains Marketplace extension point registry. Search is **case-insensitive** (the filtering is done client-side with `grep -i`), but the name you pass to Step 1 must be **exact and case-sensitive**. + +```bash +# Partial search — find all extension points containing a keyword +KEYWORD="completion" + +curl -s "https://plugins.jetbrains.com/api/extension-points" \ + | jq -r '.[].implementationName' \ + | grep -i "$KEYWORD" \ + | sort +``` + +Examples: +- `KEYWORD="contributor"` → lists all `*contributor*` extension points +- `KEYWORD="completion.contributor"` → narrows to completion contributors +- `KEYWORD="inspection"` → lists all inspection-related extension points + +Once you have the exact name (e.g., `com.intellij.completion.contributor`), use it in Step 2. + +--- + +## 2. Find plugins implementing an extension point + +Query the JetBrains Plugin Repository GraphQL API to find open-source plugins that use a specific extension point: + +```bash +EXTENSION_POINT="com.intellij.psi.referenceContributor" + +curl -s -X POST "https://plugins.jetbrains.com/api/search/graphql" \ + -H "Content-Type: application/json" \ + -d "{\"query\":\"{ plugins(search: { max: 24, offset: 0, filters: [{ field: \\\"fields.extensionPoints\\\", value: \\\"${EXTENSION_POINT}\\\" }, { field: \\\"hasSource\\\", value: \\\"true\\\" }, { field: \\\"family\\\", value: \\\"intellij\\\" }], sortBy: DOWNLOADS }) { total, plugins { id, name, downloads, sourceCodeUrl, lastUpdateDate, organization { id, verified } } } }\"}" \ + | jq -r --arg ep "$EXTENSION_POINT" ' + .data.plugins | + "Total plugins found: \(.total)\n", + (.plugins[] | select(.sourceCodeUrl != null and .sourceCodeUrl != "") | + "Plugin: \(.name)", + "ID: \(.id)", + "Downloads: \(.downloads)", + "Source: \(.sourceCodeUrl)", + "Updated: \(.lastUpdateDate)", + "Verified: \(.organization.verified // false)", + "Marketplace: https://plugins.jetbrains.com/plugin/\(.id)", + "Search: \("https://github.com/search?q=" + ("repo:" + (.sourceCodeUrl | ltrimstr("https://github.com/") | rtrimstr("/")) + " " + $ep | @uri) + "&type=code")", + "---" + ) + ' +``` + +## 3. Download a plugin for decompilation and feature investigation + +> **Note:** This section is **not** limited to extension point research. Use it any time you want to download a plugin JAR/ZIP for decompilation, reverse engineering, or feature investigation — regardless of how you found the plugin ID. + +The plugin ID can come from: +- **Step 2** results (`ID: 7219`) +- A Marketplace URL: `https://plugins.jetbrains.com/plugin/` + +The `sourceCodeUrl` (GitHub URL) from Step 2 gives you two options: +- **Search the repo** for usage examples → use the `Search:` URL from Step 2 output, or browse `https://github.com//` +- **Download the latest release** for decompilation → use the Marketplace API below to get the direct ZIP URL + +Given a plugin ID, fetch its metadata and the direct ZIP download URL of the latest release: + +```bash +PLUGIN_ID="7219" + +# Plugin metadata +curl -s "https://plugins.jetbrains.com/api/plugins/${PLUGIN_ID}" \ + | jq '{ + id: .id, + name: .name, + xmlId: .xmlId, + downloads: .downloads, + source: .urls.sourceCodeUrl, + marketplace: ("https://plugins.jetbrains.com/plugin/" + (.id | tostring)) + }' + +# Latest release — includes direct ZIP download URL +curl -s "https://plugins.jetbrains.com/api/plugins/${PLUGIN_ID}/updates?size=1" \ + | jq '.[0] | { + version: .version, + date: (.cdate | tonumber / 1000 | strftime("%Y-%m-%d")), + downloads: .downloads, + size_kb: (.size / 1024 | floor), + channel: (if .channel == "" then "stable" else .channel end), + download_url: ("https://plugins.jetbrains.com/files/" + .file), + notes: (.notes | gsub("<[^>]+>"; "") | gsub(">"; ">") | gsub("<"; "<") | gsub("&"; "&") | split("\n") | map(select(length > 0)) | .[:5] | join("\n")) + }' +``` + +Once you have the ZIP URL, download and decompile with **vineflower** (see [`references.md`](./references.md)): +```bash +curl -L -o plugin.zip "https://plugins.jetbrains.com/files/7219/974671/Symfony_Plugin-2026.1.289.zip" +unzip plugin.zip -d plugin-extracted/ +java -jar decompiled/vineflower.jar plugin-extracted/lib/plugin.jar decompiled-src/ +``` + +--- + +## Notes + +- **Case sensitivity:** `com.intellij.completion.contributor` ≠ `com.intellij.CompletionContributor` — always verify the exact name in `plugin.xml` or IntelliJ SDK docs. +- The API returns max 24 results per request; use `offset` to paginate. +- `sortBy` options: `DOWNLOADS`, `UPDATE_DATE`, `RATING`. +- Only plugins with `hasSource: true` and a non-empty `sourceCodeUrl` are useful for code examples. +- `jq` and `curl` are required; `jq` must support `@uri` (version ≥ 1.6). +- For decompilation tooling and API references, see [`references.md`](./references.md). diff --git a/.gitignore b/.gitignore index f21ecdd..8a48f5f 100644 --- a/.gitignore +++ b/.gitignore @@ -3,4 +3,8 @@ out/ /php-annotation.jar /build /.gradle -.intellijPlatform \ No newline at end of file +.intellijPlatform +/decompiled +/.junie +*.hprof +.mcp.json \ No newline at end of file diff --git a/AGENTS.md b/AGENTS.md new file mode 100644 index 0000000..74dfd96 --- /dev/null +++ b/AGENTS.md @@ -0,0 +1,52 @@ +# CLAUDE.md + +This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. + +## Project Overview + +This is an IntelliJ IDEA/PhpStorm plugin that provides PHP annotation and PHP 8 Attribute support. The plugin extends the IDE to recognize annotation classes marked with `@Annotation`, provides code completion, navigation, inspections, and integrates with Doctrine ORM and Symfony frameworks. + +**Plugin ID**: `de.espend.idea.php.annotation` + +## Build Commands + +### Build the plugin +```bash +./gradlew buildPlugin +``` +The plugin ZIP will be in `build/distributions/`. + +### Running Tests + +```bash +# Run all tests +./gradlew test + +# Run a specific test class +./gradlew test --tests "fr.adrienbrault.idea.symfony2plugin.tests.dic.SymfonyContainerTypeProviderTest" + +# Run tests matching a pattern +./gradlew test --tests "*ContainerTest" +``` + +## Architecture + +- Tests extend `AnnotationLightCodeInsightFixtureTestCase` which provides a test fixture framework. + +Test data files are in `src/test/java/de/espend/idea/php/annotation/tests/fixtures/`. + + +## Decompiler Tools + +For analyzing bundled plugins like Twig and PHP you MUST use **vineflower** and NOT **Fernflower** from IntelliJ (less quality): + +**vineflower** + +- **GitHub:** https://github.com/Vineflower/vineflower +- **Download:** https://repo1.maven.org/maven2/org/vineflower/vineflower/1.11.2/vineflower-1.11.2.jar +- **Local copy:** `decompiled/vineflower.jar` +- **Usage:** `java -jar vineflower.jar input.jar output/` + +**Bundled Plugin JARs (for decompilation):** +- **Location:** `~/.gradle/caches/[gradle-version]/transforms/*/transformed/com.jetbrains.[plugin]-[intellij-version]/[plugin]/lib/[plugin].jar` +- **Example:** `~/.gradle/caches/9.3.0/transforms/*/transformed/com.jetbrains.twig-253.28294.322/twig/lib/twig.jar` diff --git a/CLAUDE.md b/CLAUDE.md index 43176c9..8d565ad 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -2,167 +2,6 @@ This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. -## Project Overview +### Project Overview -This is an IntelliJ IDEA/PhpStorm plugin that provides PHP annotation and PHP 8 Attribute support. The plugin extends the IDE to recognize annotation classes marked with `@Annotation`, provides code completion, navigation, inspections, and integrates with Doctrine ORM and Symfony frameworks. - -**Plugin ID**: `de.espend.idea.php.annotation` - -## Build Commands - -### Build the plugin -```bash -./gradlew buildPlugin -``` -The plugin ZIP will be in `build/distributions/`. - -### Run tests -```bash -./gradlew test -``` - -### Run a single test class -```bash -./gradlew test --tests "de.espend.idea.php.annotation.tests.AnnotationStubIndexTest" -``` - -### Run a single test method -```bash -./gradlew test --tests "de.espend.idea.php.annotation.tests.AnnotationStubIndexTest.testThatAnnotationClassIsInIndex" -``` - -### Run the plugin in a test IDE instance -```bash -./gradlew runIde -``` - -### Verify plugin compatibility -```bash -./gradlew verifyPlugin -``` - -### Clean build -```bash -./gradlew clean buildPlugin -``` - -## Architecture - -### Extension Point System - -The plugin's core architecture is based on extension points that allow both internal components and external plugins (like Symfony Support or PHP Toolbox) to extend functionality. - -**Key extension point interfaces** (in `src/main/java/de/espend/idea/php/annotation/extension/`): - -- **PhpAnnotationCompletionProvider**: Provides code completion for annotation property values -- **PhpAnnotationReferenceProvider**: Provides references and navigation for annotation elements -- **PhpAnnotationDocTagGotoHandler**: Handles "Go to Declaration" for annotation tags -- **PhpAnnotationDocTagAnnotator**: Provides custom highlighting/error annotations for doc tags -- **PhpAnnotationGlobalNamespacesLoader**: Loads global annotation namespace mappings -- **PhpAnnotationVirtualProperties**: Provides virtual properties for annotation classes -- **PhpAnnotationUseAlias**: Maps custom class aliases (e.g., "ORM" => "Doctrine\\ORM\\Mapping") - -Extension points are registered in `src/main/resources/META-INF/plugin.xml` and can be used by other plugins. - -### Indexing System - -The plugin uses two main file-based indices for fast lookup: - -- **AnnotationStubIndex**: Indexes all PHP classes marked with `@Annotation` in their doc block -- **AnnotationUsageIndex**: Indexes where annotations are used in the codebase - -These indices power the navigation features (find usages, line markers) and are updated automatically when files change. - -### Module Organization - -- **annotator/**: Provides inline error highlighting and warnings -- **completion/**: Code completion contributors and providers -- **dict/**: Data transfer objects and dictionary classes -- **doctrine/**: Doctrine ORM-specific features (property generators, repository class handling, column type support) -- **extension/**: Extension point interfaces and parameters -- **inspection/**: Code inspections (missing imports, deprecated usage, etc.) -- **navigation/**: Navigation handlers and line marker providers -- **pattern/**: PSI pattern matching for identifying annotation contexts -- **reference/**: Reference contributors for navigation and "Find Usages" -- **symfony/**: Symfony-specific annotation support -- **toolbox/**: PHP Toolbox integration -- **ui/**: Settings forms and configuration UI -- **util/**: Utility classes, particularly `AnnotationUtil` which contains core logic for annotation detection and processing - -### Dual Support: DocBlock Annotations and PHP 8 Attributes - -The plugin supports both: -- **DocBlock annotations**: `/** @Route("/path") */` -- **PHP 8 Attributes**: `#[Route('/path')]` - -Extension points work transparently with both formats, allowing feature implementations to support both simultaneously. - -## Key Concepts - -### Annotation Detection - -Classes are recognized as annotation classes if they have `@Annotation` in their doc block: -```php -/** - * @Annotation - * @Target("METHOD", "CLASS") - */ -class Route { - public $path; -} -``` - -### Target Filtering - -The `@Target` annotation restricts where annotations can be used (METHOD, CLASS, PROPERTY, ALL). The plugin uses this for completion filtering. - -### Property Type Detection - -Annotation properties support type hints via doc comments: -- Simple types: `@var string`, `@var bool` -- Arrays: `@var array` -- Enums: `@Enum({"GET", "POST", "PUT"})` -- Mixed: `@var mixed|string|bool` - -### Use Alias System - -The plugin supports configurable namespace aliases (Settings > PHP > Annotations / Attributes > Use Alias): -- Maps short names to FQCNs: `ORM` => `Doctrine\ORM\Mapping` -- Auto-import suggestions use these mappings -- External plugins can provide their own mappings via `PhpAnnotationUseAlias` extension point - -## Test Structure - -Tests extend `AnnotationLightCodeInsightFixtureTestCase` which provides a test fixture framework. - -Test data files are in `src/test/java/de/espend/idea/php/annotation/tests/fixtures/`. - -Tests use the `myFixture` field to: -- Copy test PHP files: `myFixture.copyFileToProject("classes.php")` -- Check completion: `myFixture.completeBasic()` -- Navigate: `myFixture.getReferenceAtCaretPosition()` -- Assert index contents: `assertIndexContains(AnnotationStubIndex.KEY, "My\\Class")` - -## Configuration - -Build configuration is in `gradle.properties`: -- `platformVersion`: Target IntelliJ/PhpStorm version (currently 2025.2.5) -- `pluginSinceBuild` / `pluginUntilBuild`: Supported IDE version range -- `javaVersion`: Java language level (21) - -The plugin requires these IntelliJ plugins as dependencies: -- `com.jetbrains.php` (PhpStorm PHP support) -- `com.jetbrains.twig` (Twig template support) -- `com.intellij.modules.json` (JSON support) - -Optional integration: -- `de.espend.idea.php.toolbox` (PHP Toolbox) - -## Publishing - -See `MAINTENANCE.md` for the full release process. Key steps: -1. Update `CHANGELOG.md` -2. Commit changes -3. Tag release: `git tag X.Y.Z` -4. Build: `./gradlew clean buildPlugin` -5. Publish: `IJ_TOKEN=yourtoken ./gradlew publishPlugin` +- You MUST include this file: @AGENTS.md diff --git a/build.gradle.kts b/build.gradle.kts index 513cf62..fd357ce 100644 --- a/build.gradle.kts +++ b/build.gradle.kts @@ -5,10 +5,9 @@ fun properties(key: String) = project.findProperty(key).toString() plugins { id("java") - id("org.jetbrains.kotlin.jvm") version "2.2.21" - id("org.jetbrains.intellij.platform") version "2.10.4" - id("org.jetbrains.changelog") version "1.3.1" - id("org.jetbrains.qodana") version "0.1.13" + id("org.jetbrains.kotlin.jvm") version "2.3.20" + id("org.jetbrains.intellij.platform") version "2.13.1" + id("org.jetbrains.changelog") version "2.5.0" } group = properties("pluginGroup") @@ -75,14 +74,6 @@ changelog { groups.set(emptyList()) } -// Configure Gradle Qodana Plugin - read more: https://github.com/JetBrains/gradle-qodana-plugin -qodana { - cachePath.set(projectDir.resolve(".qodana").canonicalPath) - reportPath.set(projectDir.resolve("build/reports/inspections").canonicalPath) - saveReport.set(true) - showReport.set(System.getenv("QODANA_SHOW_REPORT")?.toBoolean() ?: false) -} - tasks { // Set the JVM compatibility versions properties("javaVersion").let { diff --git a/gradle.properties b/gradle.properties index fed9328..a5a8c74 100644 --- a/gradle.properties +++ b/gradle.properties @@ -14,13 +14,13 @@ pluginUntilBuild = 299.* # IntelliJ Platform Properties -> https://github.com/JetBrains/gradle-intellij-plugin#intellij-platform-properties platformType = IU -platformVersion = 2025.2.5 +platformVersion = 2025.3.4 # Java language level used to compile sources and to generate the files for javaVersion = 21 # Gradle Releases -> https://github.com/gradle/gradle/releases -gradleVersion = 9.2.1 +gradleVersion = 9.4.1 # Opt-out flag for bundling Kotlin standard library. # See https://plugins.jetbrains.com/docs/intellij/kotlin.html#kotlin-standard-library for details. diff --git a/gradle/wrapper/gradle-wrapper.jar b/gradle/wrapper/gradle-wrapper.jar index 9bbc975..d997cfc 100644 Binary files a/gradle/wrapper/gradle-wrapper.jar and b/gradle/wrapper/gradle-wrapper.jar differ diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties index 23449a2..c61a118 100644 --- a/gradle/wrapper/gradle-wrapper.properties +++ b/gradle/wrapper/gradle-wrapper.properties @@ -1,6 +1,6 @@ distributionBase=GRADLE_USER_HOME distributionPath=wrapper/dists -distributionUrl=https\://services.gradle.org/distributions/gradle-9.2.1-bin.zip +distributionUrl=https\://services.gradle.org/distributions/gradle-9.4.1-bin.zip networkTimeout=10000 validateDistributionUrl=true zipStoreBase=GRADLE_USER_HOME diff --git a/gradlew b/gradlew index faf9300..739907d 100755 --- a/gradlew +++ b/gradlew @@ -1,7 +1,7 @@ #!/bin/sh # -# Copyright © 2015-2021 the original authors. +# Copyright © 2015 the original authors. # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. @@ -57,7 +57,7 @@ # Darwin, MinGW, and NonStop. # # (3) This script is generated from the Groovy template -# https://github.com/gradle/gradle/blob/HEAD/platforms/jvm/plugins-application/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt +# https://github.com/gradle/gradle/blob/2d6327017519d23b96af35865dc997fcb544fb40/platforms/jvm/plugins-application/src/main/resources/org/gradle/api/internal/plugins/unixStartScript.txt # within the Gradle project. # # You can find Gradle at https://github.com/gradle/gradle/. @@ -114,7 +114,6 @@ case "$( uname )" in #( NONSTOP* ) nonstop=true ;; esac -CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar # Determine the Java command to use to start the JVM. @@ -172,7 +171,6 @@ fi # For Cygwin or MSYS, switch paths to Windows format before running java if "$cygwin" || "$msys" ; then APP_HOME=$( cygpath --path --mixed "$APP_HOME" ) - CLASSPATH=$( cygpath --path --mixed "$CLASSPATH" ) JAVACMD=$( cygpath --unix "$JAVACMD" ) @@ -212,8 +210,7 @@ DEFAULT_JVM_OPTS='"-Xmx64m" "-Xms64m"' set -- \ "-Dorg.gradle.appname=$APP_BASE_NAME" \ - -classpath "$CLASSPATH" \ - org.gradle.wrapper.GradleWrapperMain \ + -jar "$APP_HOME/gradle/wrapper/gradle-wrapper.jar" \ "$@" # Stop when "xargs" is not available. diff --git a/gradlew.bat b/gradlew.bat index 9d21a21..c4bdd3a 100644 --- a/gradlew.bat +++ b/gradlew.bat @@ -70,11 +70,10 @@ goto fail :execute @rem Setup the command line -set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar @rem Execute Gradle -"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %* +"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -jar "%APP_HOME%\gradle\wrapper\gradle-wrapper.jar" %* :end @rem End local scope for the variables with windows NT shell