diff --git a/CHANGELOG.md b/CHANGELOG.md index 88ea621..9b84cde 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,24 +1,29 @@ # Changelog -All notable changes to this project will be documented in this file. +All notable changes to this project will be documented in this file. This project adheres to [Semantic Versioning](http://semver.org/). +## [0.11.0](https://github.com/shyiko/jabba/compare/0.10.1...0.11.0) - 2018-05-07 + +### Added +- Support for `jabba exec JVM_VERSION -- command -with args` (#285)[https://github.com/shyiko/jabba/issues/285] + ## [0.10.1](https://github.com/shyiko/jabba/compare/0.10.0...0.10.1) - 2018-05-07 ### Fixed -- `jabba install ` not checking whether JDK is already installed. +- `jabba install ` not checking whether JDK is already installed. ## [0.10.0](https://github.com/shyiko/jabba/compare/0.9.6...0.10.0) - 2018-05-06 -- [OpenJDK with Shenandoah GC](https://wiki.openjdk.java.net/display/shenandoah/Main) support ([#191](https://github.com/shyiko/jabba/issues/191)) +- [OpenJDK with Shenandoah GC](https://wiki.openjdk.java.net/display/shenandoah/Main) support ([#191](https://github.com/shyiko/jabba/issues/191)) (e.g. `jabba install openjdk-shenandoah@1.9`). -- Ability to install JDK from `tar.xz` archives +- Ability to install JDK from `tar.xz` archives (e.g. `jabba install openjdk-shenandoah@1.9.0-220=tgx+file://$PWD/local-copy-of-openjdk-shenandoah-jdk9-b220-x86-release.tar.xz`). ## [0.9.6](https://github.com/shyiko/jabba/compare/0.9.5...0.9.6) - 2018-05-05 ### Fixed -- Sporadic "open: permission denied" when installing from tgz/zip's ([#190](https://github.com/shyiko/jabba/issues/190)). -Fix applied in 0.9.5 proved to be incomplete. +- Sporadic "open: permission denied" when installing from tgz/zip's ([#190](https://github.com/shyiko/jabba/issues/190)). +Fix applied in 0.9.5 proved to be incomplete. ## [0.9.5](https://github.com/shyiko/jabba/compare/0.9.4...0.9.5) - 2018-05-04 @@ -35,17 +40,17 @@ Fix applied in 0.9.5 proved to be incomplete. ### Fixed - `Contents/Home` handling (macOS) ([#187](https://github.com/shyiko/jabba/issues/187)). -## [0.9.2](https://github.com/shyiko/jabba/compare/0.9.1...0.9.2) - 2017-11-18 +## [0.9.2](https://github.com/shyiko/jabba/compare/0.9.1...0.9.2) - 2017-11-18 ### Fixed - `zip` & `tgz` stripping on Windows ([#116](https://github.com/shyiko/jabba/issues/116)). -## [0.9.1](https://github.com/shyiko/jabba/compare/0.9.0...0.9.1) - 2017-10-12 +## [0.9.1](https://github.com/shyiko/jabba/compare/0.9.0...0.9.1) - 2017-10-12 ### Fixed -- `tgz is not supported` when trying to install JDK from `tar.gz` on macOS & Windows. +- `tgz is not supported` when trying to install JDK from `tar.gz` on macOS & Windows. -## [0.9.0](https://github.com/shyiko/jabba/compare/0.8.0...0.9.0) - 2017-09-19 +## [0.9.0](https://github.com/shyiko/jabba/compare/0.8.0...0.9.0) - 2017-09-19 ### Added - Latest JDK / `default` alias (automatic) linking ([#6](https://github.com/shyiko/jabba/issues/6)) @@ -60,7 +65,7 @@ Fix applied in 0.9.5 proved to be incomplete. lrwxrwxrwx 1 shyiko shyiko 30 Sep 19 2017 default -> /home/shyiko/.jabba/jdk/1.8.144/ ``` -## [0.8.0](https://github.com/shyiko/jabba/compare/0.7.0...0.8.0) - 2017-09-19 +## [0.8.0](https://github.com/shyiko/jabba/compare/0.7.0...0.8.0) - 2017-09-19 ### Added - [Adopt OpenJDK](https://adoptopenjdk.net/) support. @@ -74,11 +79,11 @@ Fix applied in 0.9.5 proved to be incomplete. zulu@1.6.97 ``` -- Ability to install JDK in a custom location (`jabba install -o /jdk/destination`) +- Ability to install JDK in a custom location (`jabba install -o /jdk/destination`) NOTE: any JDK installed in this way is considered to be unmanaged, i.e. not available to `jabba ls`, `jabba use`, etc. (unless `jabba link`ed). ### Changed -- semver library to [masterminds/semver](https://github.com/Masterminds/semver) +- semver library to [masterminds/semver](https://github.com/Masterminds/semver) (previously used library proved unreliable when given certain input (e.g. `>=1.6`)). ## [0.7.0](https://github.com/shyiko/jabba/compare/0.6.1...0.7.0) - 2017-05-12 @@ -114,7 +119,7 @@ NOTE: any JDK installed in this way is considered to be unmanaged, i.e. not avai ## [0.5.0](https://github.com/shyiko/jabba/compare/0.4.0...0.5.0) - 2016-11-11 ### Added -* `.jabbarc` support. +* `.jabbarc` support. ## [0.4.0](https://github.com/shyiko/jabba/compare/0.3.3...0.4.0) - 2016-07-22 @@ -145,14 +150,14 @@ NOTE: any JDK installed in this way is considered to be unmanaged, i.e. not avai ### Added * Zulu OpenJDK support (e.g. `jabba install zulu@`). * Ability to install JDK from `zip` archives (in addition to already implemented `dmg`/`tar.gz`/`bin`). -* Support for custom registries (e.g. `JABBA_INDEX=https://github.com/shyiko/jabba/raw/master/index.json jabba install ...`). +* Support for custom registries (e.g. `JABBA_INDEX=https://github.com/shyiko/jabba/raw/master/index.json jabba install ...`). ### Fixed * `which `. ## [0.2.0](https://github.com/shyiko/jabba/compare/0.1.0...0.2.0) - 2016-03-24 -### Added -* `alias default`/`unalias default`, `which`, `deactivate` commands. +### Added +* `alias default`/`unalias default`, `which`, `deactivate` commands. ## 0.1.0 - 2016-03-23 diff --git a/README.md b/README.md index b98f776..de3099c 100644 --- a/README.md +++ b/README.md @@ -5,16 +5,16 @@ Java Version Manager inspired by [nvm](https://github.com/creationix/nvm) (Node.js). Written in Go. The goal is to provide unified pain-free experience of **installing** (and **switching** between different versions of) JDK regardless of -the OS (macOS, Linux x86/x86_64/ARMv7+, Windows x86_64). +the OS (macOS, Linux x86/x86_64/ARMv7+, Windows x86_64). `jabba install` - [Oracle JDK](http://www.oracle.com/technetwork/java/javase/archive-139210.html) (latest-version only) -- [Oracle Server JRE](http://www.oracle.com/technetwork/java/javase/downloads/server-jre8-downloads-2133154.html) (latest-version only), -- [Adopt OpenJDK](https://adoptopenjdk.net/) (jabba >=0.8.0 is required) - - Hotspot +- [Oracle Server JRE](http://www.oracle.com/technetwork/java/javase/downloads/server-jre8-downloads-2133154.html) (latest-version only), +- [Adopt OpenJDK](https://adoptopenjdk.net/) (jabba >=0.8.0 is required) + - Hotspot - [Eclipse OpenJ9](https://www.eclipse.org/openj9/oj9_faq.html) - [Zulu OpenJDK](http://zulu.org/) (jabba >=0.3.0 is required) -- [IBM SDK, Java Technology Edition](https://developer.ibm.com/javasdk/) (jabba >=0.6.0 is required) +- [IBM SDK, Java Technology Edition](https://developer.ibm.com/javasdk/) (jabba >=0.6.0 is required) - [GraalVM CE](https://www.graalvm.org/) - [OpenJDK](http://openjdk.java.net/) - [OpenJDK with Shenandoah GC](https://wiki.openjdk.java.net/display/shenandoah/Main) (jabba >=0.10.0 is required) @@ -33,19 +33,19 @@ curl -sL https://github.com/shyiko/jabba/raw/master/install.sh | bash && . ~/.ja > (use the same command to upgrade) -> In [fish](https://fishshell.com/) command looks a little bit different - -`curl -sL https://github.com/shyiko/jabba/raw/master/install.sh | bash; and . ~/.jabba/jabba.fish` +> In [fish](https://fishshell.com/) command looks a little bit different - +`curl -sL https://github.com/shyiko/jabba/raw/master/install.sh | bash; and . ~/.jabba/jabba.fish` > If you don't have `curl` installed - replace `curl -sL` with `wget -qO-`. > If you are behind a proxy see - -[curl](https://curl.haxx.se/docs/manpage.html#ENVIRONMENT) / -[wget](https://www.gnu.org/software/wget/manual/wget.html#Proxies) manpage. -Usually simple `http_proxy=http://proxy-server:port https_proxy=http://proxy-server:port curl -sL ...` is enough. +[curl](https://curl.haxx.se/docs/manpage.html#ENVIRONMENT) / +[wget](https://www.gnu.org/software/wget/manual/wget.html#Proxies) manpage. +Usually simple `http_proxy=http://proxy-server:port https_proxy=http://proxy-server:port curl -sL ...` is enough. #### Docker -While you can use the same snippet as above, chances are you don't want jabba binary & shell +While you can use the same snippet as above, chances are you don't want jabba binary & shell integration script(s) to be included in the final Docker image, all you want is a JDK. Here is the `Dockerfile` showing how this can be done: ```dockerfile @@ -92,14 +92,14 @@ jabba ls-remote "*@>=1.6.45 <1.9" --latest=minor # install Oracle JDK jabba install 1.8 # install Oracle Server JRE -jabba install sjre@1.8 +jabba install sjre@1.8 # install Adopt OpenJDK (Hotspot) jabba install adopt@1.8-0 # install Adopt OpenJDK (Eclipse OpenJ9) jabba install adopt-openj9@1.9-0 # install Zulu OpenJDK jabba install zulu@1.8 -jabba install zulu@~1.8.144 # same as "zulu@>=1.8.144 <1.9" +jabba install zulu@~1.8.144 # same as "zulu@>=1.8.144 <1.9" # install IBM SDK, Java Technology Edition jabba install ibm@1.8 # install GraalVM CE @@ -132,22 +132,26 @@ jabba use # set default java version on shell (since 0.2.0) # this version will automatically be "jabba use"d every time you open up a new terminal jabba alias default 1.8 + +# execute a single command with specified JDK version +# make sure to add the `--` separator between jabba and your command +jabba exec system@1.8.72 -- mvn clean assemble ``` -> `.jabbarc` has to be a valid YAML file. JDK version can be specified as `jdk: 1.8` or simply as `1.8` +> `.jabbarc` has to be a valid YAML file. JDK version can be specified as `jdk: 1.8` or simply as `1.8` (same as `~1.8`, `1.8.x` `">=1.8.0 <1.9.0"` (mind the quotes)). -> jsyk: **jabba** keeps everything under `~/.jabba` (on Linux/Mac OS X) / `%USERPROFILE%/.jabba` (on Windows). If at any point of time you decide to uninstall **jabba** - just remove this directory. +> jsyk: **jabba** keeps everything under `~/.jabba` (on Linux/Mac OS X) / `%USERPROFILE%/.jabba` (on Windows). If at any point of time you decide to uninstall **jabba** - just remove this directory. -For more information see `jabba --help`. +For more information see `jabba --help`. ## Development > PREREQUISITE: [go1.8](https://github.com/moovweb/gvm) ```sh -git clone https://github.com/shyiko/jabba $GOPATH/src/github.com/shyiko/jabba -cd $GOPATH/src/github.com/shyiko/jabba +git clone https://github.com/shyiko/jabba $GOPATH/src/github.com/shyiko/jabba +cd $GOPATH/src/github.com/shyiko/jabba make fetch go run jabba.go @@ -156,20 +160,20 @@ go run jabba.go make test # or "test-coverage" if you want to get a coverage breakdown # to make a build -make build # or "build-release" (latter is cross-compiling jabba to different OSs/ARCHs) +make build # or "build-release" (latter is cross-compiling jabba to different OSs/ARCHs) ``` ## FAQ **Q**: What if I already have `java` installed? -A: It's fine. You can switch between system JDK and `jabba`-provided one whenever you feel like it (`jabba use ...` / `jabba deactivate`). +A: It's fine. You can switch between system JDK and `jabba`-provided one whenever you feel like it (`jabba use ...` / `jabba deactivate`). They are not gonna conflict with each other. **Q**: How do I switch `java` globally? -A: **jabba** doesn't have this functionality built-in because the exact way varies greatly between the operation systems and usually -involves elevated permissions. But. Here are the snippets that should work: +A: **jabba** doesn't have this functionality built-in because the exact way varies greatly between the operation systems and usually +involves elevated permissions. But. Here are the snippets that should work: * Windows @@ -210,5 +214,5 @@ By using this software you agree to - Apple's Software License Agreement in case of "Java for OS X" - [International License Agreement for Non-Warranted Programs](http://www14.software.ibm.com/cgi-bin/weblap/lap.pl?la_formnum=&li_formnum=L-PMAA-A3Z8P2&l=en) in case of IBM SDK, Java Technology Edition. -This software is for educational purposes only. -Use it at your own risk. +This software is for educational purposes only. +Use it at your own risk. diff --git a/command/exec.go b/command/exec.go new file mode 100644 index 0000000..f5a31d7 --- /dev/null +++ b/command/exec.go @@ -0,0 +1,38 @@ +package command + +import ( + "os" + "os/exec" + "path/filepath" + "syscall" + + "github.com/shyiko/jabba/cfg" +) + +func Exec(selector string, command string, commandArgs []string) error { + aliasValue := GetAlias(selector) + if aliasValue != "" { + selector = aliasValue + } + ver, err := LsBestMatch(selector) + if err != nil { + return err + } + + vars, err := GetVars(filepath.Join(cfg.Dir(), "jdk", ver)) + if err != nil { + return err + } + + for variableName, variableValue := range vars { + os.Setenv(variableName, variableValue) + } + + binary, err := exec.LookPath(command) + if err != nil { + return err + } + + err = syscall.Exec(binary, commandArgs, os.Environ()) + return err +} diff --git a/command/use.go b/command/use.go index 7bbf01c..150b2e4 100644 --- a/command/use.go +++ b/command/use.go @@ -1,11 +1,12 @@ package command import ( - "github.com/shyiko/jabba/cfg" "os" "path/filepath" "regexp" "runtime" + + "github.com/shyiko/jabba/cfg" ) func Use(selector string) ([]string, error) { @@ -20,7 +21,7 @@ func Use(selector string) ([]string, error) { return usePath(filepath.Join(cfg.Dir(), "jdk", ver)) } -func usePath(path string) ([]string, error) { +func GetVars(path string) (map[string]string, error) { path, err := filepath.Abs(path) if err != nil { return nil, err @@ -36,9 +37,26 @@ func usePath(path string) ([]string, error) { if !overrideWasSet { systemJavaHome, _ = os.LookupEnv("JAVA_HOME") } - return []string{ - "export PATH=\"" + filepath.Join(path, "bin") + string(os.PathListSeparator) + pth + "\"", - "export JAVA_HOME=\"" + path + "\"", - "export JAVA_HOME_BEFORE_JABBA=\"" + systemJavaHome + "\"", - }, nil + + paths := make(map[string]string) + paths["PATH"] = filepath.Join(path, "bin") + string(os.PathListSeparator) + pth + paths["JAVA_HOME"] = path + paths["JAVA_HOME_BEFORE_JABBA"] = systemJavaHome + + return paths, nil +} + +func usePath(path string) ([]string, error) { + vars, err := GetVars(path) + if err != nil { + return nil, err + } + + paths := []string{} + + for variableName, variableValue := range vars { + paths = append(paths, "export "+variableName+"=\""+variableValue+"\"") + } + + return paths, nil } diff --git a/jabba.go b/jabba.go index 5a3604b..fc010eb 100644 --- a/jabba.go +++ b/jabba.go @@ -329,6 +329,28 @@ func main() { }, }, whichCmd, + &cobra.Command{ + Use: "exec [version] [--] [command] [args]", + Short: "Execute a command the specified JVM version", + RunE: func(cmd *cobra.Command, args []string) error { + if len(args) < 2 { + return pflag.ErrHelp + } + + version := args[0] + executable := args[1] + commandArgs := args[1:] + + err := command.Exec(version, executable, commandArgs) + if err != nil { + log.Fatal(err) + } + return nil + }, + Example: " jabba exec system@1.8.20 ./gradlew clean assemble\n" + + " jabba exec ~1.8.73 -- java -version # use -- separator if using args\n" + + " jabba exec ~1.8.73 ./gradlew clean assemble # same as \">=1.8.73 <1.9.0\"", + }, ) rootCmd.Flags().Bool("version", false, "version of jabba") rootCmd.PersistentFlags().String("fd3", "", "")