Delay loading compression classes until used

Description

Even when the user uses the default ProtocolOptions.Compression.NONE, driver tries to initialize the Snappy and LZ4 compressors. When user does not have those jars in the class path, they get warnings like this:

2015-03-18 10:39:41 WARN FrameCompressor:44 - Cannot find Snappy class, you should make sure the Snappy library is in the classpath if you intend to use it. Snappy compression will not be available for the protocol.
2015-03-18 10:39:52 WARN FrameCompressor:87 - Cannot find LZ4 class, you should make sure the LZ4 library is in the classpath if you intend to use it. LZ4 compression will not be available for the protocol.

At times, the jars are present in the class path but there is a problem with .so finding the right dependencies on the host. We see errors like:

java.lang.reflect.InvocationTargetException
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
at java.lang.reflect.Method.invoke(Method.java:597)
at org.xerial.snappy.SnappyLoader.loadNativeLibrary(SnappyLoader.java:322)
at org.xerial.snappy.SnappyLoader.load(SnappyLoader.java:229)
at org.xerial.snappy.Snappy.<clinit>(Snappy.java:48)
at com.datastax.driver.core.FrameCompressor$SnappyCompressor.<init>(FrameCompressor.java:55)
at com.datastax.driver.core.FrameCompressor$SnappyCompressor.<clinit>(FrameCompressor.java:41)
at com.datastax.driver.core.ProtocolOptions$Compression.<clinit>(ProtocolOptions.java:35)
at com.datastax.driver.core.Cluster$Builder.<init>(Cluster.java:542)
Caused by: java.lang.UnsatisfiedLinkError: /tmp/snappy-1.0.5-libsnappyjava.so: /usr/lib64/libstdc++.so.6: version `GLIBCXX_3.4.9' not found (required by /tmp/snappy-1.0.5-libsnappyjava.so)
at java.lang.ClassLoader$NativeLibrary.load(Native Method)
at java.lang.ClassLoader.loadLibrary0(ClassLoader.java:1807)
at java.lang.ClassLoader.loadLibrary(ClassLoader.java:1703)
at java.lang.Runtime.load0(Runtime.java:770)
at java.lang.System.load(System.java:1003)
at org.xerial.snappy.SnappyNativeLoader.load(SnappyNativeLoader.java:39)
... 44 more

These errors confuse the novice users. We can avoid these things by delaying loading of compression classes until needed.

Environment

None

Pull Requests

None

Activity

Andy Tolbert 
March 30, 2015 at 4:41 PM

Validated that the warning is now logged only when building a Cluster using withCompression with a compression that is not on the classpath, like previously an IllegalStateException is also raised in this case. Therefore you should now no longer see compression warnings unless you try using compression with a compression library that is not in the classpath.

Olivier Michallat 
March 18, 2015 at 6:49 PM

Scheduling for 2.0.10 because this is a trivial fix (I have it in a local branch).

Olivier Michallat 
March 18, 2015 at 6:48 PM

Regarding the Snappy issue, it looks like it's a glibc compatibility issue (see this answer).

If you don't use Snappy, the lazy initialization will solve this.
If you actually want to use Snappy, try upgrading to version 1.1.1.6.

Olivier Michallat 
March 18, 2015 at 6:15 PM
(edited)

I think simply making Compression.compressor() abstract and implementing it in each enum constant instead of using a field will do the trick.

Fixed

Details

Assignee

Reporter

Labels

Fix versions

Priority

Created March 18, 2015 at 5:47 PM
Updated March 31, 2015 at 1:15 PM
Resolved March 31, 2015 at 1:15 PM