Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How can a project support Java 7 despite using Java 8 features

I'm reviewing the HikariCP project on github, and it declares that it supports "Java 7 and Java 8 maven artifact", in its source code, it uses some Java 8 features:

java.util.function.Consumer;
java.util.function.Predicate;
java.util.function.UnaryOperator;

I guess if this project is being referenced by others with Java 7, error will occur. So, how the project makes it to support Java 7 and Java 8 at the same time?

like image 539
lawrence Avatar asked Aug 12 '16 02:08

lawrence


1 Answers

This is not a mistake (as I myself thought). The project indeed uses classes from Java 8. It does not compile with Java 7, and its Maven build doesn't run with Java 7 either.

However, as Java 8-specific features like Lambdas are used nowhere in the source code, it does run with Java 7.

Try creating a Java 7 project, declaring HikariCP as a dependency, and running the following code:

import com.zaxxer.hikari.util.FastList;

public class Main {

    public static void main(String[] args) {

        FastList<String> fastList = new FastList<>(String.class);
        fastList.add("Hello");
        System.out.println(fastList);
    }
}

It runs successfully. On the other hand, the following code fails:

fastList.removeIf(null);

This is because removeIf() and some other methods use classes from Java 8, and can't therefore run with Java 7. But they all throw UnsupportedOperationException anyway! You may notice that the only class to import Java 8 classes is com.zaxxer.hikari.util.FastList. I'm not sure why they did it.

UPDATE: Just wanted to clarify that the project bytecode's version is 1.7, as can be easily verified with a decompiler or hexdump. Its source code does comply with Java 7 and therefore can be build with

<source>1.7</source>
<target>1.7</target>

as pointed out by @Puce.

On the other hand, it must be compiled with JDK 1.8 so that the Java 8 classes referenced in the source code are available during compilation. Once the code has been compiled, it can run with Java 7 as long as no attempts are made to load a missing Java 8 class (from the java.util.function package in this case).

like image 103
vempo Avatar answered Sep 29 '22 07:09

vempo