package com.wegas.log.neo4j;

import org.codehaus.jettison.json.JSONObject;

import javax.ejb.Asynchronous;
import javax.ejb.LocalBean;
import javax.ejb.Schedule;
import javax.ejb.Singleton;

/**
 * Neo4j Singleton for communicating with db
 *
 * @author Cyril Junod (cyril.junod at gmail.com)
 */
@Singleton
@LocalBean
public class Neo4jCommunication {

    private static boolean dbUp = Neo4jUtils.checkDataBaseIsRunning();

    /**
     * Link a new node to an already existing newest filtered by key
     *
     * @param key           key to filter "youngest" nodes
     * @param relationLabel label to put onto the relation
     * @param target        new node to create
     * @param label         label to put onto the node
     */
    @Asynchronous
    public void createLinkedToYoungest(String key, String relationLabel, JSONObject target, String label) {
        String query = "CREATE (p:`" + label + "` " + target.toString().replaceAll("\"([^\"]+)\"\\s*:", "$1:") + ") WITH p AS p Match (n " + key
                + ") WHERE n <> p WITH max(n.starttime) AS max, p AS p MATCH (n "
                + key + ") WHERE n.starttime = max AND n <> p WITH n AS n, p AS p CREATE (n)-[:`"
                + relationLabel + "`]->(p) return p";
        String result = Neo4jUtils.queryDBString(query);
        checkError(result);
    }


    /**
     * Checks if an error occurred during the execution of a query. The
     * potential error message is recorded in the JSON result of the query. If
     * an error was found this method raises an exception.
     *
     * @param result the result of the query
     */
    private static void checkError(String result) {
        String err = Neo4jUtils.extractErrorData(result);
        if (err == null) {
            return;
        }
        throw new RuntimeException(err);
    }

    public static boolean isDBUp() {
        return dbUp;
    }

    @Schedule(hour = "*", minute = "*/15")
    private void checkDB() {
        dbUp = Neo4jUtils.checkDataBaseIsRunning();
    }
}

@@ -23,16 +23,79 @@
 neo4j;%0A%0A
+import com.hazelcast.core.ILock;%0Aimport com.wegas.core.Helper;%0A
 import o
@@ -132,16 +132,16 @@
 Object;%0A
-
 %0Aimport 
@@ -246,16 +246,76 @@
 ngleton;
+%0Aimport javax.ejb.Stateless;%0Aimport org.slf4j.LoggerFactory;
 %0A%0A/**%0A *
@@ -414,16 +414,18 @@
 om)%0A */%0A
+//
 @Singlet
@@ -427,16 +427,27 @@
 ngleton%0A
+@Stateless%0A
 @LocalBe
@@ -990,24 +990,128 @@
 ng label) %7B%0A
+        ILock lock = Helper.getHazelcastInstance().getLock(%22Neo4J%22);%0A        lock.lock();%0A        try %7B%0A
         Stri
@@ -1534,16 +1534,16 @@
 query);%0A
-
         
@@ -1558,24 +1558,80 @@
 or(result);%0A
+        %7D finally%7B%0A            lock.unlock();%0A        %7D%0A
     %7D%0A%0A%0A    

Make Neo4j Singleton cluster-ready