2013年9月2日 星期一

Customized Parent Last ClassLoader

I am currently assisting my company to migrate Kafka 0.7 to Kafka 0.8. I discovered some interesting code practice in the migration tool.

In the migration tool, there are a Kafka 0.7 consumer and a Kafka 0.8 producer.

As these two version 's code path are almost the same, the parent last classloader is written in order to let the tool load the previous version consumer. Normally, classloader in java prefers parent first. Like the graph below:


Source:http://javarevisited.blogspot.hk/2012/12/how-classloader-works-in-java.html (Java Revisit)

After loading the class in the customized class loader, we can use the customized class loader to create the instance by using reflection.


  private static class ParentLastURLClassLoader extends ClassLoader {
    private ChildURLClassLoader childClassLoader;

    /**
     * This class allows me to call findClass on a class loader
     */
    private static class FindClassClassLoader extends ClassLoader {
      public FindClassClassLoader(ClassLoader parent) {
        super(parent);
      }
      @Override
      public Class<?> findClass(String name) throws ClassNotFoundException {
        return super.findClass(name);
      }
    }

    /**
     * This class delegates (child then parent) for the findClass method for a URLClassLoader.
     * We need this because findClass is protected in URLClassLoader
     */
    private static class ChildURLClassLoader extends URLClassLoader {
      private FindClassClassLoader realParent;
      public ChildURLClassLoader( URL[] urls, FindClassClassLoader realParent) {
        super(urls, null);
        this.realParent = realParent;
      }

      @Override
      public Class<?> findClass(String name) throws ClassNotFoundException {
        try{
          // first try to use the URLClassLoader findClass
          return super.findClass(name);
        }
        catch( ClassNotFoundException e ) {
          // if that fails, we ask our real parent class loader to load the class (we give up)
          return realParent.loadClass(name);
        }
      }
    }

    public ParentLastURLClassLoader(URL[] urls) {
      super(Thread.currentThread().getContextClassLoader());
      childClassLoader = new ChildURLClassLoader(urls, new FindClassClassLoader(this.getParent()));
    }

    @Override
    protected synchronized Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException {
      try {
        // first we try to find a class inside the child class loader
        return childClassLoader.findClass(name);
      }
      catch( ClassNotFoundException e ) {
        // didn't find it, try the parent
        return super.loadClass(name, resolve);
      }
    }
  }

2013年6月6日 星期四

Async RESTful Service with Disruptor 3

I am currently developing a small POC model for testing out the Async feature of Jersey 2 with the help of Disruptor to dispatch the RESTful request
Phase 1:

Detail:
Main Thread :HTTP RESTful Get of Input Parameter ---> Jersey 2 --> Disruptor Dispatch the parameter to another thread.
Thread 1 : GCD Calculation.
Thread 2:  Async Response to the client
Thread 3:  Using AMQP(RabbitMQ) to write the log to DB, Probably Cassandra and each value is written using JSON .


With this POC, what I want to know more about Disruptor over ArrayBlockQueue and the latest Jersey 2 JAX-WS  implementation.

Besides, I also wanted to test for the AMQP service.



I will jot down more information and the code here later on.

Stay Tuned.

6,June,2013 17.47 GMT +8

sun.misc.Unsafe in Netty

I am currently seeking for some involvement in some Open Source Project in Java.
For me, I am specially in interested in threading, high scalability for I/O.
Netty really catches my eyes.
Therefore, I used eGit to get a copy from their GitHub.


What I aware is their pooling of the ByteBuf, it makes use of sun.misc.Unsafe. It allows us to allocate the MEMORY OFF HEAPLY.

Get yourself a cup of coffee and enjoy the below links if you are interested in High Performance Java:

1 . Java Magic. Part 4: sun.misc.Unsafe - mishadoff thoughts

http://mishadoff.github.io/blog/java-magic-part-4-sun-dot-misc-dot-unsafe/

 2 . Highly Scalable Blog
http://highlyscalable.wordpress.com/2012/02/02/direct-memory-access-in-java/


 I will write a more detailed style here to describe how Netty make use of Unsafe.

2013年5月27日 星期一

Conurrency 101 : Sychronizing Correctly

In this week, I want to ensure all guys know about some synchronizing skill.

DON'T DO:
1. Synchronizing on String:  

For example, we pass in a string "abcdef" created previously by: String xxx="abcdef"; into the function session, JVM would get the "abcdef" String Object in the String pool in Perm Gen. If there is more than one "abcdef" String in the String Pool. It may causes all String "abcdef" obtaining the lock, it may causes a lot of unexpected errors if there are also some critical sessions using "abcdef" as the synchronizer, causing race condition.


2. Synchronize on Numerical wrapper, like Integer(),Long(),Double() 

In fact, the JLS specified a certain range of number that always return the same instance when called. For example, It seems that two thread would be obtained their lock successfully, BUT, in fact, for sometime, threadOne or threadTwo would be blocked by chance as Integer one and Integer two are actually refer to the same instance in JVM Heap. For the above, I suggest to create a brand new Object to peform the locking. Like here: Object lock=new Object();

3.  Forget to do the Synchronize after using synchronized collections,like ConcurrentHashMap(), Collections.synchronizedMap(new HashMap())

By using these data structures, we can only ensure the thread Safety during get/put.
After we get the object from the data structure, you must use lock explicitly to ensure the thread safety issue.


DO: 1. Use JSR-166 Concurrent API. 
There are some concurrent API available after Java 5, they are CountDownLatches, CyclicBarrier, Semaphore..
List of API is as below: http://docs.oracle.com/javase/6/docs/api/java/util/concurrent/package-summary.html

2. Consider Lock API . 
Java has an API java.util.concurrent.locks that provides more features than synchronized. Statistically , it is more scalable than sychronized during high load.
Moreover, it provides a more flexible API and a provides a fair locking.

3. Use ArrayBlockQueue/LinkedBlockQueue/BlockDeque for Producer/Consumer pattern.
Please don't re-invent the wheel. Use the updated implementation from Java.
(LMAX Disruptor seems a more interested library recently. The Ring Buffer really makes it attractive for low latency dispatching/thread communication )

4. Follow the lock Sequence.
Avoid the deadlock.


This 101 would be updated when I have more ideas in mind.
Welcome everybody suggesting some pitfalls are required to beware for the Thread Safety.

2013年5月16日 星期四

Java 7 Try-with-Resource

最近的Refactoring Project真是令人發悶,由於 Upgrade Project 是包含了 Java 5-->Java 7 的Update, 我可以測試一下 Java 7 的 try with Resource.
Try-With-Resource 是指 Java 在 嘗試 Initialize Resource 的時候的動作:
1. Object Initialized successful -> Close the resource
 2. Object Initialized failed -> Close the resource

 Java 7: static String readFirstLineFromFile(String path) throws IOException
{ try (BufferedReader br = new BufferedReader(new FileReader(path)))
{ return br.readLine(); } }

 Before Java 7: static String readFirstLineFromFileWithFinallyBlock(String path) throws IOException
{ BufferedReader br = new BufferedReader(new FileReader(path));
 try { return br.readLine(); }
 finally { if (br != null) br.close(); } }

 比較一下,大家可以發現沒有Try-with-Resource 沒有了 finally 關上 BufferedReader 的 Coding.
 Resource 只需要 implements AutoCloseable, 便可以以使用 這種 syntactic sugar 了.

 其實這種 Syntax , 在 C# 一早便已存在(Using())

2013年5月13日 星期一

[Unit Testing]Ant with JoCoCo

近排的工作是在準備做Websphere 8.5 + Hibernate 4.2 Upgrade.


我需要寫不同的JUnit Test Case 去 Test 不同的DAO 和 Persistence Unit.


公司的要求相當低:

1. 不講究Code Coverage.
2.  有部份同事為左方便,從來沒有Test 過其他 Create , Retrieve , and Update Function.( Code Coverage below 10%)
3. 用 DB 現成Data, 因為Data 會在很多時候變動,使 Unit Test Rely on DB Data. 不夠獨立性。


我本着 Tech Geek 的心態,為左嘗試不同的小技術,就把他們的 ANT Script 進行小修改:
1. 首先,在 build.xml 修改,加入 xmlns:jacoco="antlib:org.jacoco.ant" 。

<project name="Impl" default="default" basedir="." xmlns:jacoco="antlib:org.jacoco.ant">
2.  加入 JaCoCo 的 Task Def
<taskdef uri="antlib:org.jacoco.ant" resource="org/jacoco/ant/antlib.xml">
        <classpath path="lib/jacocoant.jar" />
    </taskdef>

3. 把 需要行 Code Coverage 的 Java Task 用 <jacoco:coverage></jacoco:coverage> 包上。

4. 再將 已 Compile 好 的.class path 和 src file path 在紅的地方填上。

   <target name="test-suite" depends="test-compile" description="Execute unit tests suite">
             <echo> Test classpath ${proj.test.classpath}</echo>
           
            <jacoco:coverage>
            <java fork="yes" classname="org.junit.runner.JUnitCore">
                  <classpath>
                      <path refid="proj.test.classpath"/>
                  </classpath>
                 
  <arg line="com.xzxxx.abcd.ordermanagement.persistence.impl.test.TestTradeHistoryHibernatePersistence" />
        </java>
        </jacoco:coverage>
            <jacoco:report>
                          
        <executiondata>
            <file file="jacoco.exec"/>
        </executiondata>
                          
        <structure name="Example Project">
            <classfiles>
                <fileset dir="build\classes"/>
            </classfiles>
            <sourcefiles encoding="UTF-8">
                <fileset dir="src\java"/>
            </sourcefiles>
        </structure>
                          
        <html destdir="report"/>
                          
    </jacoco:report>
    </target>

5. 最後,便是 行 ant <你的 target-name>

6. Report 會在 Report Directory Generate 出來。

HK Coding Style below.



Ant:  http://ant.apache.org/
JaCoCo: http://www.eclemma.org/jacoco/

2013年2月22日 星期五

Singleton



由今日開始,本Blog 改為用中文編寫,敬請留意。

1. A simple one
public class Singleton{
  
  
    private static StringBuilder sb;
  
    public static StringBuilder getInstance(){
        if(sb==null){
            sb=new StringBuilder();
            return sb;
        }else{
            return sb;
        }
    }
  
  
}

這個 Class 有什麼問題?
就是沒有考慮到Multi Threading Access 的問題。

假設有兩條Thread 同時 Access 一個未被Constructed 的 StringBuilder, 第一條Thread 首先Create Object 到 Heap Memory 和存放 Reference 去到Stack.

可是,第二條 Thread 並未能看見第一條Thread 提供的改動,它看到的 sb 仍是 null ,所以

在 Java 5 的打後,Java JSR-133 提供了JMM, Java Memory Model.

Hey Hey Hey, what 's that about??

在這裡,我只會簡單地介紹,有興趣的朋友可以到

JSR 133 (Java Memory Model) FAQ

http://www.cs.umd.edu/~pugh/java/memoryModel/jsr-133-faq.html#otherlanguages
 

其中一個重點是提供了 volatile modifier.


它提供了一個溝通的機制,令到Thread 1 能夠和Thread 2 溝通,Make sure Thread 1 的 Changes 會被Thread 2 看見。

Volatile 的出現,令到我們可以寫一個Thread safe 的 Singleton, Double Checked Singleton.

Double Checked Singleton
class Foo {
    private volatile Helper helper = null;
    public Helper getHelper() {
        if (helper == null) {
            synchronized(this) {
                if (helper == null) {
                    helper = new Helper();
                }
            }
        }
        return helper;
    } 
}
假設有兩條Thread 先後執行 getHelper(), 當Thread 1 進入時,會首先Check 一下 Helper 是否為null,
由於 synchronized 去拿個java monitor 的時間會大大影響程式的運行速度,所以我們會將 null checking 放在第一個if。
接著,Thread 1 從 synchronized 取得lock, 再以null checking determine 一下 helper 是null or not.
最後才創建 Helper.
Volatile 的作用是在創建了 Helper 之後,Thread 1 令到 Thread 2 知道 helper 己經被創建。

第二種方法:
使用Enum:(參考 Effective Java Edition 2 , Joshua Bloch)
public enum Singleton {
 INSTANCE;
 
 public void doStuff(String stuff) {
    System.out.println(stuff);
 }
}

這種方法的Call 法非常簡單, Singleton.INSTANCE.doStuff("abc"), 便call 了 Singleton 一次了。

但這種的缺點就是它會隨着Class Loader load 起的時候,裏面的Obect 便 Constructed 了起來,沒有了Lazy Initialized 的感覺。


第三種方法:

Initialization-on-demand holder idiom(From University of Maryland Computer Science researcher Bill Pugh)




public class Something {
        private Something() {
        }
 
        private static class LazyHolder {
                private static final Something INSTANCE = new Something();
        }
 
        public static Something getInstance() {
                return LazyHolder.INSTANCE;
        }
}
 
 
這個Solution 能夠有Lazy initialization 的是因為 Inner Class 是只會在第一次存取時才會被JVM Initialize ,
所以便逹到了 Lazy 的效果。再者,Class Initialization 是 non-concurrent 的,所以並不需要Sycnhronization 的幫助來逹至Thread Safe 的效果。




看似這是我在大學時的Software Engineering 學過的, 可以Provide 一個Global Point of Access and 省卻記憶體和物件Create 的時間.

什麼可以係Singleton 呢?
1. Datasource
2. Cache Instance

Singleton 缺點:
 1. Per Class loader wise(不是Unique in every JVM, 因為可以有數個同一個Singleton 的Class) 
 2. Unit Testing, 因為Singleton是只會Initalize 一次,跟着便放在 Memory 內,難以被Mock or subclass override.

參考:
1. Singleton Pattern

2. Effective Java 2nd Ed
3. Java Concurrency (&c)
4. Patterns I hate

期待下一次大家分享其他Knowledge 和工作經驗! 
希望下次可以講一下ORM, 以及 Persistence Polygot...哈哈,要加油喔.

有錯請多多指教,謝!