From 986668164531d82c67ae3ca8c36509230b2781d0 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sat, 2 Nov 2013 19:39:30 -0500 Subject: [PATCH 01/48] groupmembership changes --- .../groupmembership/GroupMembership.java | 249 +++++++++++------- .../boltdb/groupmembership/MergeThread.java | 8 +- .../RefreshMembershipListThread.java | 35 +-- .../groupmembership/SendGossipThread.java | 1 + 4 files changed, 170 insertions(+), 123 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index ee5f2fc..e9a7c18 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -19,46 +19,53 @@ import edu.uiuc.boltdb.groupmembership.beans.*; -/**This class is the entry point for Distributed Group Membership. - * It takes two arguments - - * 1) -contact : true if its the contact machine,false otherwise - * 2) -id : this is an argument to identify a machine and will be used to name its log file +/** + * This class is the entry point for Distributed Group Membership. It takes two + * arguments - 1) -contact : true if its the contact machine,false + * otherwise 2) -id : this is an argument to identify a machine and + * will be used to name its log file * - * Data structures : - * The membership list is maintained inside a ConcurrentHashMap. - * There are two advantages of doing this : - * 1. Thread Safety : Both read/write on the membership list is thread safe. - * 2. Fast : only a portion of the map is locked while writing into it and not the whole map. - * This means other READ threads can continue accessing the map while another writes to it. - * - * Parameters : - * This class needs 6 parameters to function and all of these come from a property file boltdb.prop. - * The parameters are contact hostname,gossip frequency, heartbeat increment frequency, tfail, refresh membership list frequency, lossrate(for 4th credit). + * Data structures : The membership list is maintained inside a + * ConcurrentHashMap. There are two advantages of doing + * this : 1. Thread Safety : Both read/write on the membership list is thread + * safe. 2. Fast : only a portion of the map is locked while writing into it and + * not the whole map. This means other READ threads can continue accessing the + * map while another writes to it. * - * The class initializes and starts the following threads : - * 1. ReceiveGossipThread - * 2. HeartbeatIncrementerThread - * 3. RefreshMembershipListThread - * 4. SendGossipThread + * Parameters : This class needs 6 parameters to function and all of these come + * from a property file boltdb.prop. The parameters are contact hostname,gossip + * frequency, heartbeat increment frequency, tfail, refresh membership list + * frequency, lossrate(for 4th credit). + * + * The class initializes and starts the following threads : 1. + * ReceiveGossipThread 2. HeartbeatIncrementerThread 3. + * RefreshMembershipListThread 4. SendGossipThread + * + * More detils about each of the thread can be found in the javadoc of its + * class. * - * More detils about each of the thread can be found in the javadoc of its class. * @author ashwin(ashanka2) - * + * */ -public class GroupMembership -{ +public class GroupMembership implements Runnable { private static org.apache.log4j.Logger log = Logger.getRootLogger(); - public static ConcurrentHashMap membershipList = new ConcurrentHashMap(); + public static ConcurrentHashMap membershipList = new ConcurrentHashMap(); public static String pid = new String(); public static String pidDelimiter = "--"; public static long bandwidth = 0; - + private String[] args; + + public GroupMembership(String args[]) { + this.args = args; + } + /** - * Initialize the logger. Set the name of the log file with the machineid passed as parameter. + * Initialize the logger. Set the name of the log file with the machineid + * passed as parameter. + * * @param serverId */ - public static void initializeLogger(String serverId) - { + public static void initializeLogger(String serverId) { FileAppender fa = new FileAppender(); fa.setName("FileLogger"); fa.setFile(serverId + ".log"); @@ -68,87 +75,125 @@ public static void initializeLogger(String serverId) fa.activateOptions(); log.addAppender(fa); } - - public static void main(String[] args) throws IOException, InterruptedException - { - //Command line parsing - if(args.length < 1 || !(args[0].equals("-contact"))) - { - System.out.println("Usage: groupmembership -contact [-id ]"); + + public void run() { + // Command line parsing + if (args.length < 1 || !(args[0].equals("-contact"))) { + System.out + .println("Usage: groupmembership -contact [-id ]"); System.exit(1); } - + boolean isContact = false; - if(args[1].equals("true")) + if (args[1].equals("true")) isContact = true; - - pid += InetAddress.getLocalHost().getHostName() + GroupMembership.pidDelimiter + (new Date().toString()); - if (args.length > 2 && args[2].equals("-id")) - { - pid += "-" + args[3]; - initializeLogger(args[3]); - } - - //Insert the current machine into the membership list with heartbeat=1. This single entry is going to be sent to the contact node for joining the cluster. - GroupMembership.membershipList.putIfAbsent(GroupMembership.pid, new MembershipBean(InetAddress.getLocalHost().getHostName(), 1, System.currentTimeMillis(), false)); - - //Load all the paramters needed from the property file. - Properties prop = new Properties(); - FileInputStream fis = new FileInputStream("./boltdb.prop"); - prop.load(fis); - fis.close(); - - //Start the thread that listens to gossip messages. - Thread receiveGossip = new Thread(new ReceiveGossipThread()); - receiveGossip.start(); - - //JOINING : This is the JOIN part . So,if this node is not the contact machine,then try to connect to the contact machine - //and send your membership list which contains just one entry ie current machine's details. - if (!isContact) - { - int maxTries = 10; - while(maxTries-- > 0) - { - new SendMembershipListThread(prop.getProperty("groupmembership.contact"), 8764).start(); - try { - Thread.sleep(1000); - } catch (InterruptedException e) { - // TODO Auto-generated catch block - e.printStackTrace(); + try { + pid += InetAddress.getLocalHost().getHostName() + + GroupMembership.pidDelimiter + (new Date().toString()); + if (args.length > 2 && args[2].equals("-id")) { + pid += "-" + args[3]; + initializeLogger(args[3]); + } + + // Insert the current machine into the membership list with + // heartbeat=1. This single entry is going to be sent to the contact + // node for joining the cluster. + GroupMembership.membershipList.putIfAbsent( + GroupMembership.pid, + new MembershipBean( + InetAddress.getLocalHost().getHostName(), 1, System + .currentTimeMillis(), false)); + + // Load all the parameters needed from the property file. + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + + // Start the thread that listens to gossip messages. + Thread receiveGossip = new Thread(new ReceiveGossipThread()); + receiveGossip.start(); + + // JOINING : This is the JOIN part . So,if this node is not the + // contact machine,then try to connect to the contact machine + // and send your membership list which contains just one entry ie + // current machine's details. + if (!isContact) { + int maxTries = 10; + while (maxTries-- > 0) { + new SendMembershipListThread( + prop.getProperty("groupmembership.contact"), 8764) + .start(); + try { + Thread.sleep(1000); + } catch (InterruptedException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + if (GroupMembership.membershipList.size() > 1) + break; } - if(GroupMembership.membershipList.size() > 1) break; } - } - - //Get the tFail from property file - int tFail = Integer.parseInt(prop.getProperty("groupmembership.tfail")); - - //ScheduledExecutorService is used to schedule all the threads mentioned in the class javadoc with frequency mentioned in property file - ScheduledExecutorService scheduler = Executors.newSingleThreadScheduledExecutor(); - scheduler.scheduleAtFixedRate(new HeartbeatIncrementerThread(), 0, Integer.parseInt(prop.getProperty("groupmembership.heartbeat.freq")), TimeUnit.MILLISECONDS); - scheduler.scheduleAtFixedRate(new RefreshMembershipListThread(tFail), 0, Integer.parseInt(prop.getProperty("groupmembership.refreshMembershipList.freq")), TimeUnit.MILLISECONDS); - scheduler.scheduleAtFixedRate(new SendGossipThread(Integer.parseInt(prop.getProperty("groupmembership.lossrate"))), 0, Integer.parseInt(prop.getProperty("groupmembership.gossip.freq")), TimeUnit.MILLISECONDS); - //scheduler.scheduleAtFixedRate(new LogBandwidthThread(), 0, 60000, TimeUnit.MILLISECONDS); - - //VOLUTARY LEAVE : This is the code for voluntary leave part. Basically we wait for user to input the string "leave". - //Once the user enters "leave",all the threads are stopped. The heartbeat of the current node is set to -1 and - //one last gossip happens. - //Please note that we don't send the last message to everyone in the list. - BufferedReader bufferRead = new BufferedReader(new InputStreamReader(System.in)); - while(true) { - String s = bufferRead.readLine(); - if(s.equals("leave")) { - receiveGossip.stop(); - scheduler.shutdownNow(); - scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); - MembershipBean mBean = membershipList.get(pid); - mBean.hearbeatLastReceived = -1; - mBean.timeStamp = System.currentTimeMillis(); - membershipList.put(pid, mBean); - Thread gossipOneLastTime = new Thread(new SendGossipThread(0)); - gossipOneLastTime.start(); - break; + + // Get the tFail from property file + int tFail = Integer.parseInt(prop + .getProperty("groupmembership.tfail")); + + // ScheduledExecutorService is used to schedule all the threads + // mentioned in the class javadoc with frequency mentioned in + // property file + ScheduledExecutorService scheduler = Executors + .newSingleThreadScheduledExecutor(); + //scheduler.scheduleAtFixedRate(new HeartbeatIncrementerThread(), 0, + // Integer.parseInt(prop + // .getProperty("groupmembership.heartbeat.freq")), + // TimeUnit.MILLISECONDS); + scheduler + .scheduleAtFixedRate( + new RefreshMembershipListThread(tFail), + 0, + Integer.parseInt(prop + .getProperty("groupmembership.refreshMembershipList.freq")), + TimeUnit.MILLISECONDS); + scheduler.scheduleAtFixedRate( + new SendGossipThread(Integer.parseInt(prop + .getProperty("groupmembership.lossrate"))), 0, + Integer.parseInt(prop + .getProperty("groupmembership.gossip.freq")), + TimeUnit.MILLISECONDS); + // scheduler.scheduleAtFixedRate(new LogBandwidthThread(), 0, 60000, + // TimeUnit.MILLISECONDS); + + // VOLUTARY LEAVE : This is the code for voluntary leave part. + // Basically we wait for user to input the string "leave". + // Once the user enters "leave",all the threads are stopped. The + // heartbeat of the current node is set to -1 and + // one last gossip happens. + // Please note that we don't send the last message to everyone in + // the list. + BufferedReader bufferRead = new BufferedReader( + new InputStreamReader(System.in)); + while (true) { + String s = bufferRead.readLine(); + if (s.equals("leave")) { + receiveGossip.stop(); + scheduler.shutdownNow(); + scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); + MembershipBean mBean = membershipList.get(pid); + mBean.hearbeatLastReceived = -1; + mBean.timeStamp = System.currentTimeMillis(); + membershipList.put(pid, mBean); + System.out.println("just before gossip thread"); + Thread gossipOneLastTime = new Thread(new SendGossipThread( + 0)); + gossipOneLastTime.start(); + System.out.println("going to break"); + break; + } } + System.out.println("exiting"); + } catch (Exception e) { + System.out.println("Exception occured"); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 705491a..a9f32a1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -75,7 +75,7 @@ private void mergeIncomingMembershipList() UDPBean receivedMBean = entry.getValue(); //Check if pid present in this entry is also present in our membership list. - if(GroupMembership.membershipList.containsKey(receivedPid)) + if(GroupMembership.membershipList.containsKey(receivedPid) && receivedMBean.hearbeatLastReceived < 0) { MembershipBean currentMBean = GroupMembership.membershipList.get(receivedPid); @@ -99,7 +99,7 @@ private void mergeIncomingMembershipList() } else if (receivedMBean.hearbeatLastReceived <= 0 || currentMBean.hearbeatLastReceived <= 0) continue; //If the incoming entry's heartbeat is greater than current node's membership list,then update the list. - if(receivedMBean.hearbeatLastReceived > currentMBean.hearbeatLastReceived) + /*if(receivedMBean.hearbeatLastReceived > currentMBean.hearbeatLastReceived) { currentMBean.hearbeatLastReceived = receivedMBean.hearbeatLastReceived; currentMBean.timeStamp = System.currentTimeMillis(); @@ -108,9 +108,9 @@ private void mergeIncomingMembershipList() currentMBean.toBeDeleted = false; } GroupMembership.membershipList.put(receivedPid, currentMBean); - } + }*/ } - else + else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBean.hearbeatLastReceived > 0) { //JOIN : If the incoming entry is not in our membership list then it means a new node has joined. if(receivedMBean.hearbeatLastReceived <= 0) continue; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index c1cda11..4c46aac 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -35,24 +35,25 @@ public void run() { Map.Entry entry = iterator.next(); MembershipBean membershipBean = entry.getValue(); + if(membershipBean.hearbeatLastReceived <= 0) { + //If current node's heartbeat is less than zero ie has Voluntarily left,then don't do anything + if(membershipBean.hearbeatLastReceived <= 0 && entry.getKey().equals(GroupMembership.pid)) { + continue; + } - //If current node's heartbeat is less than zero ie has Voluntarily left,then don't do anything - if(membershipBean.hearbeatLastReceived <= 0 && entry.getKey().equals(GroupMembership.pid)) { - continue; - } - - //Remove entry which is marked toBeDeleted - if (membershipBean.toBeDeleted) - { - GroupMembership.membershipList.remove(entry.getKey()); - } - //If the membership list entry has timed-out then mark it toBeDeleted - else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000) - { - membershipBean.toBeDeleted = true; - if (membershipBean.hearbeatLastReceived > 0) { - System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); - log.info("CRASHED - - - " + entry.getKey()); + //Remove entry which is marked toBeDeleted + if (membershipBean.toBeDeleted) + { + GroupMembership.membershipList.remove(entry.getKey()); + } + //If the membership list entry has timed-out then mark it toBeDeleted + else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000) + { + membershipBean.toBeDeleted = true; + /*if (membershipBean.hearbeatLastReceived > 0) { + System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); + log.info("CRASHED - - - " + entry.getKey()); + }*/ } } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java index b487269..d7e3c88 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java @@ -42,6 +42,7 @@ public void run() int maxTries = 100; while(gossipGroupSize > 0 && (maxTries-- > 0)) { + System.out.println("in while with gossip groupsize:"+gossipGroupSize); MembershipBean mBean = GroupMembership.membershipList.get(keys[generator.nextInt(listSize)]); if(mBean.toBeDeleted) continue; From 4914c966773e0a97357ad170bd71a830eadcb2af Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sat, 2 Nov 2013 23:56:32 -0500 Subject: [PATCH 02/48] hash changes --- .../groupmembership/GroupMembership.java | 14 +++++- .../HeartbeatIncrementerThread.java | 45 ++++++++----------- .../boltdb/groupmembership/MergeThread.java | 2 +- .../SendMembershipListThread.java | 2 +- .../groupmembership/beans/MembershipBean.java | 5 ++- .../boltdb/groupmembership/beans/UDPBean.java | 5 ++- 6 files changed, 39 insertions(+), 34 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index e9a7c18..d3ee4ef 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -94,7 +94,9 @@ public void run() { pid += "-" + args[3]; initializeLogger(args[3]); } - + + long hashValue = computeHash(pid); + // Insert the current machine into the membership list with // heartbeat=1. This single entry is going to be sent to the contact // node for joining the cluster. @@ -102,7 +104,7 @@ public void run() { GroupMembership.pid, new MembershipBean( InetAddress.getLocalHost().getHostName(), 1, System - .currentTimeMillis(), false)); + .currentTimeMillis(), hashValue, false)); // Load all the parameters needed from the property file. Properties prop = new Properties(); @@ -197,4 +199,12 @@ public void run() { } } + + private long computeHash(String pid) { + long hashValue = 13; + for (int i=0; i < pid.length(); i++) { + hashValue = hashValue*31 + pid.charAt(i); + } + return hashValue % 1000001L; + } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/HeartbeatIncrementerThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/HeartbeatIncrementerThread.java index 3dbf562..ebee07b 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/HeartbeatIncrementerThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/HeartbeatIncrementerThread.java @@ -6,33 +6,26 @@ /** * This class increments the hearbeat of the current node. - * + * */ -public class HeartbeatIncrementerThread implements Runnable -{ - //@Override - public void run() - { - try - { - MembershipBean entry = GroupMembership.membershipList.get(GroupMembership.pid); - if(entry == null) - { - GroupMembership.membershipList.putIfAbsent(GroupMembership.pid, new MembershipBean(InetAddress.getLocalHost().getHostAddress(), 1, System.currentTimeMillis(), false)); - } - else - { - //Dont update the heartbeat if its less than zero which means the node has voluntarily left. - if(entry.hearbeatLastReceived <= 0) return; - //Increment the heartbeat - entry.hearbeatLastReceived++; - //Update the timestamp - entry.timeStamp = System.currentTimeMillis(); - GroupMembership.membershipList.put(GroupMembership.pid, entry); - } - } - catch(Exception e) - { +public class HeartbeatIncrementerThread implements Runnable { + // @Override + public void run() { + try { + MembershipBean entry = GroupMembership.membershipList + .get(GroupMembership.pid); + + // Dont update the heartbeat if its less than zero which means the + // node has voluntarily left. + if (entry.hearbeatLastReceived <= 0) + return; + // Increment the heartbeat + entry.hearbeatLastReceived++; + // Update the timestamp + entry.timeStamp = System.currentTimeMillis(); + GroupMembership.membershipList.put(GroupMembership.pid, entry); + + } catch (Exception e) { System.out.println("EXCEPTION:In HeartbeatIncrementerThread"); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index a9f32a1..db5bb88 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -115,7 +115,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea //JOIN : If the incoming entry is not in our membership list then it means a new node has joined. if(receivedMBean.hearbeatLastReceived <= 0) continue; String receivedHost = receivedPid.split(GroupMembership.pidDelimiter)[0]; - MembershipBean mBean = new MembershipBean(receivedHost, receivedMBean.hearbeatLastReceived, System.currentTimeMillis(), false); + MembershipBean mBean = new MembershipBean(receivedHost, receivedMBean.hearbeatLastReceived, System.currentTimeMillis(), receivedMBean.hashValue, false); MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); if (returnVal == null) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendMembershipListThread.java index a0f3e14..8f288cc 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendMembershipListThread.java @@ -49,7 +49,7 @@ public void run() Map.Entry entry = iterator.next(); if(entry.getValue().toBeDeleted) continue; - listToSend.put(entry.getKey(), new UDPBean(entry.getValue().hearbeatLastReceived)); + listToSend.put(entry.getKey(), new UDPBean(entry.getValue().hearbeatLastReceived,entry.getValue().hashValue)); } String json = gson.toJson(listToSend, typeOfHashMap); byte[] jsonBytes = json.getBytes(); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java index 3b03a67..d806221 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java @@ -10,10 +10,11 @@ public class MembershipBean extends UDPBean { public boolean toBeDeleted; public MembershipBean(String ipaddress, long hearbeatLastReceived, long timeStamp, - boolean toBeDeleted) { - super(hearbeatLastReceived); + long hashValue, boolean toBeDeleted) { + super(hearbeatLastReceived, hashValue); this.hostname = ipaddress; this.timeStamp = timeStamp; + this.hashValue = hashValue; this.toBeDeleted = toBeDeleted; } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/UDPBean.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/UDPBean.java index d380022..73550be 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/UDPBean.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/UDPBean.java @@ -7,10 +7,11 @@ public class UDPBean { public long hearbeatLastReceived; - - public UDPBean(long hearbeatLastReceived) { + public long hashValue; + public UDPBean(long hearbeatLastReceived, long hashValue) { super(); this.hearbeatLastReceived = hearbeatLastReceived; + this.hashValue = hashValue; } From dfb6d33212ccac636aa0b03d877e5ff9894d7fa1 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sat, 2 Nov 2013 23:58:16 -0500 Subject: [PATCH 03/48] hash changes --- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 16 ++++++ .../java/edu/uiuc/boltdb/BoltDBServer.java | 50 +++++++++++++++++++ 2 files changed, 66 insertions(+) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java new file mode 100644 index 0000000..a7bb277 --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -0,0 +1,16 @@ +package edu.uiuc.boltdb; + +import java.rmi.Remote; +import java.rmi.RemoteException; + +public interface BoltDBProtocol extends Remote { + + public void insert(K key, V value) throws RemoteException; + + public V lookup(K key) throws RemoteException; + + public void update(K key, V value) throws RemoteException; + + public void delete(K key) throws RemoteException; + +} diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java new file mode 100644 index 0000000..25ca33e --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -0,0 +1,50 @@ +package edu.uiuc.boltdb; + +import java.rmi.RemoteException; +import java.rmi.server.UnicastRemoteObject; +import java.util.Map; +import java.util.TreeMap; + +import edu.uiuc.boltdb.groupmembership.GroupMembership; + +public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { + + + private static final long serialVersionUID = 1L; + + protected BoltDBServer() throws RemoteException { + super(); + // TODO Auto-generated constructor stub + } + + /** + * @param args + */ + private static Map KVStore = new TreeMap(); + + public static void main(String[] args) { + + Runnable groupMembership = new GroupMembership(args); + Thread groupMembershipThread = new Thread(groupMembership); + groupMembershipThread.start(); + } + + public void insert(Long key, Object value) throws RemoteException { + KVStore.put(key, value); + } + + public Object lookup(Long key) throws RemoteException { + return KVStore.get(key); + } + + public void update(Long key, Object value) throws RemoteException { + KVStore.put(key, value); + } + + public void delete(Long key) throws RemoteException { + KVStore.remove(key); + } + + + +} From d9247db104880a25291b177d7b92ab3aedd20908 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 3 Nov 2013 00:34:32 -0500 Subject: [PATCH 04/48] Adding BoltDBClient --- boltdb/boltdb.prop | 7 +++ .../java/edu/uiuc/boltdb/BoltDBClient.java | 55 +++++++++++++++++++ 2 files changed, 62 insertions(+) create mode 100644 boltdb/boltdb.prop create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java diff --git a/boltdb/boltdb.prop b/boltdb/boltdb.prop new file mode 100644 index 0000000..5f95c23 --- /dev/null +++ b/boltdb/boltdb.prop @@ -0,0 +1,7 @@ +machines.address=192.17.11.8:6789,192.17.11.7:6789,192.17.11.18:6789,192.17.11.19:6789 +groupmembership.lossrate=0 +groupmembership.contact=siebl-0218-07.ews.illinois.edu +groupmembership.tfail=3 +groupmembership.heartbeat.freq=600 +groupmembership.refreshMembershipList.freq=1000 +groupmembership.gossip.freq=1000 diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java new file mode 100644 index 0000000..201360a --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -0,0 +1,55 @@ +package edu.uiuc.boltdb; + +import java.io.BufferedReader; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStreamReader; +import java.net.MalformedURLException; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.rmi.RemoteException; +import java.util.Properties; + +public class BoltDBClient { + + private BoltDBProtocol boltDBServer = null; + + public BoltDBClient(String rmiString) throws MalformedURLException, RemoteException, NotBoundException{ + boltDBServer = (BoltDBProtocol) Naming.lookup(rmiString + "/BoldDBServer"); + } + + /** + * @param args + * @throws IOException + * @throws NotBoundException + */ + public static void main(String[] args) throws IOException, NotBoundException { + // TODO Auto-generated method stub + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.server"); + BoltDBClient boltDBClient = new BoltDBClient(rmiString); + boltDBClient.runClientShell(); + } + + private void runClientShell() throws IOException{ + //TODO : Write code to similate a unix shell + String commandString = ""; + BufferedReader console = new BufferedReader(new InputStreamReader(System.in)); + + // Break out with Ctrl+C + while (true) { + // Read user's input + System.out.print("boltdb>"); + commandString = console.readLine(); + + // If the user entered a return, just loop again + if (commandString.equals("")) + continue; + + + } + } +} From 7c59dbc20ca590d5973dc66c6738633c7c1a226a Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 3 Nov 2013 14:32:37 -0600 Subject: [PATCH 05/48] BoldDBClient and boltdb.prop --- boltdb/boltdb.prop | 1 + .../java/edu/uiuc/boltdb/BoltDBClient.java | 133 ++++++++++++++++-- 2 files changed, 120 insertions(+), 14 deletions(-) diff --git a/boltdb/boltdb.prop b/boltdb/boltdb.prop index 5f95c23..60a8072 100644 --- a/boltdb/boltdb.prop +++ b/boltdb/boltdb.prop @@ -5,3 +5,4 @@ groupmembership.tfail=3 groupmembership.heartbeat.freq=600 groupmembership.refreshMembershipList.freq=1000 groupmembership.gossip.freq=1000 +boltdb.server=172.16.149.48 diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index 201360a..4502ecc 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -9,13 +9,19 @@ import java.rmi.NotBoundException; import java.rmi.RemoteException; import java.util.Properties; +import java.util.StringTokenizer; public class BoltDBClient { private BoltDBProtocol boltDBServer = null; - public BoltDBClient(String rmiString) throws MalformedURLException, RemoteException, NotBoundException{ - boltDBServer = (BoltDBProtocol) Naming.lookup(rmiString + "/BoldDBServer"); + public BoltDBClient(String rmiString) throws MalformedURLException, RemoteException, NotBoundException { + System.out.println(rmiString); + if(System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); + System.out.println("HERE"); } /** @@ -23,19 +29,24 @@ public BoltDBClient(String rmiString) throws MalformedURLException, RemoteExcept * @throws IOException * @throws NotBoundException */ - public static void main(String[] args) throws IOException, NotBoundException { + public static void main(String[] args) { // TODO Auto-generated method stub - Properties prop = new Properties(); - FileInputStream fis = new FileInputStream("./boltdb.prop"); - prop.load(fis); - fis.close(); - String rmiString = prop.getProperty("boltdb.server"); - BoltDBClient boltDBClient = new BoltDBClient(rmiString); - boltDBClient.runClientShell(); + try { + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.server"); + BoltDBClient boltDBClient = new BoltDBClient(rmiString); + boltDBClient.runClientShell(); + } catch(Exception e) { + e.printStackTrace(); + System.out.println("Operation Failed"); + } } - private void runClientShell() throws IOException{ - //TODO : Write code to similate a unix shell + private void runClientShell() throws IOException { + // Simulate a unix shell String commandString = ""; BufferedReader console = new BufferedReader(new InputStreamReader(System.in)); @@ -48,8 +59,102 @@ private void runClientShell() throws IOException{ // If the user entered a return, just loop again if (commandString.equals("")) continue; - - + handleCommand(commandString); + } + } + + private void handleCommand(String commandString) throws RemoteException { + StringTokenizer stk = new StringTokenizer(commandString); + if(stk.countTokens() < 2) { + printUsage(0); + return; + } + + // The Command Type + String commandType = stk.nextToken(); + + if(commandType.equals("insert")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + String value = ""; + if(stk.hasMoreTokens()) { + value = stk.nextToken(); + } + else { + printUsage(1); + return; + } + // Perform Insert Operation + boltDBServer.insert(key, value); + } else if(commandType.equals("update")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + String value = ""; + if(stk.hasMoreTokens()) { + value = stk.nextToken(); + } + else { + printUsage(2); + return; + } + // Perform Update Operation + boltDBServer.update(key, value); + } else if(commandType.equals("lookup")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + // Perform Look Up Operation + String value = (String)boltDBServer.lookup(key); + System.out.println("Look Up Result : " + value); + } else if(commandType.equals("delete")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + // Perform Delete Operation + boltDBServer.delete(key); + System.out.println("Key Value Pair Deleted"); + } else { + printUsage(0); + return; + } + } + + private long parseKey(String keyStr) { + long key; + try { + key = Long.parseLong(keyStr); + if(key < 0L || key > 1000000L) { + System.out.println("Invalid Key Range. Key should be in the Range 0 - 1000000"); + return -1L; + } + return key; + } catch(NumberFormatException nfe) { + System.out.println("Invalid Key : Please enter an Integer value for key"); + return -1L; + } + } + + private void printUsage(int type) { + System.out.println("Invalid Command"); + System.out.println("Usage : "); + switch(type) { + case 1: System.out.println("insert "); + break; + case 2: System.out.println("update "); + break; + case 3: System.out.println("lookukp "); + break; + case 4: System.out.println("delete "); + break; + default:System.out.println("insert "); + System.out.println("update "); + System.out.println("lookup "); + System.out.println("delete "); + break; } + System.out.println(" is an integer value in the range 0 - 1000000"); + System.out.println(); } } From a8177c3c62ae834ddaf383410b5c18c7d0604302 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 3 Nov 2013 15:53:07 -0600 Subject: [PATCH 06/48] rmi stuff --- boltdb/pom.xml | 20 +++++++++++++++++++ .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 10 +++++----- .../java/edu/uiuc/boltdb/BoltDBServer.java | 18 ++++++++++------- 3 files changed, 36 insertions(+), 12 deletions(-) diff --git a/boltdb/pom.xml b/boltdb/pom.xml index ec72118..4a57aad 100644 --- a/boltdb/pom.xml +++ b/boltdb/pom.xml @@ -13,7 +13,27 @@ UTF-8 + + + + + org.codehaus.mojo + rmic-maven-plugin + 1.2.1 + + + rmi compilation + + rmic + + + + + + + + junit diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index a7bb277..925e50e 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -3,14 +3,14 @@ import java.rmi.Remote; import java.rmi.RemoteException; -public interface BoltDBProtocol extends Remote { +public interface BoltDBProtocol extends Remote { - public void insert(K key, V value) throws RemoteException; + public void insert(long key, String value) throws RemoteException; - public V lookup(K key) throws RemoteException; + public String lookup(long key) throws RemoteException; - public void update(K key, V value) throws RemoteException; + public void update(long key, String value) throws RemoteException; - public void delete(K key) throws RemoteException; + public void delete(long key) throws RemoteException; } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 25ca33e..a70b686 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -1,5 +1,7 @@ package edu.uiuc.boltdb; +import java.net.MalformedURLException; +import java.rmi.Naming; import java.rmi.RemoteException; import java.rmi.server.UnicastRemoteObject; import java.util.Map; @@ -7,7 +9,7 @@ import edu.uiuc.boltdb.groupmembership.GroupMembership; -public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { +public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { private static final long serialVersionUID = 1L; @@ -20,28 +22,30 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - private static Map KVStore = new TreeMap(); + private static Map KVStore = new TreeMap(); - public static void main(String[] args) { + public static void main(String[] args) throws RemoteException, MalformedURLException { Runnable groupMembership = new GroupMembership(args); Thread groupMembershipThread = new Thread(groupMembership); groupMembershipThread.start(); + Naming.rebind ("KVStore", new BoltDBServer()); + System.out.println ("Server is ready."); } - public void insert(Long key, Object value) throws RemoteException { + public void insert(long key, String value) throws RemoteException { KVStore.put(key, value); } - public Object lookup(Long key) throws RemoteException { + public String lookup(long key) throws RemoteException { return KVStore.get(key); } - public void update(Long key, Object value) throws RemoteException { + public void update(long key, String value) throws RemoteException { KVStore.put(key, value); } - public void delete(Long key) throws RemoteException { + public void delete(long key) throws RemoteException { KVStore.remove(key); } From 3b7cfb4e5d03d59cdf76e9d59f3c6e716f125850 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 3 Nov 2013 15:56:18 -0600 Subject: [PATCH 07/48] rmi stuff --- .../java/edu/uiuc/boltdb/BoltDBClient.java | 160 ++++++++++++++++++ .../edu/uiuc/boltdb/BoltDBClientTemp.java | 31 ++++ 2 files changed, 191 insertions(+) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java new file mode 100644 index 0000000..dfad16a --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -0,0 +1,160 @@ +package edu.uiuc.boltdb; + +import java.io.BufferedReader; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStreamReader; +import java.net.MalformedURLException; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.rmi.RemoteException; +import java.util.Properties; +import java.util.StringTokenizer; + +public class BoltDBClient { + + private BoltDBProtocol boltDBServer = null; + + public BoltDBClient(String rmiString) throws MalformedURLException, RemoteException, NotBoundException { + System.out.println(rmiString); + if(System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/Hello"); + System.out.println("HERE"); + } + + /** + * @param args + * @throws IOException + * @throws NotBoundException + */ + public static void main(String[] args) { + // TODO Auto-generated method stub + try { + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.server"); + BoltDBClient boltDBClient = new BoltDBClient(rmiString); + boltDBClient.runClientShell(); + } catch(Exception e) { + e.printStackTrace(); + System.out.println("Operation Failed"); + } + } + + private void runClientShell() throws IOException { + // Simulate a unix shell + String commandString = ""; + BufferedReader console = new BufferedReader(new InputStreamReader(System.in)); + + // Break out with Ctrl+C + while (true) { + // Read user's input + System.out.print("boltdb>"); + commandString = console.readLine(); + + // If the user entered a return, just loop again + if (commandString.equals("")) + continue; + handleCommand(commandString); + } + } + + private void handleCommand(String commandString) throws RemoteException { + StringTokenizer stk = new StringTokenizer(commandString); + if(stk.countTokens() < 2) { + printUsage(0); + return; + } + + // The Command Type + String commandType = stk.nextToken(); + + if(commandType.equals("insert")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + String value = ""; + if(stk.hasMoreTokens()) { + value = stk.nextToken(); + } + else { + printUsage(1); + return; + } + // Perform Insert Operation + boltDBServer.insert(key, value); + } else if(commandType.equals("update")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + String value = ""; + if(stk.hasMoreTokens()) { + value = stk.nextToken(); + } + else { + printUsage(2); + return; + } + // Perform Update Operation + boltDBServer.update(key, value); + } else if(commandType.equals("lookup")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + // Perform Look Up Operation + String value = (String)boltDBServer.lookup(key); + System.out.println("Look Up Result : " + value); + } else if(commandType.equals("delete")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + // Perform Delete Operation + boltDBServer.delete(key); + System.out.println("Key Value Pair Deleted"); + } else { + printUsage(0); + return; + } + } + + private long parseKey(String keyStr) { + long key; + try { + key = Long.parseLong(keyStr); + if(key < 0L || key > 1000000L) { + System.out.println("Invalid Key Range. Key should be in the Range 0 - 1000000"); + return -1L; + } + return key; + } catch(NumberFormatException nfe) { + System.out.println("Invalid Key : Please enter an Integer value for key"); + return -1L; + } + } + + private void printUsage(int type) { + System.out.println("Invalid Command"); + System.out.println("Usage : "); + switch(type) { + case 1: System.out.println("insert "); + break; + case 2: System.out.println("update "); + break; + case 3: System.out.println("lookukp "); + break; + case 4: System.out.println("delete "); + break; + default:System.out.println("insert "); + System.out.println("update "); + System.out.println("lookup "); + System.out.println("delete "); + break; + } + System.out.println(" is an integer value in the range 0 - 1000000"); + System.out.println(); + } +} diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java new file mode 100644 index 0000000..0d8fdef --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java @@ -0,0 +1,31 @@ +package edu.uiuc.boltdb; + +import java.net.MalformedURLException; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.rmi.RMISecurityManager; +import java.rmi.RemoteException; + + +public class BoltDBClientTemp { + + /** + * @param args + * @throws NotBoundException + * @throws RemoteException + * @throws MalformedURLException + */ + public static void main(String[] args) throws MalformedURLException, RemoteException, NotBoundException { + // TODO Auto-generated method stub + System.out.println("starting security manager"); + if (System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + BoltDBProtocol boltdb = + (BoltDBProtocol) Naming.lookup ("//localhost/KVStore"); + boltdb.insert(123l, "a"); + System.out.println(boltdb.lookup(123l)); + + } + +} From 0560b302c2c84cb206095af41f7847d09b3b23c0 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Mon, 4 Nov 2013 10:28:52 -0600 Subject: [PATCH 08/48] Server request forwarding --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 107 ++++++++++++++++-- 1 file changed, 100 insertions(+), 7 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index a70b686..4dcdf5c 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -1,13 +1,17 @@ package edu.uiuc.boltdb; +import java.net.InetAddress; import java.net.MalformedURLException; +import java.net.UnknownHostException; import java.rmi.Naming; +import java.rmi.NotBoundException; import java.rmi.RemoteException; import java.rmi.server.UnicastRemoteObject; import java.util.Map; import java.util.TreeMap; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.groupmembership.beans.MembershipBean; public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { @@ -16,7 +20,6 @@ public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol protected BoltDBServer() throws RemoteException { super(); - // TODO Auto-generated constructor stub } /** @@ -34,21 +37,111 @@ public static void main(String[] args) throws RemoteException, MalformedURLExcep } public void insert(long key, String value) throws RemoteException { - KVStore.put(key, value); + String targetHost = getTargetHost(key); + try { + if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { + KVStore.put(key, value); + } else { + BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); + targetServer.insert(key, value); + } + } catch (UnknownHostException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (MalformedURLException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (NotBoundException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } } public String lookup(long key) throws RemoteException { - return KVStore.get(key); + if(checkLocalStore(key)) { + return KVStore.get(key); + } else { + try { + String targetHost = getTargetHost(key); + BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); + return targetServer.lookup(key); + } catch (MalformedURLException e) { + e.printStackTrace(); + } catch (NotBoundException e) { + e.printStackTrace(); + } + } + return null; + } public void update(long key, String value) throws RemoteException { - KVStore.put(key, value); + String targetHost = getTargetHost(key); + try { + if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { + KVStore.put(key, value); + } else { + BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); + targetServer.update(key, value); + } + } catch (UnknownHostException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (MalformedURLException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (NotBoundException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } } public void delete(long key) throws RemoteException { - KVStore.remove(key); - } + if(checkLocalStore(key)) { + KVStore.remove(key); + return; + } else { + try { + String targetHost = getTargetHost(key); + BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); + targetServer.delete(key); + return; + } catch (MalformedURLException e) { + e.printStackTrace(); + } catch (NotBoundException e) { + e.printStackTrace(); + } + } + } -} + private boolean checkLocalStore(long key) { + return KVStore.containsKey(computeHash((new Long(key)).toString())); + } + + private String getTargetHost(long key) { + long keyHash = computeHash((new Long(key).toString())); + String targetHost = null; + String firstHost = null; + + for (Map.Entry entry : GroupMembership.membershipList.entrySet()) + { + if(keyHash <= entry.getValue().hashValue) { + targetHost = entry.getValue().hostname; + continue; + } + else + return targetHost; + } + return firstHost; + } + + private long computeHash(String pid) { + long hashValue = 13; + for (int i=0; i < pid.length(); i++) { + hashValue = hashValue*31 + pid.charAt(i); + } + return hashValue % 1000001L; + } +} \ No newline at end of file From 5d2e91ef5255fdc8692d23d6d7e994d66610474d Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Mon, 4 Nov 2013 11:07:32 -0600 Subject: [PATCH 09/48] pom changes --- boltdb/pom.xml | 21 ++++++++----------- .../java/edu/uiuc/boltdb/BoltDBServer.java | 8 +++++-- 2 files changed, 15 insertions(+), 14 deletions(-) diff --git a/boltdb/pom.xml b/boltdb/pom.xml index 4a57aad..6116ab8 100644 --- a/boltdb/pom.xml +++ b/boltdb/pom.xml @@ -14,24 +14,21 @@ UTF-8 - - - - org.codehaus.mojo - rmic-maven-plugin - 1.2.1 - + + + org.codehaus.mojo + rmic-maven-plugin + 1.2.1 + - rmi compilation + rmic-process-classes rmic - - - - + + diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index a70b686..f136516 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -3,6 +3,7 @@ import java.net.MalformedURLException; import java.rmi.Naming; import java.rmi.RemoteException; +import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; import java.util.Map; import java.util.TreeMap; @@ -11,8 +12,10 @@ public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { - - private static final long serialVersionUID = 1L; + /** + * + */ + private static final long serialVersionUID = 5195393553928167809L; protected BoltDBServer() throws RemoteException { super(); @@ -29,6 +32,7 @@ public static void main(String[] args) throws RemoteException, MalformedURLExcep Runnable groupMembership = new GroupMembership(args); Thread groupMembershipThread = new Thread(groupMembership); groupMembershipThread.start(); + LocateRegistry.createRegistry(1099); Naming.rebind ("KVStore", new BoltDBServer()); System.out.println ("Server is ready."); } From d828dda21680f28e13d9519ee01f02e11792ea61 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Mon, 4 Nov 2013 11:16:56 -0600 Subject: [PATCH 10/48] BoltDBServer Show functionality --- .../java/edu/uiuc/boltdb/BoltDBClient.java | 4 +- .../java/edu/uiuc/boltdb/BoltDBServer.java | 41 +++++++++++++++++++ 2 files changed, 42 insertions(+), 3 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index 2466ae7..c0a7ce6 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -20,9 +20,7 @@ public BoltDBClient(String rmiString) throws MalformedURLException, RemoteExcept if(System.getSecurityManager() == null) { System.setSecurityManager(new SecurityManager()); } - boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); - System.out.println("HERE"); } /** @@ -121,7 +119,7 @@ private void handleCommand(String commandString) throws RemoteException { return; } } - + private long parseKey(String keyStr) { long key; try { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 4dcdf5c..e310fd3 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -1,5 +1,8 @@ package edu.uiuc.boltdb; +import java.io.BufferedReader; +import java.io.IOException; +import java.io.InputStreamReader; import java.net.InetAddress; import java.net.MalformedURLException; import java.net.UnknownHostException; @@ -34,6 +37,44 @@ public static void main(String[] args) throws RemoteException, MalformedURLExcep groupMembershipThread.start(); Naming.rebind ("KVStore", new BoltDBServer()); System.out.println ("Server is ready."); + + } + + private void runServerShell() throws IOException { + // Simulate a unix shell + String commandString = ""; + BufferedReader console = new BufferedReader(new InputStreamReader(System.in)); + + // Break out with Ctrl+C + while (true) { + // Read user's input + System.out.print("boltdb>"); + commandString = console.readLine(); + + // If the user entered a return, just loop again + if (commandString.equals("")) + continue; + else if (commandString.equals("show")) { + System.out.println("-------------------------------------------------"); + System.out.println("Membership List : "); + System.out.println("-------------------------------------------------"); + for (Map.Entry entry : GroupMembership.membershipList.entrySet()) + { + System.out.println(entry); + } + System.out.println("-------------------------------------------------"); + System.out.println(); + System.out.println("-------------------------------------------------"); + System.out.println("Key Value Store : "); + System.out.println("-------------------------------------------------"); + for (Map.Entry entry : KVStore.entrySet()) + { + System.out.println(entry.getKey() + " ---> " + entry.getValue()); + } + System.out.println("-------------------------------------------------"); + System.out.println(); + } + } } public void insert(long key, String value) throws RemoteException { From 2927a2b764e77119cb5d8c74c28e23382fa459b2 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Mon, 4 Nov 2013 12:21:54 -0600 Subject: [PATCH 11/48] finding successor node --- .../groupmembership/GroupMembership.java | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index d3ee4ef..9ed8cc7 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -6,7 +6,9 @@ import java.io.InputStreamReader; import java.net.InetAddress; import java.util.Date; +import java.util.Iterator; import java.util.Properties; +import java.util.Map.Entry; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.Executors; import java.util.concurrent.ScheduledExecutorService; @@ -207,4 +209,20 @@ private long computeHash(String pid) { } return hashValue % 1000001L; } + + public static String getSuccessorNodeOf(long keyHash) { + Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); + long minClockwiseDistance = 1000000L; + String successorNode = new String(); + while(itr.hasNext()) { + Entry entry = itr.next(); + long hashCurrent = entry.getValue().hashValue; + long clockWiseDistance = keyHash > hashCurrent ? 1000000l - (keyHash - hashCurrent) : hashCurrent - keyHash; + if(minClockwiseDistance > clockWiseDistance) { + minClockwiseDistance = clockWiseDistance; + successorNode = entry.getKey(); + } + } + return successorNode; + } } From 265c854236cfc1e4ab7436264612b5478adc6c1f Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Mon, 4 Nov 2013 12:32:32 -0600 Subject: [PATCH 12/48] finding successor node --- .../edu/uiuc/boltdb/groupmembership/GroupMembership.java | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 9ed8cc7..4141c99 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -213,16 +213,16 @@ private long computeHash(String pid) { public static String getSuccessorNodeOf(long keyHash) { Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); long minClockwiseDistance = 1000000L; - String successorNode = new String(); + String successorHost = new String(); while(itr.hasNext()) { Entry entry = itr.next(); long hashCurrent = entry.getValue().hashValue; long clockWiseDistance = keyHash > hashCurrent ? 1000000l - (keyHash - hashCurrent) : hashCurrent - keyHash; if(minClockwiseDistance > clockWiseDistance) { minClockwiseDistance = clockWiseDistance; - successorNode = entry.getKey(); + successorHost = entry.getValue().hostname; } } - return successorNode; + return successorHost; } } From 5873a76ebd2298b3690f709b27ef3ba15a6df651 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Mon, 4 Nov 2013 13:14:39 -0600 Subject: [PATCH 13/48] A lot of changes --- .../java/edu/uiuc/boltdb/BoltDBClient.java | 8 +- .../edu/uiuc/boltdb/BoltDBClientTemp.java | 31 ------- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 8 +- .../java/edu/uiuc/boltdb/BoltDBServer.java | 93 ++++++------------- .../groupmembership/GroupMembership.java | 33 ++++++- .../groupmembership/SendGossipThread.java | 1 - 6 files changed, 64 insertions(+), 110 deletions(-) delete mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index c0a7ce6..c01e688 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -85,7 +85,7 @@ private void handleCommand(String commandString) throws RemoteException { return; } // Perform Insert Operation - boltDBServer.insert(key, value); + boltDBServer.insert(key, value, true); } else if(commandType.equals("update")) { String keyStr = stk.nextToken(); long key = parseKey(keyStr); @@ -99,20 +99,20 @@ private void handleCommand(String commandString) throws RemoteException { return; } // Perform Update Operation - boltDBServer.update(key, value); + boltDBServer.update(key, value, true); } else if(commandType.equals("lookup")) { String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; // Perform Look Up Operation - String value = (String)boltDBServer.lookup(key); + String value = (String)boltDBServer.lookup(key, true); System.out.println("Look Up Result : " + value); } else if(commandType.equals("delete")) { String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; // Perform Delete Operation - boltDBServer.delete(key); + boltDBServer.delete(key, true); System.out.println("Key Value Pair Deleted"); } else { printUsage(0); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java deleted file mode 100644 index 0d8fdef..0000000 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClientTemp.java +++ /dev/null @@ -1,31 +0,0 @@ -package edu.uiuc.boltdb; - -import java.net.MalformedURLException; -import java.rmi.Naming; -import java.rmi.NotBoundException; -import java.rmi.RMISecurityManager; -import java.rmi.RemoteException; - - -public class BoltDBClientTemp { - - /** - * @param args - * @throws NotBoundException - * @throws RemoteException - * @throws MalformedURLException - */ - public static void main(String[] args) throws MalformedURLException, RemoteException, NotBoundException { - // TODO Auto-generated method stub - System.out.println("starting security manager"); - if (System.getSecurityManager() == null) { - System.setSecurityManager(new SecurityManager()); - } - BoltDBProtocol boltdb = - (BoltDBProtocol) Naming.lookup ("//localhost/KVStore"); - boltdb.insert(123l, "a"); - System.out.println(boltdb.lookup(123l)); - - } - -} diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index 925e50e..24cb078 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -5,12 +5,12 @@ public interface BoltDBProtocol extends Remote { - public void insert(long key, String value) throws RemoteException; + public void insert(long key, String value, boolean canBeForwarded) throws RemoteException; - public String lookup(long key) throws RemoteException; + public String lookup(long key, boolean canBeForwarded) throws RemoteException; - public void update(long key, String value) throws RemoteException; + public void update(long key, String value, boolean canBeForwarded) throws RemoteException; - public void delete(long key) throws RemoteException; + public void delete(long key, boolean canBeForwarded) throws RemoteException; } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 60fdfd6..574bcbf 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -31,64 +31,25 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - private static Map KVStore = new TreeMap(); + public static Map KVStore = new TreeMap(); - public static void main(String[] args) throws RemoteException, MalformedURLException { + public static void main(String[] args) throws IOException { Runnable groupMembership = new GroupMembership(args); Thread groupMembershipThread = new Thread(groupMembership); groupMembershipThread.start(); LocateRegistry.createRegistry(1099); Naming.rebind ("KVStore", new BoltDBServer()); - System.out.println ("Server is ready."); - } - private void runServerShell() throws IOException { - // Simulate a unix shell - String commandString = ""; - BufferedReader console = new BufferedReader(new InputStreamReader(System.in)); - - // Break out with Ctrl+C - while (true) { - // Read user's input - System.out.print("boltdb>"); - commandString = console.readLine(); - - // If the user entered a return, just loop again - if (commandString.equals("")) - continue; - else if (commandString.equals("show")) { - System.out.println("-------------------------------------------------"); - System.out.println("Membership List : "); - System.out.println("-------------------------------------------------"); - for (Map.Entry entry : GroupMembership.membershipList.entrySet()) - { - System.out.println(entry); - } - System.out.println("-------------------------------------------------"); - System.out.println(); - System.out.println("-------------------------------------------------"); - System.out.println("Key Value Store : "); - System.out.println("-------------------------------------------------"); - for (Map.Entry entry : KVStore.entrySet()) - { - System.out.println(entry.getKey() + " ---> " + entry.getValue()); - } - System.out.println("-------------------------------------------------"); - System.out.println(); - } - } - } - - public void insert(long key, String value) throws RemoteException { - String targetHost = getTargetHost(key); + public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { + String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); try { if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { KVStore.put(key, value); - } else { + } else if(canBeForwarded){ BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - targetServer.insert(key, value); + targetServer.insert(key, value, false); } } catch (UnknownHostException e) { // TODO Auto-generated catch block @@ -102,14 +63,14 @@ public void insert(long key, String value) throws RemoteException { } } - public String lookup(long key) throws RemoteException { + public String lookup(long key, boolean canBeForwarded) throws RemoteException { if(checkLocalStore(key)) { return KVStore.get(key); - } else { + } else if(canBeForwarded){ try { - String targetHost = getTargetHost(key); + String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - return targetServer.lookup(key); + return targetServer.lookup(key, false); } catch (MalformedURLException e) { e.printStackTrace(); } catch (NotBoundException e) { @@ -120,14 +81,14 @@ public String lookup(long key) throws RemoteException { } - public void update(long key, String value) throws RemoteException { - String targetHost = getTargetHost(key); + public void update(long key, String value, boolean canBeForwarded) throws RemoteException { + String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); try { if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { KVStore.put(key, value); - } else { + } else if(canBeForwarded) { BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - targetServer.update(key, value); + targetServer.update(key, value, false); } } catch (UnknownHostException e) { // TODO Auto-generated catch block @@ -141,15 +102,15 @@ public void update(long key, String value) throws RemoteException { } } - public void delete(long key) throws RemoteException { + public void delete(long key, boolean canBeForwarded) throws RemoteException { if(checkLocalStore(key)) { KVStore.remove(key); return; - } else { + } else if(canBeForwarded){ try { - String targetHost = getTargetHost(key); + String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - targetServer.delete(key); + targetServer.delete(key, false); return; } catch (MalformedURLException e) { e.printStackTrace(); @@ -162,25 +123,25 @@ public void delete(long key) throws RemoteException { } private boolean checkLocalStore(long key) { - return KVStore.containsKey(computeHash((new Long(key)).toString())); + return KVStore.containsKey(key); } - private String getTargetHost(long key) { +/* private String getTargetHost(long key) { long keyHash = computeHash((new Long(key).toString())); - String targetHost = null; String firstHost = null; - + boolean gotFirstHost = false; for (Map.Entry entry : GroupMembership.membershipList.entrySet()) { + if(!gotFirstHost) { + firstHost = entry.getValue().hostname; + gotFirstHost = true; + } if(keyHash <= entry.getValue().hashValue) { - targetHost = entry.getValue().hostname; - continue; + return entry.getValue().hostname; } - else - return targetHost; } return firstHost; - } + }*/ private long computeHash(String pid) { long hashValue = 13; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 9ed8cc7..e80278d 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -7,6 +7,7 @@ import java.net.InetAddress; import java.util.Date; import java.util.Iterator; +import java.util.Map; import java.util.Properties; import java.util.Map.Entry; import java.util.concurrent.ConcurrentHashMap; @@ -19,6 +20,7 @@ import org.apache.log4j.Logger; import org.apache.log4j.PatternLayout; +import edu.uiuc.boltdb.BoltDBServer; import edu.uiuc.boltdb.groupmembership.beans.*; /** @@ -178,8 +180,12 @@ public void run() { BufferedReader bufferRead = new BufferedReader( new InputStreamReader(System.in)); while (true) { - String s = bufferRead.readLine(); - if (s.equals("leave")) { + // Read user's input + System.out.print("boltdb>"); + String commandString = bufferRead.readLine(); + if (commandString.equals("")) + continue; + if (commandString.equals("leave")) { receiveGossip.stop(); scheduler.shutdownNow(); scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); @@ -187,13 +193,32 @@ public void run() { mBean.hearbeatLastReceived = -1; mBean.timeStamp = System.currentTimeMillis(); membershipList.put(pid, mBean); - System.out.println("just before gossip thread"); Thread gossipOneLastTime = new Thread(new SendGossipThread( 0)); gossipOneLastTime.start(); System.out.println("going to break"); break; } + else if(commandString.equals("show")) { + System.out.println("-------------------------------------------------"); + System.out.println("Membership List : "); + System.out.println("-------------------------------------------------"); + for (Map.Entry entry : membershipList.entrySet()) + { + System.out.println(entry); + } + System.out.println("-------------------------------------------------"); + System.out.println(); + System.out.println("-------------------------------------------------"); + System.out.println("Key Value Store : "); + System.out.println("-------------------------------------------------"); + for (Map.Entry entry : BoltDBServer.KVStore.entrySet()) + { + System.out.println(entry.getKey() + " ---> " + entry.getValue() + " | Hash Value of Key - " + computeHash((new Long(entry.getKey())).toString())); + } + System.out.println("-------------------------------------------------"); + System.out.println(); + } } System.out.println("exiting"); } catch (Exception e) { @@ -220,7 +245,7 @@ public static String getSuccessorNodeOf(long keyHash) { long clockWiseDistance = keyHash > hashCurrent ? 1000000l - (keyHash - hashCurrent) : hashCurrent - keyHash; if(minClockwiseDistance > clockWiseDistance) { minClockwiseDistance = clockWiseDistance; - successorNode = entry.getKey(); + successorNode = entry.getValue().hostname; } } return successorNode; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java index d7e3c88..b487269 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/SendGossipThread.java @@ -42,7 +42,6 @@ public void run() int maxTries = 100; while(gossipGroupSize > 0 && (maxTries-- > 0)) { - System.out.println("in while with gossip groupsize:"+gossipGroupSize); MembershipBean mBean = GroupMembership.membershipList.get(keys[generator.nextInt(listSize)]); if(mBean.toBeDeleted) continue; From da3187d3fca1900fae4eadb450548827ff035f0a Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Mon, 4 Nov 2013 15:08:39 -0600 Subject: [PATCH 14/48] moving keys --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 4 +- .../boltdb/groupmembership/MergeThread.java | 46 ++++++++++++++++++- 2 files changed, 46 insertions(+), 4 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 8517b9f..f1a3e1f 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -8,8 +8,8 @@ import java.rmi.RemoteException; import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; +import java.util.HashMap; import java.util.Map; -import java.util.TreeMap; import edu.uiuc.boltdb.groupmembership.GroupMembership; import edu.uiuc.boltdb.groupmembership.beans.MembershipBean; @@ -28,7 +28,7 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - private static Map KVStore = new TreeMap(); + public static Map KVStore = new HashMap(); public static void main(String[] args) throws RemoteException, MalformedURLException { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index db5bb88..0e36a13 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -2,10 +2,17 @@ import java.io.IOException; import java.lang.reflect.Type; +import java.net.InetAddress; +import java.net.MalformedURLException; +import java.net.UnknownHostException; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.rmi.RemoteException; import java.util.Date; import java.util.HashMap; import java.util.Iterator; import java.util.Map; +import java.util.Map.Entry; import org.apache.log4j.Logger; @@ -13,6 +20,8 @@ import com.google.gson.GsonBuilder; import com.google.gson.reflect.TypeToken; +import edu.uiuc.boltdb.BoltDBProtocol; +import edu.uiuc.boltdb.BoltDBServer; import edu.uiuc.boltdb.groupmembership.beans.MembershipBean; import edu.uiuc.boltdb.groupmembership.beans.UDPBean; @@ -46,7 +55,12 @@ public void run() System.out.println("Problem receiving gossip"); return; } - mergeIncomingMembershipList(); + try { + mergeIncomingMembershipList(); + } catch (Exception e) { + e.printStackTrace(); + } + //System.out.println("\nAFTER MERGE : "+GroupMembership.membershipList); } @@ -63,8 +77,12 @@ private void getGossipFromClient() throws IOException /** * Merge the incoming membership list into the current node's membership list + * @throws UnknownHostException + * @throws NotBoundException + * @throws RemoteException + * @throws MalformedURLException */ - private void mergeIncomingMembershipList() + private void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException { Iterator> iterator = incomingMembershipList.entrySet().iterator(); //Iterate over each entry of incoming membershiplist @@ -121,8 +139,32 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea { System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); + boolean amISuccessor = amITheSuccesorOf(receivedPid); + + if(amISuccessor) { + moveKeys(receivedHost,mBean.hashValue); + } } } } } + + private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { + long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; + if(GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode) == InetAddress.getLocalHost().getHostName()) return true; + return false; + } + + private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException { + BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); + Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); + long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; + while(itr.hasNext()) { + Entry entry = itr.next(); + if (entry.getKey() > myHash || entry.getKey() <= hashOfNewJoinedNode) { + targetRMIServer.insert(entry.getKey(), entry.getValue()); + BoltDBServer.KVStore.remove(entry.getKey()); + } + } + } } From f377e6d4a07eef13c1b6be3847f1d916c5591ffe Mon Sep 17 00:00:00 2001 From: Adarsh Date: Mon, 4 Nov 2013 15:57:07 -0600 Subject: [PATCH 15/48] changes --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 58 +++++++++---------- .../groupmembership/GroupMembership.java | 16 ++--- .../boltdb/groupmembership/MergeThread.java | 4 +- .../groupmembership/beans/MembershipBean.java | 2 +- 4 files changed, 40 insertions(+), 40 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 574bcbf..a9bbff1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -11,6 +11,7 @@ import java.rmi.RemoteException; import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; +import java.security.NoSuchAlgorithmException; import java.util.Map; import java.util.TreeMap; @@ -43,7 +44,13 @@ public static void main(String[] args) throws IOException { } public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { - String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); + String targetHost = null; + try { + targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + } catch (NoSuchAlgorithmException e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } try { if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { KVStore.put(key, value); @@ -68,7 +75,13 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { return KVStore.get(key); } else if(canBeForwarded){ try { - String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); + String targetHost = null; + try { + targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + } catch (NoSuchAlgorithmException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); return targetServer.lookup(key, false); } catch (MalformedURLException e) { @@ -82,7 +95,13 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { } public void update(long key, String value, boolean canBeForwarded) throws RemoteException { - String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); + String targetHost = null; + try { + targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + } catch (NoSuchAlgorithmException e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } try { if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { KVStore.put(key, value); @@ -108,7 +127,13 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { return; } else if(canBeForwarded){ try { - String targetHost = GroupMembership.getSuccessorNodeOf(computeHash((new Long(key).toString()))); + String targetHost = null; + try { + targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + } catch (NoSuchAlgorithmException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); targetServer.delete(key, false); return; @@ -125,29 +150,4 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { private boolean checkLocalStore(long key) { return KVStore.containsKey(key); } - -/* private String getTargetHost(long key) { - long keyHash = computeHash((new Long(key).toString())); - String firstHost = null; - boolean gotFirstHost = false; - for (Map.Entry entry : GroupMembership.membershipList.entrySet()) - { - if(!gotFirstHost) { - firstHost = entry.getValue().hostname; - gotFirstHost = true; - } - if(keyHash <= entry.getValue().hashValue) { - return entry.getValue().hostname; - } - } - return firstHost; - }*/ - - private long computeHash(String pid) { - long hashValue = 13; - for (int i=0; i < pid.length(); i++) { - hashValue = hashValue*31 + pid.charAt(i); - } - return hashValue % 1000001L; - } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 9e6f17e..f4982f6 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -4,7 +4,10 @@ import java.io.FileInputStream; import java.io.IOException; import java.io.InputStreamReader; +import java.math.BigInteger; import java.net.InetAddress; +import java.security.MessageDigest; +import java.security.NoSuchAlgorithmException; import java.util.Date; import java.util.Iterator; import java.util.Map; @@ -220,19 +223,16 @@ else if(commandString.equals("show")) { System.out.println(); } } - System.out.println("exiting"); } catch (Exception e) { - System.out.println("Exception occured"); + e.printStackTrace(); } } - private long computeHash(String pid) { - long hashValue = 13; - for (int i=0; i < pid.length(); i++) { - hashValue = hashValue*31 + pid.charAt(i); - } - return hashValue % 1000001L; + public static long computeHash(String pid) throws NoSuchAlgorithmException { + MessageDigest md = MessageDigest.getInstance("MD5"); + BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); + return Math.abs(bigInt.longValue()) % 1000001L; } public static String getSuccessorNodeOf(long keyHash) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index db5bb88..5204c2b 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -89,7 +89,7 @@ private void mergeIncomingMembershipList() //VOLUNTARILY LEAVE : If the incoming entry has heartbeat less than zero,then log 'VOLUNTARILY LEFT' message. //Also update current node's membership list if(receivedMBean.hearbeatLastReceived <= 0 && currentMBean.hearbeatLastReceived > 0) { - System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); + //System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); log.info("VOLUNTARILY LEFT - - - " + receivedPid); currentMBean.hearbeatLastReceived = -1; currentMBean.timeStamp = System.currentTimeMillis(); @@ -119,7 +119,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); if (returnVal == null) { - System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); + //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java index d806221..c618037 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/MembershipBean.java @@ -20,7 +20,7 @@ public MembershipBean(String ipaddress, long hearbeatLastReceived, long timeStam @Override public String toString() { - return new String("[" + hostname + " " +hearbeatLastReceived+" "+timeStamp+" "+toBeDeleted+"]"); + return new String("[" + hostname + " " +hearbeatLastReceived+" "+timeStamp+" "+toBeDeleted+ " " + hashValue + "]"); } } From 3d65b09dae38984a77815da665a251d1e7d41fb0 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Mon, 4 Nov 2013 20:01:18 -0600 Subject: [PATCH 16/48] move keys during leave fixed --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 4 ++- .../groupmembership/GroupMembership.java | 4 ++- .../boltdb/groupmembership/MergeThread.java | 32 +++++++++++++++---- 3 files changed, 32 insertions(+), 8 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 2953624..144dba9 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -14,6 +14,7 @@ import java.security.NoSuchAlgorithmException; import java.util.HashMap; import java.util.Map; +import java.util.concurrent.ConcurrentHashMap; import edu.uiuc.boltdb.groupmembership.GroupMembership; @@ -31,7 +32,7 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - public static Map KVStore = new HashMap(); + public static Map KVStore = new ConcurrentHashMap(); public static void main(String[] args) throws IOException { @@ -44,6 +45,7 @@ public static void main(String[] args) throws IOException { } public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { + if(!canBeForwarded) KVStore.put(key, value); String targetHost = null; try { targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index fd08bc9..859d8d1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -197,12 +197,13 @@ public void run() { //Move your keys to successor long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; String successor = getSuccessorNodeOf(myHash); - + System.out.println("successor:"+successor); BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successor + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { Entry entry = itr.next(); + System.out.println("inserting:"+entry.getKey()); successorRMIServer.insert(entry.getKey(), entry.getValue(), false); } BoltDBServer.KVStore.clear(); @@ -256,6 +257,7 @@ public static String getSuccessorNodeOf(long keyHash) { String successorHost = new String(); while(itr.hasNext()) { Entry entry = itr.next(); + if(entry.getValue().hashValue == keyHash) continue; long hashCurrent = entry.getValue().hashValue; long clockWiseDistance = keyHash > hashCurrent ? 1000000l - (keyHash - hashCurrent) : hashCurrent - keyHash; if(minClockwiseDistance > clockWiseDistance) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 3fb8314..e6118df 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -8,6 +8,7 @@ import java.rmi.Naming; import java.rmi.NotBoundException; import java.rmi.RemoteException; +import java.security.NoSuchAlgorithmException; import java.util.Date; import java.util.HashMap; import java.util.Iterator; @@ -81,8 +82,9 @@ private void getGossipFromClient() throws IOException * @throws NotBoundException * @throws RemoteException * @throws MalformedURLException + * @throws NoSuchAlgorithmException */ - private void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException + private void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { Iterator> iterator = incomingMembershipList.entrySet().iterator(); //Iterate over each entry of incoming membershiplist @@ -137,7 +139,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); if (returnVal == null) { - //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); + System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); boolean amISuccessor = amITheSuccesorOf(receivedPid); @@ -151,20 +153,38 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; - if(GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode) == InetAddress.getLocalHost().getHostName()) return true; + System.out.println("hash of new:"+hashOfNewlyJoinedNode); + System.out.println("successor node:"+GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode)); + if(GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode).equals(InetAddress.getLocalHost().getHostName())) return true; return false; } - private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException { + private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { + System.out.println("Moving keys:"); BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; while(itr.hasNext()) { Entry entry = itr.next(); - if (entry.getKey() > myHash || entry.getKey() <= hashOfNewJoinedNode) { + long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); + System.out.println("hash of "+entry.getKey()+" is "+hashOfKey); + System.out.println("my hash is:"+myHash); + System.out.println("hash of new guy:"+hashOfNewJoinedNode); + System.out.println("value of condition:"+(hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode)); + if (myHash > hashOfNewJoinedNode) { + if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { + System.out.println("Moving key:"+entry.getKey()); + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + BoltDBServer.KVStore.remove(entry.getKey()); + } + } + else { + if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { + System.out.println("Moving key:"+entry.getKey()); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); BoltDBServer.KVStore.remove(entry.getKey()); - } + } + } } } } From d167af5a0839e63db38b5aabfbb68c574623ac8f Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 8 Nov 2013 22:20:05 -0600 Subject: [PATCH 17/48] Fixed all operations --- .../java/edu/uiuc/boltdb/BoltDBClient.java | 120 +++++++------- .../java/edu/uiuc/boltdb/BoltDBServer.java | 146 ++++++++---------- .../groupmembership/GroupMembership.java | 5 +- .../boltdb/groupmembership/MergeThread.java | 23 +-- 4 files changed, 134 insertions(+), 160 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index c01e688..727d2ee 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -16,7 +16,6 @@ public class BoltDBClient { private BoltDBProtocol boltDBServer = null; public BoltDBClient(String rmiString) throws MalformedURLException, RemoteException, NotBoundException { - System.out.println(rmiString); if(System.getSecurityManager() == null) { System.setSecurityManager(new SecurityManager()); } @@ -29,18 +28,16 @@ public BoltDBClient(String rmiString) throws MalformedURLException, RemoteExcept * @throws NotBoundException */ public static void main(String[] args) { - // TODO Auto-generated method stub try { Properties prop = new Properties(); FileInputStream fis = new FileInputStream("./boltdb.prop"); prop.load(fis); fis.close(); - String rmiString = prop.getProperty("boltdb.server"); + String rmiString = prop.getProperty("boltdb.kvstore.server"); BoltDBClient boltDBClient = new BoltDBClient(rmiString); boltDBClient.runClientShell(); } catch(Exception e) { e.printStackTrace(); - System.out.println("Operation Failed"); } } @@ -52,7 +49,7 @@ private void runClientShell() throws IOException { // Break out with Ctrl+C while (true) { // Read user's input - System.out.print("boltdb>"); + System.out.print("boltdb-client>"); commandString = console.readLine(); // If the user entered a return, just loop again @@ -62,61 +59,72 @@ private void runClientShell() throws IOException { } } - private void handleCommand(String commandString) throws RemoteException { - StringTokenizer stk = new StringTokenizer(commandString); - if(stk.countTokens() < 2) { - printUsage(0); - return; - } - - // The Command Type - String commandType = stk.nextToken(); - - if(commandType.equals("insert")) { - String keyStr = stk.nextToken(); - long key = parseKey(keyStr); - if(key == -1) return; - String value = ""; - if(stk.hasMoreTokens()) { - value = stk.nextToken(); - } - else { - printUsage(1); + private void handleCommand(String commandString) { + try { + StringTokenizer stk = new StringTokenizer(commandString); + if(stk.countTokens() < 2) { + printUsage(0); return; } - // Perform Insert Operation - boltDBServer.insert(key, value, true); - } else if(commandType.equals("update")) { - String keyStr = stk.nextToken(); - long key = parseKey(keyStr); - if(key == -1) return; - String value = ""; - if(stk.hasMoreTokens()) { - value = stk.nextToken(); - } - else { - printUsage(2); + + // The Command Type + String commandType = stk.nextToken(); + + if(commandType.equals("insert")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + String value = ""; + if(stk.hasMoreTokens()) { + while(stk.hasMoreTokens()) + value += stk.nextToken() + " "; + } + else { + printUsage(1); + return; + } + value = value.trim(); + // Perform Insert Operation + boltDBServer.insert(key, value, true); + } else if(commandType.equals("update")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + String value = ""; + if(stk.hasMoreTokens()) { + while(stk.hasMoreTokens()) + value += stk.nextToken() + " "; + } + else { + printUsage(2); + return; + } + value = value.trim(); + // Perform Update Operation + boltDBServer.update(key, value, true); + } else if(commandType.equals("lookup")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + // Perform Look Up Operation + String value = (String)boltDBServer.lookup(key, true); + System.out.println("Look Up Result : " + value); + } else if(commandType.equals("delete")) { + String keyStr = stk.nextToken(); + long key = parseKey(keyStr); + if(key == -1) return; + // Perform Delete Operation + boltDBServer.delete(key, true); + System.out.println("Key Value Pair Deleted"); + } else { + printUsage(0); return; } - // Perform Update Operation - boltDBServer.update(key, value, true); - } else if(commandType.equals("lookup")) { - String keyStr = stk.nextToken(); - long key = parseKey(keyStr); - if(key == -1) return; - // Perform Look Up Operation - String value = (String)boltDBServer.lookup(key, true); - System.out.println("Look Up Result : " + value); - } else if(commandType.equals("delete")) { - String keyStr = stk.nextToken(); - long key = parseKey(keyStr); - if(key == -1) return; - // Perform Delete Operation - boltDBServer.delete(key, true); - System.out.println("Key Value Pair Deleted"); - } else { - printUsage(0); - return; + } catch(RemoteException re) { + if(re.getCause().getCause() != null) + System.out.println(re.getCause().getCause().getMessage()); + else + System.out.println(re.getCause().getMessage()); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 144dba9..f895d61 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -1,21 +1,16 @@ package edu.uiuc.boltdb; -import java.io.BufferedReader; import java.io.IOException; -import java.io.InputStreamReader; import java.net.InetAddress; -import java.net.MalformedURLException; -import java.net.UnknownHostException; import java.rmi.Naming; -import java.rmi.NotBoundException; import java.rmi.RemoteException; import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; -import java.security.NoSuchAlgorithmException; -import java.util.HashMap; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; +import org.apache.log4j.Logger; + import edu.uiuc.boltdb.groupmembership.GroupMembership; public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { @@ -24,7 +19,8 @@ public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol * */ private static final long serialVersionUID = 5195393553928167809L; - + private static org.apache.log4j.Logger log = Logger.getRootLogger(); + protected BoltDBServer() throws RemoteException { super(); } @@ -45,111 +41,105 @@ public static void main(String[] args) throws IOException { } public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { - if(!canBeForwarded) KVStore.put(key, value); + if(!canBeForwarded) { + if(KVStore.containsKey(key)) + throw new RemoteException("Key already present."); + KVStore.put(key, value); + return; + } String targetHost = null; try { targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); - } catch (NoSuchAlgorithmException e1) { - // TODO Auto-generated catch block - e1.printStackTrace(); - } - try { if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { + if(KVStore.containsKey(key)) + throw new RemoteException("Key already present."); KVStore.put(key, value); - } else if(canBeForwarded){ + } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); targetServer.insert(key, value, false); } - } catch (UnknownHostException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } catch (MalformedURLException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } catch (NotBoundException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } + } catch(RemoteException re) { + throw re; + } catch (Exception e) { + log.error("ERROR" , e); + throw new RemoteException("Error occured at Server"); + } } public String lookup(long key, boolean canBeForwarded) throws RemoteException { - if(checkLocalStore(key)) { + if(!canBeForwarded) { + if(!KVStore.containsKey(key)) + throw new RemoteException("Key not present."); return KVStore.get(key); - } else if(canBeForwarded){ - try { - String targetHost = null; - try { - targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); - } catch (NoSuchAlgorithmException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } + } + String targetHost = null; + try { + targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { + if(!KVStore.containsKey(key)) + throw new RemoteException("Key not present."); + return KVStore.get(key); + } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); return targetServer.lookup(key, false); - } catch (MalformedURLException e) { - e.printStackTrace(); - } catch (NotBoundException e) { - e.printStackTrace(); } + } catch(RemoteException re) { + throw re; + } catch (Exception e) { + log.error("ERROR" , e); + throw new RemoteException("Error occured at Server"); } - return null; - } public void update(long key, String value, boolean canBeForwarded) throws RemoteException { + if(!canBeForwarded) { + if(!KVStore.containsKey(key)) + throw new RemoteException("Key not present."); + KVStore.put(key, value); + return; + } String targetHost = null; try { targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); - } catch (NoSuchAlgorithmException e1) { - // TODO Auto-generated catch block - e1.printStackTrace(); - } - try { if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { + if(!KVStore.containsKey(key)) + throw new RemoteException("Key not present."); KVStore.put(key, value); - } else if(canBeForwarded) { + } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); targetServer.update(key, value, false); } - } catch (UnknownHostException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } catch (MalformedURLException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } catch (NotBoundException e) { - // TODO Auto-generated catch block - e.printStackTrace(); + } catch(RemoteException re) { + throw re; + } catch (Exception e) { + log.error("ERROR" , e); + throw new RemoteException("Error occured at Server"); } } public void delete(long key, boolean canBeForwarded) throws RemoteException { - if(checkLocalStore(key)) { + if(!canBeForwarded) { + if(!KVStore.containsKey(key)) + throw new RemoteException("Key not present."); KVStore.remove(key); return; - } else if(canBeForwarded){ - try { - String targetHost = null; - try { - targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); - } catch (NoSuchAlgorithmException e) { - // TODO Auto-generated catch block - e.printStackTrace(); - } + } + String targetHost = null; + try { + targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { + if(!KVStore.containsKey(key)) + throw new RemoteException("Key not present."); + KVStore.remove(key); + } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); targetServer.delete(key, false); - return; - } catch (MalformedURLException e) { - e.printStackTrace(); - } catch (NotBoundException e) { - e.printStackTrace(); } - } - - - } - - private boolean checkLocalStore(long key) { - return KVStore.containsKey(key); + } catch(RemoteException re) { + throw re; + } catch (Exception e) { + log.error("ERROR" , e); + throw new RemoteException("Error occured at Server"); + } } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 859d8d1..528d1f1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -186,7 +186,7 @@ public void run() { new InputStreamReader(System.in)); while (true) { // Read user's input - System.out.print("boltdb>"); + System.out.print("boltdb-server>"); String commandString = bufferRead.readLine(); if (commandString.equals("")) continue; @@ -197,13 +197,11 @@ public void run() { //Move your keys to successor long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; String successor = getSuccessorNodeOf(myHash); - System.out.println("successor:"+successor); BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successor + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { Entry entry = itr.next(); - System.out.println("inserting:"+entry.getKey()); successorRMIServer.insert(entry.getKey(), entry.getValue(), false); } BoltDBServer.KVStore.clear(); @@ -215,7 +213,6 @@ public void run() { Thread gossipOneLastTime = new Thread(new SendGossipThread( 0)); gossipOneLastTime.start(); - System.out.println("going to break"); break; } else if(commandString.equals("show")) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index e6118df..fc7ace3 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -117,18 +117,6 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme GroupMembership.membershipList.put(receivedPid, currentMBean); continue; } else if (receivedMBean.hearbeatLastReceived <= 0 || currentMBean.hearbeatLastReceived <= 0) continue; - - //If the incoming entry's heartbeat is greater than current node's membership list,then update the list. - /*if(receivedMBean.hearbeatLastReceived > currentMBean.hearbeatLastReceived) - { - currentMBean.hearbeatLastReceived = receivedMBean.hearbeatLastReceived; - currentMBean.timeStamp = System.currentTimeMillis(); - if(currentMBean.toBeDeleted) { - System.out.println("JOINED : " + receivedPid); - currentMBean.toBeDeleted = false; - } - GroupMembership.membershipList.put(receivedPid, currentMBean); - }*/ } else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBean.hearbeatLastReceived > 0) { @@ -139,7 +127,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); if (returnVal == null) { - System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); + //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); boolean amISuccessor = amITheSuccesorOf(receivedPid); @@ -153,34 +141,25 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; - System.out.println("hash of new:"+hashOfNewlyJoinedNode); - System.out.println("successor node:"+GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode)); if(GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode).equals(InetAddress.getLocalHost().getHostName())) return true; return false; } private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { - System.out.println("Moving keys:"); BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; while(itr.hasNext()) { Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); - System.out.println("hash of "+entry.getKey()+" is "+hashOfKey); - System.out.println("my hash is:"+myHash); - System.out.println("hash of new guy:"+hashOfNewJoinedNode); - System.out.println("value of condition:"+(hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode)); if (myHash > hashOfNewJoinedNode) { if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { - System.out.println("Moving key:"+entry.getKey()); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); BoltDBServer.KVStore.remove(entry.getKey()); } } else { if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { - System.out.println("Moving key:"+entry.getKey()); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); BoltDBServer.KVStore.remove(entry.getKey()); } From dd55a6ec1faf959b67f817b55b159e72f12b16c7 Mon Sep 17 00:00:00 2001 From: ashwinshankar77 Date: Sat, 9 Nov 2013 17:35:13 -0800 Subject: [PATCH 18/48] Update BoltDBProtocol.java --- boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java | 3 +++ 1 file changed, 3 insertions(+) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index 24cb078..3d15673 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -3,6 +3,9 @@ import java.rmi.Remote; import java.rmi.RemoteException; +/** + * + */ public interface BoltDBProtocol extends Remote { public void insert(long key, String value, boolean canBeForwarded) throws RemoteException; From d2d43b26eef7aaca41fbf4f1b376164c11f77188 Mon Sep 17 00:00:00 2001 From: Ashwin Date: Sat, 9 Nov 2013 18:52:42 -0800 Subject: [PATCH 19/48] added comments --- boltdb/.classpath | 12 +++--- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 37 ++++++++++++++++++- .../groupmembership/GroupMembership.java | 17 +++++++++ .../boltdb/groupmembership/MergeThread.java | 23 ++++++++++++ 4 files changed, 82 insertions(+), 7 deletions(-) diff --git a/boltdb/.classpath b/boltdb/.classpath index b39967e..2d87044 100644 --- a/boltdb/.classpath +++ b/boltdb/.classpath @@ -6,25 +6,25 @@ - + - + + + - + - - + - diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index 3d15673..343a5be 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -4,16 +4,51 @@ import java.rmi.RemoteException; /** - * + * This interface represents the protocol between client and key-value store server. + * @author Ashwin + * */ public interface BoltDBProtocol extends Remote { + /** + * The insert api is used to insert a key and a value into the store. + *'canBeForwarded' is a flag to indicate whether the request can be forwarded to + *other servers to perform the operation. + *Throws an exception if key is already present in the store. + * @param key + * @param value + * @param canBeForwarded + * @throws RemoteException + */ public void insert(long key, String value, boolean canBeForwarded) throws RemoteException; + /** + * The lookup api is used to lookup the value associated with a key. + * Throws an exception is key is not present in the store. + * @param key + * @param canBeForwarded + * @return + * @throws RemoteException + */ public String lookup(long key, boolean canBeForwarded) throws RemoteException; + /** + * The update api updates the value of the provided key with the new value. + * Throws an exception if the key is not present. + * @param key + * @param value + * @param canBeForwarded + * @throws RemoteException + */ public void update(long key, String value, boolean canBeForwarded) throws RemoteException; + /** + * The delete api removes the key-value entry from the store. + * Throws an exception is the key is not present in the store. + * @param key + * @param canBeForwarded + * @throws RemoteException + */ public void delete(long key, boolean canBeForwarded) throws RemoteException; } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 528d1f1..1bfd34d 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -104,6 +104,7 @@ public void run() { initializeLogger(args[3]); } + //Compute the hashvalue of yourself(server) long hashValue = computeHash(pid); // Insert the current machine into the membership list with @@ -242,21 +243,37 @@ else if(commandString.equals("show")) { } + /** + * Computes the MD5 hash of the pid,transforms it into an integer + * and hashes it in the range 0-1 million. + * @param pid + * @return + * @throws NoSuchAlgorithmException + */ public static long computeHash(String pid) throws NoSuchAlgorithmException { MessageDigest md = MessageDigest.getInstance("MD5"); BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); return Math.abs(bigInt.longValue()) % 1000001L; } + /** + * Returns the node which is the successor of a key. + * @param keyHash + * @return + */ public static String getSuccessorNodeOf(long keyHash) { Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); + //Set the minimum clockwise distance to be maximum possible value long minClockwiseDistance = 1000000L; String successorHost = new String(); while(itr.hasNext()) { Entry entry = itr.next(); + //Ignore if the entry is yourself(Server) if(entry.getValue().hashValue == keyHash) continue; long hashCurrent = entry.getValue().hashValue; + //compute the clockwise distance long clockWiseDistance = keyHash > hashCurrent ? 1000000l - (keyHash - hashCurrent) : hashCurrent - keyHash; + //Update minimum clockwise distance if required if(minClockwiseDistance > clockWiseDistance) { minClockwiseDistance = clockWiseDistance; successorHost = entry.getValue().hostname; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index fc7ace3..b30d3ba 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -129,9 +129,11 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea { //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); + //Get the successor of newly joined node boolean amISuccessor = amITheSuccesorOf(receivedPid); if(amISuccessor) { + //If you are the successor,move keys accordingly. moveKeys(receivedHost,mBean.hashValue); } } @@ -139,25 +141,46 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea } } + /** + * Check if I am the successor of the newly joined node. + * @param receivedPid + * @return + * @throws UnknownHostException + */ private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; if(GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode).equals(InetAddress.getLocalHost().getHostName())) return true; return false; } + /** + * Move keys from yourself to the newly joined node just like in the chord paper + * @param targetHost + * @param hashOfNewJoinedNode + * @throws MalformedURLException + * @throws RemoteException + * @throws NotBoundException + * @throws NoSuchAlgorithmException + */ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { + //get the rmiserver handle from the rmi registry BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; while(itr.hasNext()) { Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); + //If hash of current server is greater than hash of newly joined server + //then move all the keys greater than hash of current server + //and less than newly joined server. if (myHash > hashOfNewJoinedNode) { if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { targetRMIServer.insert(entry.getKey(), entry.getValue(),false); BoltDBServer.KVStore.remove(entry.getKey()); } } + //If hasf of current server is less than hash of newly joined server + //then move all the keys in between the two servers hashes. else { if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { targetRMIServer.insert(entry.getKey(), entry.getValue(),false); From d941daa26697b926f2330478e960285e4a6d12f1 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 10 Nov 2013 10:02:37 -0600 Subject: [PATCH 20/48] Comments --- .../java/edu/uiuc/boltdb/BoltDBClient.java | 22 ++++++-- .../java/edu/uiuc/boltdb/BoltDBServer.java | 56 ++++++++++++++++++- .../groupmembership/GroupMembership.java | 4 ++ 3 files changed, 75 insertions(+), 7 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index 727d2ee..dc72a64 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -11,6 +11,16 @@ import java.util.Properties; import java.util.StringTokenizer; +/** + * This class represents the client component of the distributed key value store. On start up it creates + * a boltdb-client> shell where the user can type in the insert, update, lookup and delete queries. + * The BoltDBClient class creates a reference to a remote BoltDBServer object in the member variable boltDBServer. + * All the operations (insert, lookup, update and delete) are performed on this remote object reference. + * + * @author Adarsh + * + */ + public class BoltDBClient { private BoltDBProtocol boltDBServer = null; @@ -41,6 +51,7 @@ public static void main(String[] args) { } } + // Method to simulate a boltdb-client shell private void runClientShell() throws IOException { // Simulate a unix shell String commandString = ""; @@ -59,6 +70,7 @@ private void runClientShell() throws IOException { } } + // This method handles the commands entered by the user in the boltdb-client shell private void handleCommand(String commandString) { try { StringTokenizer stk = new StringTokenizer(commandString); @@ -84,7 +96,7 @@ private void handleCommand(String commandString) { return; } value = value.trim(); - // Perform Insert Operation + // Perform Insert Operation on the remote server object boltDBServer.insert(key, value, true); } else if(commandType.equals("update")) { String keyStr = stk.nextToken(); @@ -100,20 +112,20 @@ private void handleCommand(String commandString) { return; } value = value.trim(); - // Perform Update Operation + // Perform Update Operation on the remote server object boltDBServer.update(key, value, true); } else if(commandType.equals("lookup")) { String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; - // Perform Look Up Operation + // Perform LookUp Operation on the remote server object String value = (String)boltDBServer.lookup(key, true); System.out.println("Look Up Result : " + value); } else if(commandType.equals("delete")) { String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; - // Perform Delete Operation + // Perform Delete Operation on the remote server object boltDBServer.delete(key, true); System.out.println("Key Value Pair Deleted"); } else { @@ -128,6 +140,7 @@ private void handleCommand(String commandString) { } } + // Method to parse the key entered by the user to long, and to validate the key private long parseKey(String keyStr) { long key; try { @@ -143,6 +156,7 @@ private long parseKey(String keyStr) { } } + // Method to print the usage of BoltDBClient private void printUsage(int type) { System.out.println("Invalid Command"); System.out.println("Usage : "); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index f895d61..3790dfe 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -13,11 +13,20 @@ import edu.uiuc.boltdb.groupmembership.GroupMembership; +/** + * This class represents the server component of the distributed key value store. It implements the + * BoltDBProtocol interface. On startup, it starts the GroupMembership service. It maintains a + * ConcurrentHashMap KVStore that stores the key-value pairs that are destined for this host. Since it implements + * the BoltDBProtocol, it provides the Remote methods to insert, lookup, update and delete keys. Upon request + * from a client, depending on the target host and the canBeForwarded flag, it performs the operation on + * the local key value store (If it is the target host) or forwards the operation by determining the target + * host from its MembershipList. + * @author Adarsh + * + */ + public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { - /** - * - */ private static final long serialVersionUID = 5195393553928167809L; private static org.apache.log4j.Logger log = Logger.getRootLogger(); @@ -33,13 +42,27 @@ protected BoltDBServer() throws RemoteException { public static void main(String[] args) throws IOException { + // Start the GroupMembership service Runnable groupMembership = new GroupMembership(args); Thread groupMembershipThread = new Thread(groupMembership); groupMembershipThread.start(); + + //Create RMI registry LocateRegistry.createRegistry(1099); Naming.rebind ("KVStore", new BoltDBServer()); } + /** + * The insert api is used to insert a key and a value into the store. + *'canBeForwarded' is a flag to indicate whether the request can be forwarded to + *other servers to perform the operation. + *Throws an exception if key is already present in the store. + * @param key + * @param value + * @param canBeForwarded + * @throws RemoteException + */ + public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { if(!canBeForwarded) { if(KVStore.containsKey(key)) @@ -49,6 +72,7 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote } String targetHost = null; try { + // Determine the target host using the getSuccessorNodeOf method targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(KVStore.containsKey(key)) @@ -66,6 +90,14 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote } } + /** + * The lookup api is used to lookup the value associated with a key. + * Throws an exception is key is not present in the store. + * @param key + * @param canBeForwarded + * @return + * @throws RemoteException + */ public String lookup(long key, boolean canBeForwarded) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) @@ -74,6 +106,7 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { } String targetHost = null; try { + // Determine the target host using the getSuccessorNodeOf method targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) @@ -91,6 +124,14 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { } } + /** + * The update api updates the value of the provided key with the new value. + * Throws an exception if the key is not present. + * @param key + * @param value + * @param canBeForwarded + * @throws RemoteException + */ public void update(long key, String value, boolean canBeForwarded) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) @@ -100,6 +141,7 @@ public void update(long key, String value, boolean canBeForwarded) throws Remote } String targetHost = null; try { + // Determine the target host using the getSuccessorNodeOf method targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) @@ -117,6 +159,13 @@ public void update(long key, String value, boolean canBeForwarded) throws Remote } } + /** + * The delete api removes the key-value entry from the store. + * Throws an exception is the key is not present in the store. + * @param key + * @param canBeForwarded + * @throws RemoteException + */ public void delete(long key, boolean canBeForwarded) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) @@ -126,6 +175,7 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { } String targetHost = null; try { + // Determine the target host using the getSuccessorNodeOf method targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 1bfd34d..339a11b 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -216,6 +216,10 @@ public void run() { gossipOneLastTime.start(); break; } + /* + * The show command prints the current membershipList entries and the current KVStore + * entries on the console. + */ else if(commandString.equals("show")) { System.out.println("-------------------------------------------------"); System.out.println("Membership List : "); From 56fed1ab8448362fc65b229676404fc45d173597 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Mon, 25 Nov 2013 16:51:07 -0600 Subject: [PATCH 21/48] nits --- boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java | 3 --- 1 file changed, 3 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 144dba9..c1a56b1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -1,8 +1,6 @@ package edu.uiuc.boltdb; -import java.io.BufferedReader; import java.io.IOException; -import java.io.InputStreamReader; import java.net.InetAddress; import java.net.MalformedURLException; import java.net.UnknownHostException; @@ -12,7 +10,6 @@ import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; import java.security.NoSuchAlgorithmException; -import java.util.HashMap; import java.util.Map; import java.util.concurrent.ConcurrentHashMap; From cc862e926666b00e091082c01866e764a827611f Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Thu, 28 Nov 2013 19:03:21 -0600 Subject: [PATCH 22/48] heartbeat turned on --- .../groupmembership/GroupMembership.java | 8 ++--- .../boltdb/groupmembership/MergeThread.java | 22 +++++++++--- .../RefreshMembershipListThread.java | 36 +++++++++---------- 3 files changed, 39 insertions(+), 27 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 339a11b..8de348d 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -156,10 +156,10 @@ public void run() { // property file ScheduledExecutorService scheduler = Executors .newSingleThreadScheduledExecutor(); - //scheduler.scheduleAtFixedRate(new HeartbeatIncrementerThread(), 0, - // Integer.parseInt(prop - // .getProperty("groupmembership.heartbeat.freq")), - // TimeUnit.MILLISECONDS); + scheduler.scheduleAtFixedRate(new HeartbeatIncrementerThread(), 0, + Integer.parseInt(prop + .getProperty("groupmembership.heartbeat.freq")), + TimeUnit.MILLISECONDS); scheduler .scheduleAtFixedRate( new RefreshMembershipListThread(tFail), diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index b30d3ba..71e52ab 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -95,7 +95,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme UDPBean receivedMBean = entry.getValue(); //Check if pid present in this entry is also present in our membership list. - if(GroupMembership.membershipList.containsKey(receivedPid) && receivedMBean.hearbeatLastReceived < 0) + if(GroupMembership.membershipList.containsKey(receivedPid)) { MembershipBean currentMBean = GroupMembership.membershipList.get(receivedPid); @@ -109,7 +109,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme //VOLUNTARILY LEAVE : If the incoming entry has heartbeat less than zero,then log 'VOLUNTARILY LEFT' message. //Also update current node's membership list if(receivedMBean.hearbeatLastReceived <= 0 && currentMBean.hearbeatLastReceived > 0) { - //System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); + System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); log.info("VOLUNTARILY LEFT - - - " + receivedPid); currentMBean.hearbeatLastReceived = -1; currentMBean.timeStamp = System.currentTimeMillis(); @@ -117,17 +117,29 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme GroupMembership.membershipList.put(receivedPid, currentMBean); continue; } else if (receivedMBean.hearbeatLastReceived <= 0 || currentMBean.hearbeatLastReceived <= 0) continue; - } + + //If the incoming entry's heartbeat is greater than current node's membership list,then update the list. + if(receivedMBean.hearbeatLastReceived > currentMBean.hearbeatLastReceived) + { + currentMBean.hearbeatLastReceived = receivedMBean.hearbeatLastReceived; + currentMBean.timeStamp = System.currentTimeMillis(); + if(currentMBean.toBeDeleted) { + System.out.println("JOINED : " + receivedPid); + currentMBean.toBeDeleted = false; + } + GroupMembership.membershipList.put(receivedPid, currentMBean); + } + } else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBean.hearbeatLastReceived > 0) { //JOIN : If the incoming entry is not in our membership list then it means a new node has joined. - if(receivedMBean.hearbeatLastReceived <= 0) continue; + //if(receivedMBean.hearbeatLastReceived <= 0) continue; String receivedHost = receivedPid.split(GroupMembership.pidDelimiter)[0]; MembershipBean mBean = new MembershipBean(receivedHost, receivedMBean.hearbeatLastReceived, System.currentTimeMillis(), receivedMBean.hashValue, false); MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); if (returnVal == null) { - //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); + System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); //Get the successor of newly joined node boolean amISuccessor = amITheSuccesorOf(receivedPid); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index 4c46aac..ff9bee1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -35,27 +35,27 @@ public void run() { Map.Entry entry = iterator.next(); MembershipBean membershipBean = entry.getValue(); - if(membershipBean.hearbeatLastReceived <= 0) { - //If current node's heartbeat is less than zero ie has Voluntarily left,then don't do anything - if(membershipBean.hearbeatLastReceived <= 0 && entry.getKey().equals(GroupMembership.pid)) { - continue; - } - //Remove entry which is marked toBeDeleted - if (membershipBean.toBeDeleted) - { - GroupMembership.membershipList.remove(entry.getKey()); - } - //If the membership list entry has timed-out then mark it toBeDeleted - else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000) - { - membershipBean.toBeDeleted = true; - /*if (membershipBean.hearbeatLastReceived > 0) { - System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); - log.info("CRASHED - - - " + entry.getKey()); - }*/ + //If current node's heartbeat is less than zero ie has Voluntarily left,then don't do anything + if(membershipBean.hearbeatLastReceived <= 0 && entry.getKey().equals(GroupMembership.pid)) { + continue; + } + + //Remove entry which is marked toBeDeleted + if (membershipBean.toBeDeleted) + { + GroupMembership.membershipList.remove(entry.getKey()); + } + //If the membership list entry has timed-out then mark it toBeDeleted + else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000) + { + membershipBean.toBeDeleted = true; + if (membershipBean.hearbeatLastReceived > 0) { + System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); + log.info("CRASHED - - - " + entry.getKey()); } } + } } } From 5d88b0552904f453706ac3a127b194ce94f59582 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 17:33:15 -0600 Subject: [PATCH 23/48] something --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 8 +- .../groupmembership/GroupMembership.java | 108 ++++++++++++++++-- .../boltdb/groupmembership/MergeThread.java | 2 +- 3 files changed, 105 insertions(+), 13 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 3790dfe..e0ee35f 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -73,7 +73,7 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(KVStore.containsKey(key)) throw new RemoteException("Key already present."); @@ -107,7 +107,7 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); @@ -142,7 +142,7 @@ public void update(long key, String value, boolean canBeForwarded) throws Remote String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); @@ -176,7 +176,7 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNodeOf(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 8de348d..f19e60e 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -9,11 +9,13 @@ import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import java.rmi.Naming; +import java.util.ArrayList; import java.util.Date; import java.util.Iterator; import java.util.Map; import java.util.Properties; import java.util.Map.Entry; +import java.util.StringTokenizer; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.Executors; import java.util.concurrent.ScheduledExecutorService; @@ -62,6 +64,7 @@ public class GroupMembership implements Runnable { public static String pid = new String(); public static String pidDelimiter = "--"; public static long bandwidth = 0; + public static int replicationFactor = 1; private String[] args; public GroupMembership(String args[]) { @@ -121,6 +124,9 @@ public void run() { FileInputStream fis = new FileInputStream("./boltdb.prop"); prop.load(fis); fis.close(); + + // Set the replicaton factor from the properties file + replicationFactor = Integer.parseInt(prop.getProperty("groupmembership.rfactor")); // Start the thread that listens to gossip messages. Thread receiveGossip = new Thread(new ReceiveGossipThread()); @@ -197,7 +203,7 @@ public void run() { scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); //Move your keys to successor long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; - String successor = getSuccessorNodeOf(myHash); + String successor = getSuccessorNode(myHash); BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successor + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); @@ -240,6 +246,45 @@ else if(commandString.equals("show")) { System.out.println("-------------------------------------------------"); System.out.println(); } + else if(commandString.equals("ring")) { + System.out.println("-------------------------------------------------"); + System.out.println("Node Ring : "); + int noOfNodes = membershipList.size(); + long node = computeHash(this.pid); + while(noOfNodes-- > 0) { + System.out.print(node + " --> "); + node = computeHash(getSuccessorNode(node)); + } + System.out.println("looparound"); + System.out.println("-------------------------------------------------"); + System.out.println(); + } + else { + StringTokenizer stk = new StringTokenizer(commandString); + String checkCommand = stk.nextToken(); + if(checkCommand.equals("checksucc")) + { + long thisNode = Long.parseLong(stk.nextToken()); + long failedNode = Long.parseLong(stk.nextToken()); + System.out.println("inSuccReReplicationSeg output --> " + inSuccReReplicationSeg(thisNode, failedNode)); + } + else if(checkCommand.equals("checkpred")) + { + long thisNode = Long.parseLong(stk.nextToken()); + long failedNode = Long.parseLong(stk.nextToken()); + System.out.println("inPredReReplicationSeg output --> " + inPredReReplicationSeg(thisNode, failedNode)); + } + else if(checkCommand.equals("succ")) + { + long thisNode = Long.parseLong(stk.nextToken()); + System.out.println("Successor of " + thisNode + " --> " + computeHash(getSuccessorNode(thisNode))); + } + else if(checkCommand.equals("pred")) + { + long thisNode = Long.parseLong(stk.nextToken()); + System.out.println("Predecessor of " + thisNode + " --> " + computeHash(getPredecessorNode(thisNode))); + } + } } } catch (Exception e) { e.printStackTrace(); @@ -265,24 +310,71 @@ public static long computeHash(String pid) throws NoSuchAlgorithmException { * @param keyHash * @return */ - public static String getSuccessorNodeOf(long keyHash) { + public static String getSuccessorNode(long aNode) { Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); //Set the minimum clockwise distance to be maximum possible value long minClockwiseDistance = 1000000L; - String successorHost = new String(); + String successorNode = new String(); while(itr.hasNext()) { Entry entry = itr.next(); //Ignore if the entry is yourself(Server) - if(entry.getValue().hashValue == keyHash) continue; + if(entry.getValue().hashValue == aNode) continue; long hashCurrent = entry.getValue().hashValue; //compute the clockwise distance - long clockWiseDistance = keyHash > hashCurrent ? 1000000l - (keyHash - hashCurrent) : hashCurrent - keyHash; + long clockWiseDistance = aNode > hashCurrent ? 1000000l - (aNode - hashCurrent) : hashCurrent - aNode; //Update minimum clockwise distance if required if(minClockwiseDistance > clockWiseDistance) { minClockwiseDistance = clockWiseDistance; - successorHost = entry.getValue().hostname; + successorNode = entry.getKey(); } } - return successorHost; + return successorNode; + } + + + /** + * Returns the node which is the predecessor of a key. + * @param keyHash + * @return + */ + public static String getPredecessorNode(long aNode) { + Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); + //Set the maximum clockwise distance to be minimum possible value + long maxClockwiseDistance = 0L; + String predecessorNode = new String(); + while(itr.hasNext()) { + Entry entry = itr.next(); + //Ignore if the entry is yourself(Server) + if(entry.getValue().hashValue == aNode) continue; + long hashCurrent = entry.getValue().hashValue; + //compute the clockwise distance + long clockWiseDistance = aNode > hashCurrent ? 1000000L - (aNode - hashCurrent) : hashCurrent - aNode; + //Update minimum clockwise distance if required + if(maxClockwiseDistance < clockWiseDistance) { + maxClockwiseDistance = clockWiseDistance; + predecessorNode = entry.getKey(); + } + } + return predecessorNode; + } + + public static int inSuccReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException + { + int k = replicationFactor; + while(k-- > 0) { + if((failedNode=computeHash(getSuccessorNode(failedNode))) == thisNode) + return (replicationFactor - k); + } + return -1; + } + + public static int inPredReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException + { + int k = replicationFactor; + while(k-- > 0) { + if((failedNode=computeHash(getPredecessorNode(failedNode))) == thisNode) + return (replicationFactor - k); + } + return -1; } -} +} \ No newline at end of file diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 71e52ab..59380a2 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -161,7 +161,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea */ private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; - if(GroupMembership.getSuccessorNodeOf(hashOfNewlyJoinedNode).equals(InetAddress.getLocalHost().getHostName())) return true; + if(GroupMembership.getSuccessorNode(hashOfNewlyJoinedNode).equals(InetAddress.getLocalHost().getHostName())) return true; return false; } From dc2a0df79e2998bbca5f0d9aad943001b1d72006 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 17:43:34 -0600 Subject: [PATCH 24/48] something --- .../boltdb/groupmembership/GroupMembership.java | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index f19e60e..3004d79 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -277,7 +277,8 @@ else if(checkCommand.equals("checkpred")) else if(checkCommand.equals("succ")) { long thisNode = Long.parseLong(stk.nextToken()); - System.out.println("Successor of " + thisNode + " --> " + computeHash(getSuccessorNode(thisNode))); + int k = Integer.parseInt(stk.nextToken()); + System.out.println("Successor of " + thisNode + " --> " + computeHash(getKthSuccessorNode(thisNode, k))); } else if(checkCommand.equals("pred")) { @@ -377,4 +378,15 @@ public static int inPredReReplicationSeg(long thisNode, long failedNode) throws } return -1; } + + public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorithmException + { + String successorNode = new String(); + while(k-- > 0) + { + successorNode = getSuccessorNode(aNode); + aNode = computeHash(successorNode); + } + return successorNode; + } } \ No newline at end of file From 012c70ff03f79fa66c94ec6cafdee4f6cd034144 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Fri, 29 Nov 2013 18:19:11 -0600 Subject: [PATCH 25/48] in the middle-not stable --- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 2 ++ .../java/edu/uiuc/boltdb/BoltDBServer.java | 23 ++++++++++++++++++- .../groupmembership/GroupMembership.java | 13 +++++++++++ .../RefreshMembershipListThread.java | 1 + 4 files changed, 38 insertions(+), 1 deletion(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index 343a5be..a41aeb2 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -50,5 +50,7 @@ public interface BoltDBProtocol extends Remote { * @throws RemoteException */ public void delete(long key, boolean canBeForwarded) throws RemoteException; + + public void lookupAndInsertInto(String hostname, long startKeyRange, long endKeyRange) throws RemoteException; } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 3790dfe..8d1e56a 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -2,11 +2,17 @@ import java.io.IOException; import java.net.InetAddress; +import java.net.MalformedURLException; import java.rmi.Naming; +import java.rmi.NotBoundException; import java.rmi.RemoteException; import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; +import java.util.Collections; import java.util.Map; +import java.util.Map.Entry; +import java.util.SortedMap; +import java.util.TreeMap; import java.util.concurrent.ConcurrentHashMap; import org.apache.log4j.Logger; @@ -37,7 +43,7 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - public static Map KVStore = new ConcurrentHashMap(); + public static SortedMap KVStore = Collections.synchronizedSortedMap(new TreeMap()); public static void main(String[] args) throws IOException { @@ -192,4 +198,19 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { throw new RemoteException("Error occured at Server"); } } + + public void lookupAndInsertInto(String hostname, long startKeyRange, + long endKeyRange) throws RemoteException { + BoltDBProtocol targetServer = null; + try { + targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + hostname + "/KVStore"); + } catch (Exception e) { + log.error(e.getMessage()); + } + SortedMap submap = KVStore.subMap(startKeyRange, endKeyRange); + + for(Entry e : submap.entrySet()) { + targetServer.insert(e.getKey(), e.getValue(), false); + } + } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 8de348d..849026b 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -285,4 +285,17 @@ public static String getSuccessorNodeOf(long keyHash) { } return successorHost; } + + public static void handleCrash(long hashCrashedNode) { + if(inSucReReplicationSegment(hashCrashedNode)) { + String predecessorCrashedNode = getKthPredecessor(hashCrashedNode,1); + long startKeyCrashedNode = GroupMembership.membershipList.get(predecessorCrashedNode).hashValue; + long endKeyCrashedNode = hashCrashedNode; + String myPredecessor = GroupMembership.membershipList.get(getKthPredecessor(GroupMembership.membershipList.get(GroupMembership.pid).hashValue,1)).hostname; + + BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + myPredecessor + "/KVStore"); + successorRMIServer.lookupAndInsertInto(GroupMembership.membershipList.get(GroupMembership.pid).hostname, startKeyCrashedNode, endKeyCrashedNode); + } + } + } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index ff9bee1..75edd9c 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -53,6 +53,7 @@ else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000) if (membershipBean.hearbeatLastReceived > 0) { System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); log.info("CRASHED - - - " + entry.getKey()); + GroupMembership.handleCrash(membershipBean.hashValue); } } From 8b37cd2666c589256777e5eb2b3596f4d551ad1e Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 18:40:40 -0600 Subject: [PATCH 26/48] something --- .../main/java/edu/uiuc/boltdb/BoltDBServer.java | 8 ++++---- .../boltdb/groupmembership/GroupMembership.java | 4 ++-- .../uiuc/boltdb/groupmembership/MergeThread.java | 15 +++++++++++---- 3 files changed, 17 insertions(+), 10 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index e0ee35f..7117b1b 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -73,7 +73,7 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(KVStore.containsKey(key)) throw new RemoteException("Key already present."); @@ -107,7 +107,7 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); @@ -142,7 +142,7 @@ public void update(long key, String value, boolean canBeForwarded) throws Remote String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); @@ -176,7 +176,7 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { String targetHost = null; try { // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString()))); + targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 3004d79..b1f1f73 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -203,8 +203,8 @@ public void run() { scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); //Move your keys to successor long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; - String successor = getSuccessorNode(myHash); - BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successor + "/KVStore"); + String successorHost = GroupMembership.membershipList.get(getSuccessorNode(myHash)).hostname; + BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successorHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 59380a2..f726dff 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -139,7 +139,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); if (returnVal == null) { - System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); + //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); log.info("JOINED - - - " + receivedPid); //Get the successor of newly joined node boolean amISuccessor = amITheSuccesorOf(receivedPid); @@ -161,7 +161,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea */ private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; - if(GroupMembership.getSuccessorNode(hashOfNewlyJoinedNode).equals(InetAddress.getLocalHost().getHostName())) return true; + if(GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(hashOfNewlyJoinedNode)).hostname.equals(InetAddress.getLocalHost().getHostName())) return true; return false; } @@ -179,6 +179,10 @@ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws Malfor BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; + + // Get the rmiserver handle for successor's successor from the rmi registry + String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, 2)).hostname; + BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + succSuccessorHost + "/KVStore"); while(itr.hasNext()) { Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); @@ -188,10 +192,10 @@ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws Malfor if (myHash > hashOfNewJoinedNode) { if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - BoltDBServer.KVStore.remove(entry.getKey()); + //BoltDBServer.KVStore.remove(entry.getKey()); } } - //If hasf of current server is less than hash of newly joined server + //If hash of current server is less than hash of newly joined server //then move all the keys in between the two servers hashes. else { if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { @@ -199,6 +203,9 @@ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws Malfor BoltDBServer.KVStore.remove(entry.getKey()); } } + + // Delete this key in successor's successor + succSuccRMIServer.delete(entry.getKey(), false); } } } From 9530b9b435c0f4755193495a0ec7e2f0eba06164 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 19:04:37 -0600 Subject: [PATCH 27/48] something --- .../boltdb/groupmembership/GroupMembership.java | 14 +++++++++++++- .../uiuc/boltdb/groupmembership/MergeThread.java | 15 ++++++++------- 2 files changed, 21 insertions(+), 8 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index b1f1f73..c531e49 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -283,7 +283,8 @@ else if(checkCommand.equals("succ")) else if(checkCommand.equals("pred")) { long thisNode = Long.parseLong(stk.nextToken()); - System.out.println("Predecessor of " + thisNode + " --> " + computeHash(getPredecessorNode(thisNode))); + int k = Integer.parseInt(stk.nextToken()); + System.out.println("Predecessor of " + thisNode + " --> " + computeHash(getKthPredecessorNode(thisNode, k))); } } } @@ -389,4 +390,15 @@ public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorit } return successorNode; } + + public static String getKthPredecessorNode(long aNode, int k) throws NoSuchAlgorithmException + { + String predecessorNode = new String(); + while(k-- > 0) + { + predecessorNode = getPredecessorNode(aNode); + aNode = computeHash(predecessorNode); + } + return predecessorNode; + } } \ No newline at end of file diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index f726dff..026e87a 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -181,7 +181,7 @@ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws Malfor long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; // Get the rmiserver handle for successor's successor from the rmi registry - String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, 2)).hostname; + String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(hashOfNewJoinedNode, 2)).hostname; BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + succSuccessorHost + "/KVStore"); while(itr.hasNext()) { Entry entry = itr.next(); @@ -193,19 +193,20 @@ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws Malfor if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { targetRMIServer.insert(entry.getKey(), entry.getValue(),false); //BoltDBServer.KVStore.remove(entry.getKey()); + // Delete this key in successor's successor + succSuccRMIServer.delete(entry.getKey(), false); } } //If hash of current server is less than hash of newly joined server //then move all the keys in between the two servers hashes. else { if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - BoltDBServer.KVStore.remove(entry.getKey()); + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + //BoltDBServer.KVStore.remove(entry.getKey()); + // Delete this key in successor's successor + succSuccRMIServer.delete(entry.getKey(), false); } - } - - // Delete this key in successor's successor - succSuccRMIServer.delete(entry.getKey(), false); + } } } } From d8a61a544e33738f622cf5acfe8516ca41099d0a Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 21:24:33 -0600 Subject: [PATCH 28/48] something --- .../boltdb/groupmembership/MergeThread.java | 48 +++++++++++++++++-- 1 file changed, 44 insertions(+), 4 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 026e87a..4d172b7 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -143,10 +143,14 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea log.info("JOINED - - - " + receivedPid); //Get the successor of newly joined node boolean amISuccessor = amITheSuccesorOf(receivedPid); - if(amISuccessor) { //If you are the successor,move keys accordingly. - moveKeys(receivedHost,mBean.hashValue); + moveKeysSucc(receivedHost,mBean.hashValue); + } + + int amIInPredReReplicationSeg = GroupMembership.inPredReReplicationSeg(GroupMembership.computeHash(GroupMembership.pid), GroupMembership.computeHash(receivedPid)); + if(amIInPredReReplicationSeg != -1) { + moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); } } } @@ -174,14 +178,14 @@ private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException * @throws NotBoundException * @throws NoSuchAlgorithmException */ - private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { + private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { //get the rmiserver handle from the rmi registry BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; // Get the rmiserver handle for successor's successor from the rmi registry - String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(hashOfNewJoinedNode, 2)).hostname; + String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, 2)).hostname; BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + succSuccessorHost + "/KVStore"); while(itr.hasNext()) { Entry entry = itr.next(); @@ -209,4 +213,40 @@ private void moveKeys(String targetHost, long hashOfNewJoinedNode) throws Malfor } } } + + private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int amIInPredReReplicationSeg) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { + //get the rmiserver handle from the rmi registry + BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); + Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); + long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; + + // Get the rmiserver handle for (k-p)th successor from the rmi registry + String kpthSuccHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, (GroupMembership.replicationFactor - amIInPredReReplicationSeg))).hostname; + BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + kpthSuccHost + "/KVStore"); + while(itr.hasNext()) { + Entry entry = itr.next(); + long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); + //If hash of current server is greater than hash of newly joined server + //then move all the keys greater than hash of current server + //and less than newly joined server. + if (myHash > hashOfNewJoinedNode) { + if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + //BoltDBServer.KVStore.remove(entry.getKey()); + // Delete this key in successor's successor + succSuccRMIServer.delete(entry.getKey(), false); + } + } + //If hash of current server is less than hash of newly joined server + //then move all the keys in between the two servers hashes. + else { + if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + //BoltDBServer.KVStore.remove(entry.getKey()); + // Delete this key in successor's successor + succSuccRMIServer.delete(entry.getKey(), false); + } + } + } + } } From 29720f5bb6d37819fbadb89157864d80aab89a7f Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 21:50:52 -0600 Subject: [PATCH 29/48] something --- .../boltdb/groupmembership/MergeThread.java | 47 +++++++------------ 1 file changed, 18 insertions(+), 29 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 4d172b7..70c0c83 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -148,9 +148,11 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea moveKeysSucc(receivedHost,mBean.hashValue); } - int amIInPredReReplicationSeg = GroupMembership.inPredReReplicationSeg(GroupMembership.computeHash(GroupMembership.pid), GroupMembership.computeHash(receivedPid)); - if(amIInPredReReplicationSeg != -1) { - moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); + if(GroupMembership.membershipList.size() >= 3) { + int amIInPredReReplicationSeg = GroupMembership.inPredReReplicationSeg(GroupMembership.computeHash(GroupMembership.pid), GroupMembership.computeHash(receivedPid)); + if(amIInPredReReplicationSeg != -1) { + moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); + } } } } @@ -198,7 +200,8 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma targetRMIServer.insert(entry.getKey(), entry.getValue(),false); //BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor - succSuccRMIServer.delete(entry.getKey(), false); + if(GroupMembership.membershipList.size() >= 3) + succSuccRMIServer.delete(entry.getKey(), false); } } //If hash of current server is less than hash of newly joined server @@ -208,7 +211,8 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma targetRMIServer.insert(entry.getKey(), entry.getValue(),false); //BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor - succSuccRMIServer.delete(entry.getKey(), false); + if(GroupMembership.membershipList.size() >= 3) + succSuccRMIServer.delete(entry.getKey(), false); } } } @@ -217,36 +221,21 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int amIInPredReReplicationSeg) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { //get the rmiserver handle from the rmi registry BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; // Get the rmiserver handle for (k-p)th successor from the rmi registry - String kpthSuccHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, (GroupMembership.replicationFactor - amIInPredReReplicationSeg))).hostname; - BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + kpthSuccHost + "/KVStore"); + String kpthSuccHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(hashOfNewJoinedNode, (GroupMembership.replicationFactor - amIInPredReReplicationSeg))).hostname; + BoltDBProtocol kpthSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + kpthSuccHost + "/KVStore"); + + long myPredecessor = GroupMembership.computeHash(GroupMembership.getPredecessorNode(myHash)); + Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); - //If hash of current server is greater than hash of newly joined server - //then move all the keys greater than hash of current server - //and less than newly joined server. - if (myHash > hashOfNewJoinedNode) { - if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - //BoltDBServer.KVStore.remove(entry.getKey()); - // Delete this key in successor's successor - succSuccRMIServer.delete(entry.getKey(), false); - } - } - //If hash of current server is less than hash of newly joined server - //then move all the keys in between the two servers hashes. - else { - if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - //BoltDBServer.KVStore.remove(entry.getKey()); - // Delete this key in successor's successor - succSuccRMIServer.delete(entry.getKey(), false); - } - } + if ( hashOfKey > myPredecessor && hashOfKey <= myHash) { + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + kpthSuccRMIServer.delete(entry.getKey(), false); + } } } } From 0039e49cf5e2c1e5f2196a1127a00a59b28b431e Mon Sep 17 00:00:00 2001 From: Adarsh Date: Fri, 29 Nov 2013 21:54:50 -0600 Subject: [PATCH 30/48] something --- .../main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 70c0c83..0142fc4 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -127,7 +127,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme System.out.println("JOINED : " + receivedPid); currentMBean.toBeDeleted = false; } - GroupMembership.membershipList.put(receivedPid, currentMBean); + GroupMembership.membershipList.put(receivedPid, currentMBean); } } else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBean.hearbeatLastReceived > 0) From a66164a9da6c5e47f8c01f4e4d55b98573d0ee92 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sat, 30 Nov 2013 00:24:30 -0600 Subject: [PATCH 31/48] something --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 2 +- .../groupmembership/GroupMembership.java | 20 +++++++- .../boltdb/groupmembership/MergeThread.java | 47 ++++++++++++++----- .../RefreshMembershipListThread.java | 2 +- 4 files changed, 54 insertions(+), 17 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 1713129..9e3b224 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -107,7 +107,7 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote KVStore.put(key, value); } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming - .lookup("rmi://" + targetHosts[i] + "/KVStore"); + .lookup("rmi://" + GroupMembership.membershipList.get(targetHosts[i]).hostname + "/KVStore"); targetServer.insert(key, value, false); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 960ef1f..a3ec1ca 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -235,16 +235,32 @@ else if(commandString.equals("show")) { System.out.println("-------------------------------------------------"); for (Map.Entry entry : membershipList.entrySet()) { - System.out.println(entry); + System.out.println(entry.getValue().hostname + " " + entry.getValue().hashValue); } System.out.println("-------------------------------------------------"); System.out.println(); System.out.println("-------------------------------------------------"); System.out.println("Key Value Store : "); System.out.println("-------------------------------------------------"); + long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; + long myPredecessor = GroupMembership.membershipList.get(GroupMembership.getPredecessorNode(myHash)).hashValue; for (Map.Entry entry : BoltDBServer.KVStore.entrySet()) { - System.out.println(entry.getKey() + " ---> " + entry.getValue() + " | Hash Value of Key - " + computeHash((new Long(entry.getKey())).toString())); + long hashOfKey = computeHash((new Long(entry.getKey())).toString()); + System.out.print(entry.getKey() + " ---> " + entry.getValue() + " | Hash of Key - " + hashOfKey + " "); + if(myHash > myPredecessor) { + if(hashOfKey > myPredecessor && hashOfKey <= myHash) + System.out.println("Primary"); + else + System.out.println("Replica"); + } + else { + if(hashOfKey > myPredecessor || hashOfKey <= myHash) + System.out.println("Primary"); + else + System.out.println("Replica"); + } + } System.out.println("-------------------------------------------------"); System.out.println(); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 0142fc4..565b9a6 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -144,13 +144,14 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea //Get the successor of newly joined node boolean amISuccessor = amITheSuccesorOf(receivedPid); if(amISuccessor) { - //If you are the successor,move keys accordingly. + //If you are the successor,move keys accordingly. + System.out.println("hey I'm the succ of newly joined node:"+receivedHost); moveKeysSucc(receivedHost,mBean.hashValue); } - - if(GroupMembership.membershipList.size() >= 3) { - int amIInPredReReplicationSeg = GroupMembership.inPredReReplicationSeg(GroupMembership.computeHash(GroupMembership.pid), GroupMembership.computeHash(receivedPid)); + else if(GroupMembership.membershipList.size() >= 3) { + int amIInPredReReplicationSeg = GroupMembership.inPredReReplicationSeg(GroupMembership.membershipList.get(GroupMembership.pid).hashValue, mBean.hashValue); if(amIInPredReReplicationSeg != -1) { + System.out.println("hey I'm the "+amIInPredReReplicationSeg+" pred of newly joined node:"+receivedHost); moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); } } @@ -197,45 +198,65 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma //and less than newly joined server. if (myHash > hashOfNewJoinedNode) { if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { + System.out.println("Inserting key :" + entry.getKey() + " value:"+entry.getValue() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); //BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor - if(GroupMembership.membershipList.size() >= 3) + if(GroupMembership.membershipList.size() >= 3) { + System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); succSuccRMIServer.delete(entry.getKey(), false); + } } } //If hash of current server is less than hash of newly joined server //then move all the keys in between the two servers hashes. else { if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { + System.out.println("Inserting key :" + entry.getKey() + " value:"+entry.getValue() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); //BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor - if(GroupMembership.membershipList.size() >= 3) + if(GroupMembership.membershipList.size() >= 3) { + System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); succSuccRMIServer.delete(entry.getKey(), false); + } } } } } - private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int amIInPredReReplicationSeg) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { + private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int predecessorPosition) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { //get the rmiserver handle from the rmi registry BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; // Get the rmiserver handle for (k-p)th successor from the rmi registry - String kpthSuccHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(hashOfNewJoinedNode, (GroupMembership.replicationFactor - amIInPredReReplicationSeg))).hostname; + String kpthSuccHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(hashOfNewJoinedNode, (GroupMembership.replicationFactor - predecessorPosition))).hostname; BoltDBProtocol kpthSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + kpthSuccHost + "/KVStore"); - long myPredecessor = GroupMembership.computeHash(GroupMembership.getPredecessorNode(myHash)); + long myPredecessor = GroupMembership.membershipList.get(GroupMembership.getPredecessorNode(myHash)).hashValue; Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); - if ( hashOfKey > myPredecessor && hashOfKey <= myHash) { - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - kpthSuccRMIServer.delete(entry.getKey(), false); - } + if (myHash > myPredecessor) { + if ( hashOfKey > myPredecessor && hashOfKey <= myHash) { + System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + + System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); + kpthSuccRMIServer.delete(entry.getKey(), false); + } + } + else { + if ( hashOfKey > myPredecessor || hashOfKey <= myHash) { + System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); + targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + + System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); + kpthSuccRMIServer.delete(entry.getKey(), false); + } + } } } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index 81e3871..d891348 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -48,7 +48,7 @@ public void run() if (membershipBean.toBeDeleted) { try { - GroupMembership.handleCrash(membershipBean.hashValue); + //GroupMembership.handleCrash(membershipBean.hashValue); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); From 5d2463a4a02a7d58bcee2ad6b6b86be0890556d6 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 1 Dec 2013 17:34:38 -0600 Subject: [PATCH 32/48] join changes --- .../groupmembership/GroupMembership.java | 2 +- .../boltdb/groupmembership/MergeThread.java | 131 +++++++++++------- 2 files changed, 85 insertions(+), 48 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index a3ec1ca..c1c3222 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -414,7 +414,7 @@ public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorit public static void handleCrash(long hashCrashedNode) throws NoSuchAlgorithmException, MalformedURLException, NotBoundException { - //TODO doesnt work for k=1,2; + //TODO doesnt work for k=1,2; && need to compute hash of keys before comparing at all places long myhash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; if (inSuccReReplicationSeg(hashCrashedNode, myhash) != -1) { String predecessorCrashedNode = getKthPredecessorNode( diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 565b9a6..93ce4de 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -9,6 +9,7 @@ import java.rmi.NotBoundException; import java.rmi.RemoteException; import java.security.NoSuchAlgorithmException; +import java.security.acl.Group; import java.util.Date; import java.util.HashMap; import java.util.Iterator; @@ -134,28 +135,39 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea { //JOIN : If the incoming entry is not in our membership list then it means a new node has joined. //if(receivedMBean.hearbeatLastReceived <= 0) continue; - String receivedHost = receivedPid.split(GroupMembership.pidDelimiter)[0]; - MembershipBean mBean = new MembershipBean(receivedHost, receivedMBean.hearbeatLastReceived, System.currentTimeMillis(), receivedMBean.hashValue, false); - MembershipBean returnVal = GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); - if (returnVal == null) - { - //System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); - log.info("JOINED - - - " + receivedPid); - //Get the successor of newly joined node - boolean amISuccessor = amITheSuccesorOf(receivedPid); - if(amISuccessor) { - //If you are the successor,move keys accordingly. - System.out.println("hey I'm the succ of newly joined node:"+receivedHost); - moveKeysSucc(receivedHost,mBean.hashValue); - } - else if(GroupMembership.membershipList.size() >= 3) { - int amIInPredReReplicationSeg = GroupMembership.inPredReReplicationSeg(GroupMembership.membershipList.get(GroupMembership.pid).hashValue, mBean.hashValue); - if(amIInPredReReplicationSeg != -1) { - System.out.println("hey I'm the "+amIInPredReReplicationSeg+" pred of newly joined node:"+receivedHost); - moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); - } + String receivedHost = receivedPid + .split(GroupMembership.pidDelimiter)[0]; + MembershipBean mBean = new MembershipBean(receivedHost, + receivedMBean.hearbeatLastReceived, + System.currentTimeMillis(), receivedMBean.hashValue, + false); + + // System.out.println("JOINED : " + receivedPid+" at "+(new + // Date()).toString()); + log.info("JOINED - - - " + receivedPid); + // Get the successor of newly joined node + boolean amISuccessor = amITheSuccesorOf(receivedPid); + if (amISuccessor) { + // If you are the successor,move keys accordingly. + System.out.println("hey I'm the succ of newly joined node:" + + receivedHost); + moveKeysSucc(receivedHost, mBean.hashValue); + } else if (GroupMembership.membershipList.size() >= 3) { + int amIInPredReReplicationSeg = GroupMembership + .inPredReReplicationSeg( + GroupMembership.membershipList + .get(GroupMembership.pid).hashValue, + mBean.hashValue); + if (amIInPredReReplicationSeg != -1) { + System.out.println("hey I'm the " + + amIInPredReReplicationSeg + + " pred of newly joined node:" + receivedHost); + moveKeysPred(receivedHost, mBean.hashValue, + amIInPredReReplicationSeg); } } + GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); + } } } @@ -190,41 +202,66 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma // Get the rmiserver handle for successor's successor from the rmi registry String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, 2)).hostname; BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + succSuccessorHost + "/KVStore"); + long predecessorHash = GroupMembership.membershipList.get(GroupMembership.getKthPredecessorNode(myHash, 1)).hashValue; + while(itr.hasNext()) { Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); - //If hash of current server is greater than hash of newly joined server - //then move all the keys greater than hash of current server - //and less than newly joined server. - if (myHash > hashOfNewJoinedNode) { - if ( hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { - System.out.println("Inserting key :" + entry.getKey() + " value:"+entry.getValue() + " from Me to " + targetHost); - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - //BoltDBServer.KVStore.remove(entry.getKey()); - // Delete this key in successor's successor - if(GroupMembership.membershipList.size() >= 3) { - System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); - succSuccRMIServer.delete(entry.getKey(), false); + if (predecessorHash == myHash + || amIPrimaryReplicaFor(hashOfKey, myHash, predecessorHash)) { + // If hash of current server is greater than hash of newly + // joined server + // then move all the keys greater than hash of current server + // and less than newly joined server. + if (myHash > hashOfNewJoinedNode) { + if (hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { + System.out.println("Inserting key :" + entry.getKey() + + " value:" + entry.getValue() + " from Me to " + + targetHost); + targetRMIServer.insert(entry.getKey(), + entry.getValue(), false); + // BoltDBServer.KVStore.remove(entry.getKey()); + // Delete this key in successor's successor + if (GroupMembership.membershipList.size() >= 3) { + System.out.println("Deleting key :" + + entry.getKey() + " from " + + succSuccessorHost); + succSuccRMIServer.delete(entry.getKey(), false); + } } - } - } - //If hash of current server is less than hash of newly joined server - //then move all the keys in between the two servers hashes. - else { - if ( hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { - System.out.println("Inserting key :" + entry.getKey() + " value:"+entry.getValue() + " from Me to " + targetHost); - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); - //BoltDBServer.KVStore.remove(entry.getKey()); - // Delete this key in successor's successor - if(GroupMembership.membershipList.size() >= 3) { - System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); - succSuccRMIServer.delete(entry.getKey(), false); + } + // If hash of current server is less than hash of newly joined + // server + // then move all the keys in between the two servers hashes. + else { + if (hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { + System.out.println("Inserting key :" + entry.getKey() + + " value:" + entry.getValue() + " from Me to " + + targetHost); + targetRMIServer.insert(entry.getKey(), + entry.getValue(), false); + // BoltDBServer.KVStore.remove(entry.getKey()); + // Delete this key in successor's successor + if (GroupMembership.membershipList.size() >= 3) { + System.out.println("Deleting key :" + + entry.getKey() + " from " + + succSuccessorHost); + succSuccRMIServer.delete(entry.getKey(), false); + } } - } - } + } + } } } + private boolean amIPrimaryReplicaFor(long key,long myHash,long predecessorHash) { + if (myHash > predecessorHash) { + if (key > predecessorHash && key <= myHash) return true; + } else { + if (key > predecessorHash || key <= myHash) return true; + } + return false; + } private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int predecessorPosition) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { //get the rmiserver handle from the rmi registry BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); From 4fec6d2add0a9a3ec3ce3d4324a1acd8d3e7f366 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 1 Dec 2013 17:54:03 -0600 Subject: [PATCH 33/48] join changes --- .../edu/uiuc/boltdb/groupmembership/GroupMembership.java | 9 +++++---- .../edu/uiuc/boltdb/groupmembership/MergeThread.java | 5 ++--- 2 files changed, 7 insertions(+), 7 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index c1c3222..88c182a 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -416,7 +416,8 @@ public static void handleCrash(long hashCrashedNode) NotBoundException { //TODO doesnt work for k=1,2; && need to compute hash of keys before comparing at all places long myhash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; - if (inSuccReReplicationSeg(hashCrashedNode, myhash) != -1) { + int successorPosition = inSuccReReplicationSeg(hashCrashedNode, myhash); + if (successorPosition != -1) { String predecessorCrashedNode = getKthPredecessorNode( hashCrashedNode, 1); long startKeyCrashedNode = GroupMembership.membershipList @@ -430,12 +431,12 @@ public static void handleCrash(long hashCrashedNode) GroupMembership.membershipList .get(GroupMembership.pid).hashValue, i)).hostname; - BoltDBProtocol successorRMIServer; + BoltDBProtocol predecessorRMIServer; try { - successorRMIServer = (BoltDBProtocol) Naming + predecessorRMIServer = (BoltDBProtocol) Naming .lookup("rmi://" + myPredecessor + "/KVStore"); - successorRMIServer.lookupAndInsertInto( + predecessorRMIServer.lookupAndInsertInto( GroupMembership.membershipList .get(GroupMembership.pid).hostname, startKeyCrashedNode, endKeyCrashedNode); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 93ce4de..aa95e12 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -146,7 +146,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea // Date()).toString()); log.info("JOINED - - - " + receivedPid); // Get the successor of newly joined node - boolean amISuccessor = amITheSuccesorOf(receivedPid); + boolean amISuccessor = amITheSuccesorOf(receivedMBean.hashValue); if (amISuccessor) { // If you are the successor,move keys accordingly. System.out.println("hey I'm the succ of newly joined node:" @@ -178,8 +178,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea * @return * @throws UnknownHostException */ - private boolean amITheSuccesorOf(String receivedPid) throws UnknownHostException { - long hashOfNewlyJoinedNode = GroupMembership.membershipList.get(receivedPid).hashValue; + private boolean amITheSuccesorOf(long hashOfNewlyJoinedNode) throws UnknownHostException { if(GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(hashOfNewlyJoinedNode)).hostname.equals(InetAddress.getLocalHost().getHostName())) return true; return false; } From 2377f73a3bffd0101e401d17ff8da1f0e73931fc Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 1 Dec 2013 20:51:35 -0600 Subject: [PATCH 34/48] something --- .../groupmembership/GroupMembership.java | 9 ++-- .../boltdb/groupmembership/MergeThread.java | 45 ++++++++++--------- 2 files changed, 31 insertions(+), 23 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 88c182a..807d038 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -29,8 +29,7 @@ import org.apache.log4j.Logger; import org.apache.log4j.PatternLayout; -import edu.uiuc.boltdb.BoltDBProtocol; -import edu.uiuc.boltdb.BoltDBServer; +import edu.uiuc.boltdb.*; import edu.uiuc.boltdb.groupmembership.beans.*; /** @@ -69,6 +68,7 @@ public class GroupMembership implements Runnable { public static long bandwidth = 0; public static int replicationFactor = 1; private String[] args; + public static int tFail = 3; public GroupMembership(String args[]) { this.args = args; @@ -157,7 +157,7 @@ public void run() { } // Get the tFail from property file - int tFail = Integer.parseInt(prop + tFail = Integer.parseInt(prop .getProperty("groupmembership.tfail")); // ScheduledExecutorService is used to schedule all the threads @@ -321,6 +321,9 @@ else if(checkCommand.equals("pred")) * @throws NoSuchAlgorithmException */ public static long computeHash(String pid) throws NoSuchAlgorithmException { + if(pid.length() <= 6 && !pid.isEmpty()) + return Long.parseLong(pid); + MessageDigest md = MessageDigest.getInstance("MD5"); BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); return Math.abs(bigInt.longValue()) % 1000001L; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index aa95e12..2b2c6cf 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -85,7 +85,7 @@ private void getGossipFromClient() throws IOException * @throws MalformedURLException * @throws NoSuchAlgorithmException */ - private void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException + private synchronized void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { Iterator> iterator = incomingMembershipList.entrySet().iterator(); //Iterate over each entry of incoming membershiplist @@ -146,24 +146,27 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea // Date()).toString()); log.info("JOINED - - - " + receivedPid); // Get the successor of newly joined node - boolean amISuccessor = amITheSuccesorOf(receivedMBean.hashValue); - if (amISuccessor) { - // If you are the successor,move keys accordingly. - System.out.println("hey I'm the succ of newly joined node:" - + receivedHost); - moveKeysSucc(receivedHost, mBean.hashValue); - } else if (GroupMembership.membershipList.size() >= 3) { - int amIInPredReReplicationSeg = GroupMembership - .inPredReReplicationSeg( - GroupMembership.membershipList - .get(GroupMembership.pid).hashValue, - mBean.hashValue); - if (amIInPredReReplicationSeg != -1) { - System.out.println("hey I'm the " - + amIInPredReReplicationSeg - + " pred of newly joined node:" + receivedHost); - moveKeysPred(receivedHost, mBean.hashValue, - amIInPredReReplicationSeg); + if((System.currentTimeMillis() - GroupMembership.membershipList.get(GroupMembership.pid).timeStamp) > GroupMembership.tFail) { + + boolean amISuccessor = amITheSuccesorOf(receivedMBean.hashValue); + if (amISuccessor) { + // If you are the successor,move keys accordingly. + System.out.println("hey I'm the succ of newly joined node:" + + receivedHost); + moveKeysSucc(receivedHost, mBean.hashValue); + } else if (GroupMembership.membershipList.size() >= 3) { + int amIInPredReReplicationSeg = GroupMembership + .inPredReReplicationSeg( + GroupMembership.membershipList + .get(GroupMembership.pid).hashValue, + mBean.hashValue); + if (amIInPredReReplicationSeg != -1) { + System.out.println("hey I'm the " + + amIInPredReReplicationSeg + + " pred of newly joined node:" + receivedHost); + moveKeysPred(receivedHost, mBean.hashValue, + amIInPredReReplicationSeg); + } } } GroupMembership.membershipList.putIfAbsent(receivedPid, mBean); @@ -201,7 +204,9 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma // Get the rmiserver handle for successor's successor from the rmi registry String succSuccessorHost = GroupMembership.membershipList.get(GroupMembership.getKthSuccessorNode(myHash, 2)).hostname; BoltDBProtocol succSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + succSuccessorHost + "/KVStore"); - long predecessorHash = GroupMembership.membershipList.get(GroupMembership.getKthPredecessorNode(myHash, 1)).hashValue; + long predecessorHash = myHash; + if(GroupMembership.membershipList.size() > 1) + predecessorHash = GroupMembership.membershipList.get(GroupMembership.getKthPredecessorNode(myHash, 1)).hashValue; while(itr.hasNext()) { Entry entry = itr.next(); From 42d7e2c99ac3df164c8f9fbb07404fe57b9572f9 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 1 Dec 2013 23:24:41 -0600 Subject: [PATCH 35/48] join replication --- .../boltdb/groupmembership/GroupMembership.java | 8 ++++++-- .../uiuc/boltdb/groupmembership/MergeThread.java | 13 ++++++++----- .../boltdb/groupmembership/ReceiveGossipThread.java | 5 +++-- 3 files changed, 17 insertions(+), 9 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 807d038..17ad011 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -62,8 +62,9 @@ */ public class GroupMembership implements Runnable { private static org.apache.log4j.Logger log = Logger.getRootLogger(); - public static ConcurrentHashMap membershipList = new ConcurrentHashMap(); + public static volatile ConcurrentHashMap membershipList = new ConcurrentHashMap(); public static String pid = new String(); + public static long startTime; public static String pidDelimiter = "--"; public static long bandwidth = 0; public static int replicationFactor = 1; @@ -113,6 +114,9 @@ public void run() { //Compute the hashvalue of yourself(server) long hashValue = computeHash(pid); + + startTime = System.currentTimeMillis(); + // Insert the current machine into the membership list with // heartbeat=1. This single entry is going to be sent to the contact // node for joining the cluster. @@ -395,7 +399,7 @@ public static int inSuccReReplicationSeg(long thisNode, long failedNode) throws public static int inPredReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException { int k = replicationFactor; - while(k-- > 0) { + while(k-- > 1) { if((failedNode=computeHash(getPredecessorNode(failedNode))) == thisNode) return (replicationFactor - k); } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index 2b2c6cf..c51f3bb 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -39,11 +39,12 @@ public class MergeThread implements Runnable Map incomingMembershipList = null; String receivedJson = new String(); String sentHost; - - public MergeThread(String sentHost, String json) + Object lock; + public MergeThread(String sentHost, String json, Object lock) { this.sentHost = sentHost; this.receivedJson = json; + this.lock = lock; } public void run() @@ -58,7 +59,9 @@ public void run() return; } try { - mergeIncomingMembershipList(); + synchronized (lock) { + mergeIncomingMembershipList(); + } } catch (Exception e) { e.printStackTrace(); } @@ -85,7 +88,7 @@ private void getGossipFromClient() throws IOException * @throws MalformedURLException * @throws NoSuchAlgorithmException */ - private synchronized void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException + private void mergeIncomingMembershipList() throws UnknownHostException, MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { Iterator> iterator = incomingMembershipList.entrySet().iterator(); //Iterate over each entry of incoming membershiplist @@ -146,7 +149,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea // Date()).toString()); log.info("JOINED - - - " + receivedPid); // Get the successor of newly joined node - if((System.currentTimeMillis() - GroupMembership.membershipList.get(GroupMembership.pid).timeStamp) > GroupMembership.tFail) { + if((System.currentTimeMillis() - GroupMembership.startTime) > (GroupMembership.tFail * 1000)) { boolean amISuccessor = amITheSuccesorOf(receivedMBean.hashValue); if (amISuccessor) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/ReceiveGossipThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/ReceiveGossipThread.java index d77d9f4..fc6888d 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/ReceiveGossipThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/ReceiveGossipThread.java @@ -12,10 +12,11 @@ public class ReceiveGossipThread implements Runnable { private DatagramSocket serverSocket; private int gossipPort = 8764; - + private Object lock; public ReceiveGossipThread() throws IOException { serverSocket = new DatagramSocket(gossipPort); + lock = new Object(); } public void run() @@ -38,7 +39,7 @@ public void run() //System.out.println("Packet received:"+(receive.getLength() + 8)); String receivedJson = new String(receive.getData()); String sentHost = receive.getAddress().getHostName(); - MergeThread mergeThread = new MergeThread(sentHost,receivedJson.trim()); + MergeThread mergeThread = new MergeThread(sentHost,receivedJson.trim(),lock); new Thread(mergeThread).start(); } } From 221d397bbc7f4fd5ab09dca9c95e4e425d35debf Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Tue, 3 Dec 2013 17:15:01 -0600 Subject: [PATCH 36/48] commenting handle crash --- .../groupmembership/GroupMembership.java | 26 +++++++++++++------ 1 file changed, 18 insertions(+), 8 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 88c182a..013cc8c 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -411,18 +411,28 @@ public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorit } - public static void handleCrash(long hashCrashedNode) + /*public synchronized static void handleCrash(long hashCrashedNode) throws NoSuchAlgorithmException, MalformedURLException, NotBoundException { //TODO doesnt work for k=1,2; && need to compute hash of keys before comparing at all places long myhash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; int successorPosition = inSuccReReplicationSeg(hashCrashedNode, myhash); if (successorPosition != -1) { - String predecessorCrashedNode = getKthPredecessorNode( - hashCrashedNode, 1); - long startKeyCrashedNode = GroupMembership.membershipList - .get(predecessorCrashedNode).hashValue + 1; - long endKeyCrashedNode = hashCrashedNode; + long startKey, endKey; + + if(successorPosition == 3) { + String predecessorCrashedNode = getKthPredecessorNode( + hashCrashedNode, 1); + startKey = GroupMembership.membershipList + .get(predecessorCrashedNode).hashValue + 1; + endKey = hashCrashedNode; + } else { + String targetNode = getKthPredecessorNode(hashCrashedNode, replicationFactor - successorPosition); + //String predOfTargetNode = getP + startKey = GroupMembership.membershipList + .get(targetNode).hashValue + 1; + } + int i = 0; while (i < replicationFactor) { i++; @@ -439,14 +449,14 @@ public static void handleCrash(long hashCrashedNode) predecessorRMIServer.lookupAndInsertInto( GroupMembership.membershipList .get(GroupMembership.pid).hostname, - startKeyCrashedNode, endKeyCrashedNode); + startKey, endKey); break; } catch (RemoteException e) { continue; } } } - } + }*/ From cc56c18cbb20623cbd6bf49bc9e785c9c6dcf0d6 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Tue, 3 Dec 2013 21:54:36 -0600 Subject: [PATCH 37/48] crash working --- .../java/edu/uiuc/boltdb/BoltDBServer.java | 26 ++++++-- .../groupmembership/GroupMembership.java | 64 ++++++++++--------- .../RefreshMembershipListThread.java | 2 +- 3 files changed, 56 insertions(+), 36 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 9e3b224..4c42dd3 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -230,10 +230,28 @@ public void lookupAndInsertInto(String hostname, long startKeyRange, } catch (Exception e) { log.error(e.getMessage()); } - SortedMap submap = KVStore.subMap(startKeyRange, endKeyRange); - - for(Entry e : submap.entrySet()) { - targetServer.insert(e.getKey(), e.getValue(), false); + System.out.println("lookupAndInsert: start - "+startKeyRange+" end - "+ endKeyRange); + for(Entry e : KVStore.entrySet()) { + try { + long hashOfKey = GroupMembership.computeHash(e.getKey().toString()); + System.out.println("lookupAndInsert: hashOfkey - "+hashOfKey); + if (startKeyRange < endKeyRange) { + if (hashOfKey >= startKeyRange && hashOfKey <= endKeyRange) { + System.out.println("Inserting " + hashOfKey + " from " + + GroupMembership.pid + " to " + hostname); + targetServer.insert(e.getKey(), e.getValue(), false); + } + } else { + if (hashOfKey >= startKeyRange || hashOfKey <= endKeyRange) { + System.out.println("Inserting " + hashOfKey + " from " + + GroupMembership.pid + " to " + hostname); + targetServer.insert(e.getKey(), e.getValue(), false); + } + } + } catch (NoSuchAlgorithmException e1) { + // TODO Auto-generated catch block + e1.printStackTrace(); + } } } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 4e22d94..a9ef039 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -418,52 +418,54 @@ public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorit } - /*public synchronized static void handleCrash(long hashCrashedNode) + public synchronized static void handleCrash(long hashCrashedNode) throws NoSuchAlgorithmException, MalformedURLException, NotBoundException { //TODO doesnt work for k=1,2; && need to compute hash of keys before comparing at all places - long myhash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; - int successorPosition = inSuccReReplicationSeg(hashCrashedNode, myhash); + if(membershipList.size() <= 3) return; + long myhash = membershipList.get(GroupMembership.pid).hashValue; + int successorPosition = inSuccReReplicationSeg(myhash,hashCrashedNode); if (successorPosition != -1) { + System.out.println("successor position:"+successorPosition); long startKey, endKey; - + String targetNode; if(successorPosition == 3) { - String predecessorCrashedNode = getKthPredecessorNode( - hashCrashedNode, 1); - startKey = GroupMembership.membershipList - .get(predecessorCrashedNode).hashValue + 1; + startKey = membershipList.get(getPredecessorNode(hashCrashedNode)).hashValue + 1; endKey = hashCrashedNode; - } else { - String targetNode = getKthPredecessorNode(hashCrashedNode, replicationFactor - successorPosition); - //String predOfTargetNode = getP - startKey = GroupMembership.membershipList - .get(targetNode).hashValue + 1; + targetNode = getSuccessorNode(hashCrashedNode); + } + else { + targetNode = getKthPredecessorNode(hashCrashedNode, replicationFactor - successorPosition); + startKey = membershipList.get(getPredecessorNode(membershipList.get(targetNode).hashValue)).hashValue + 1; + endKey = membershipList.get(targetNode).hashValue; } - + + System.out.println("startkey:"+startKey+ " endKey:"+endKey+" targetNode:"+targetNode); + BoltDBProtocol targetRMIServer = null; int i = 0; - while (i < replicationFactor) { - i++; - String myPredecessor = GroupMembership.membershipList - .get(getKthPredecessorNode( - GroupMembership.membershipList - .get(GroupMembership.pid).hashValue, i)).hostname; - - BoltDBProtocol predecessorRMIServer; - + System.out.println("membership list:"+ membershipList); + while (i++ < replicationFactor - 1) { try { - predecessorRMIServer = (BoltDBProtocol) Naming - .lookup("rmi://" + myPredecessor + "/KVStore"); - predecessorRMIServer.lookupAndInsertInto( - GroupMembership.membershipList - .get(GroupMembership.pid).hostname, - startKey, endKey); + System.out.println("trying to connect to targetNode pid :"+targetNode+" with hostname :"+ membershipList.get(targetNode).hostname ); + targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + + membershipList.get(targetNode).hostname + "/KVStore"); + targetRMIServer.lookupAndInsertInto(membershipList.get(pid).hostname, startKey, endKey); break; - } catch (RemoteException e) { + } catch (RemoteException e1) { + System.out.println("Exception while connecting to "+targetNode+ " "+e1.getMessage()); + targetNode = getSuccessorNode(GroupMembership.membershipList + .get(targetNode).hashValue); continue; } } + + if(targetRMIServer == null) { + System.out.println("Problem replicating keys during crash"); + log.error("Problem replicating keys during crash"); + return; + } } - }*/ + } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index d891348..81e3871 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -48,7 +48,7 @@ public void run() if (membershipBean.toBeDeleted) { try { - //GroupMembership.handleCrash(membershipBean.hashValue); + GroupMembership.handleCrash(membershipBean.hashValue); } catch (Exception e) { // TODO Auto-generated catch block e.printStackTrace(); From 722df1e4de336f1081aeb779853509353c1016d6 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Thu, 5 Dec 2013 22:07:51 -0600 Subject: [PATCH 38/48] Movie search client --- .../boltdb/examples/MovieSearchClient.java | 102 ++++++++++++++++++ 1 file changed, 102 insertions(+) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java new file mode 100644 index 0000000..d6f19d9 --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java @@ -0,0 +1,102 @@ +package edu.uiuc.boltdb.examples; + +import java.io.BufferedReader; +import java.io.FileInputStream; +import java.io.IOException; +import java.io.InputStreamReader; +import java.net.MalformedURLException; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.rmi.RemoteException; +import java.security.NoSuchAlgorithmException; +import java.util.Properties; +import java.util.StringTokenizer; + +import edu.uiuc.boltdb.BoltDBProtocol; +import edu.uiuc.boltdb.groupmembership.GroupMembership; + +/** + * + * @author Adarsh + * + */ + +public class MovieSearchClient { + + private BoltDBProtocol boltDBServer = null; + + public MovieSearchClient(String rmiString) throws MalformedURLException, RemoteException, NotBoundException { + if(System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); + } + + /** + * @param args + * @throws IOException + * @throws NotBoundException + */ + public static void main(String[] args) { + try { + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.kvstore.server"); + MovieSearchClient movieSearchClient = new MovieSearchClient(rmiString); + movieSearchClient.runClient(); + } catch(Exception e) { + e.printStackTrace(); + } + } + + private void runClient() throws IOException, NoSuchAlgorithmException { + String keyWordString = ""; + BufferedReader console = new BufferedReader(new InputStreamReader(System.in)); + + System.out.println(); + System.out.println("-----------------------------------------------"); + System.out.println("MOVIE SEARCH"); + System.out.println("-----------------------------------------------"); + + while (true) { + System.out.print("Enter the keyword to search: "); + keyWordString = console.readLine(); + + // If the user entered a return, just loop again + if (keyWordString.equals("")) { + System.out.println("You did not enter anything"); + System.out.println(); + continue; + } + searchMovie(keyWordString); + } + } + + private void searchMovie(String keyWordString) throws NoSuchAlgorithmException { + try { + StringTokenizer stk = new StringTokenizer(keyWordString); + String keyWord = stk.nextToken(); + long key = GroupMembership.computeHash(keyWord); + + String result = (String)boltDBServer.lookup(key, true); + + stk = new StringTokenizer(result, ","); + + System.out.println(); + System.out.println("-----------------------------------------------"); + System.out.println("Found " + stk.countTokens() + " movie titles matchin " + " \"" + keyWord + "\""); + System.out.println("-----------------------------------------------"); + while(stk.hasMoreTokens()) + System.out.println(stk.nextToken()); + System.out.println("-----------------------------------------------"); + + } catch(RemoteException re) { + if(re.getCause().getCause() != null) + System.out.println(re.getCause().getCause().getMessage()); + else + System.out.println(re.getCause().getMessage()); + } + } +} From 9aa4a367285dff43d9f02d21aafa54d64b40c248 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sat, 7 Dec 2013 18:12:25 -0600 Subject: [PATCH 39/48] application --- .../boltdb/groupmembership/GroupMembership.java | 1 - .../uiuc/boltdb/groupmembership/MergeThread.java | 14 +++++++------- .../RefreshMembershipListThread.java | 4 ++-- 3 files changed, 9 insertions(+), 10 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index a9ef039..5ca0155 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -443,7 +443,6 @@ public synchronized static void handleCrash(long hashCrashedNode) System.out.println("startkey:"+startKey+ " endKey:"+endKey+" targetNode:"+targetNode); BoltDBProtocol targetRMIServer = null; int i = 0; - System.out.println("membership list:"+ membershipList); while (i++ < replicationFactor - 1) { try { System.out.println("trying to connect to targetNode pid :"+targetNode+" with hostname :"+ membershipList.get(targetNode).hostname ); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index c51f3bb..b085170 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -145,8 +145,8 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea System.currentTimeMillis(), receivedMBean.hashValue, false); - // System.out.println("JOINED : " + receivedPid+" at "+(new - // Date()).toString()); + System.out.println("JOINED : " + receivedPid+" at "+(new + Date()).toString()); log.info("JOINED - - - " + receivedPid); // Get the successor of newly joined node if((System.currentTimeMillis() - GroupMembership.startTime) > (GroupMembership.tFail * 1000)) { @@ -154,8 +154,8 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea boolean amISuccessor = amITheSuccesorOf(receivedMBean.hashValue); if (amISuccessor) { // If you are the successor,move keys accordingly. - System.out.println("hey I'm the succ of newly joined node:" - + receivedHost); + //System.out.println("hey I'm the succ of newly joined node:" + // + receivedHost); moveKeysSucc(receivedHost, mBean.hashValue); } else if (GroupMembership.membershipList.size() >= 3) { int amIInPredReReplicationSeg = GroupMembership @@ -164,9 +164,9 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea .get(GroupMembership.pid).hashValue, mBean.hashValue); if (amIInPredReReplicationSeg != -1) { - System.out.println("hey I'm the " - + amIInPredReReplicationSeg - + " pred of newly joined node:" + receivedHost); + //System.out.println("hey I'm the " + // + amIInPredReReplicationSeg + // + " pred of newly joined node:" + receivedHost); moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index 81e3871..24407b4 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -45,7 +45,7 @@ public void run() } //Remove entry which is marked toBeDeleted - if (membershipBean.toBeDeleted) + if (membershipBean.toBeDeleted && ((System.currentTimeMillis() - membershipBean.timeStamp) >= (2 * tFail * 1000))) { try { GroupMembership.handleCrash(membershipBean.hashValue); @@ -56,7 +56,7 @@ public void run() GroupMembership.membershipList.remove(entry.getKey()); } //If the membership list entry has timed-out then mark it toBeDeleted - else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000) + else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000 && !membershipBean.toBeDeleted) { membershipBean.toBeDeleted = true; if (membershipBean.hearbeatLastReceived > 0) { From 10e565862dceb1f283da546d06f72867ca42c344 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sat, 7 Dec 2013 23:57:36 -0600 Subject: [PATCH 40/48] cool application --- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 4 +- .../java/edu/uiuc/boltdb/BoltDBServer.java | 34 +++++++---- .../boltdb/examples/MovieSearchClient.java | 10 +++- .../groupmembership/GroupMembership.java | 57 +++++++------------ .../boltdb/groupmembership/MergeThread.java | 24 +++++++- .../RefreshMembershipListThread.java | 2 +- 6 files changed, 76 insertions(+), 55 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index a41aeb2..66860c6 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -20,7 +20,7 @@ public interface BoltDBProtocol extends Remote { * @param canBeForwarded * @throws RemoteException */ - public void insert(long key, String value, boolean canBeForwarded) throws RemoteException; + public Boolean insert(long key, String value, boolean canBeForwarded) throws RemoteException; /** * The lookup api is used to lookup the value associated with a key. @@ -49,7 +49,7 @@ public interface BoltDBProtocol extends Remote { * @param canBeForwarded * @throws RemoteException */ - public void delete(long key, boolean canBeForwarded) throws RemoteException; + public Boolean delete(long key, boolean canBeForwarded) throws RemoteException; public void lookupAndInsertInto(String hostname, long startKeyRange, long endKeyRange) throws RemoteException; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 4c42dd3..bda70d1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -10,11 +10,13 @@ import java.rmi.server.UnicastRemoteObject; import java.security.NoSuchAlgorithmException; import java.util.Collections; +import java.util.Date; import java.util.Map; import java.util.Map.Entry; import java.util.SortedMap; import java.util.TreeMap; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; import org.apache.log4j.Logger; @@ -44,7 +46,7 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - public static SortedMap KVStore = Collections.synchronizedSortedMap(new TreeMap()); + public static ConcurrentMap KVStore = new ConcurrentHashMap(); public static void main(String[] args) throws IOException { @@ -87,12 +89,13 @@ private String[] getTargetHosts(long key) throws NoSuchAlgorithmException { * @throws */ - public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { + public Boolean insert(long key, String value, boolean canBeForwarded) throws RemoteException { if(!canBeForwarded) { if(KVStore.containsKey(key)) - throw new RemoteException("Key already present."); + //throw new RemoteException("Key already present."); + return false; KVStore.put(key, value); - return; + return true; } try { @@ -103,14 +106,16 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote for (int i = 0; i < GroupMembership.replicationFactor; i++) { if (GroupMembership.membershipList.get(targetHosts[i]).hostname.equals(InetAddress.getLocalHost().getHostName())) { if (KVStore.containsKey(key)) - throw new RemoteException("Key already present."); + //throw new RemoteException("Key already present."); + return false; KVStore.put(key, value); } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming .lookup("rmi://" + GroupMembership.membershipList.get(targetHosts[i]).hostname + "/KVStore"); - targetServer.insert(key, value, false); + if(!targetServer.insert(key, value, false)) return false; } } + return true; } catch(RemoteException re) { throw re; } catch (Exception e) { @@ -195,12 +200,13 @@ public void update(long key, String value, boolean canBeForwarded) throws Remote * @param canBeForwarded * @throws RemoteException */ - public void delete(long key, boolean canBeForwarded) throws RemoteException { + public Boolean delete(long key, boolean canBeForwarded) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) - throw new RemoteException("Key not present."); + //throw new RemoteException("Key not present."); + return false; KVStore.remove(key); - return; + return true; } String targetHost = null; try { @@ -208,11 +214,13 @@ public void delete(long key, boolean canBeForwarded) throws RemoteException { targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { if(!KVStore.containsKey(key)) - throw new RemoteException("Key not present."); + //throw new RemoteException("Key not present."); + return false; KVStore.remove(key); + return true; } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - targetServer.delete(key, false); + return targetServer.delete(key, false); } } catch(RemoteException re) { throw re; @@ -239,12 +247,16 @@ public void lookupAndInsertInto(String hostname, long startKeyRange, if (hashOfKey >= startKeyRange && hashOfKey <= endKeyRange) { System.out.println("Inserting " + hashOfKey + " from " + GroupMembership.pid + " to " + hostname); + log.info("["+new Date()+"]Inserting " + hashOfKey + " from " + + GroupMembership.pid + " to " + hostname); targetServer.insert(e.getKey(), e.getValue(), false); } } else { if (hashOfKey >= startKeyRange || hashOfKey <= endKeyRange) { System.out.println("Inserting " + hashOfKey + " from " + GroupMembership.pid + " to " + hostname); + log.info("["+new Date()+"]Inserting " + hashOfKey + " from " + + GroupMembership.pid + " to " + hostname); targetServer.insert(e.getKey(), e.getValue(), false); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java index d6f19d9..83170ac 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieSearchClient.java @@ -4,10 +4,12 @@ import java.io.FileInputStream; import java.io.IOException; import java.io.InputStreamReader; +import java.math.BigInteger; import java.net.MalformedURLException; import java.rmi.Naming; import java.rmi.NotBoundException; import java.rmi.RemoteException; +import java.security.MessageDigest; import java.security.NoSuchAlgorithmException; import java.util.Properties; import java.util.StringTokenizer; @@ -78,7 +80,7 @@ private void searchMovie(String keyWordString) throws NoSuchAlgorithmException { try { StringTokenizer stk = new StringTokenizer(keyWordString); String keyWord = stk.nextToken(); - long key = GroupMembership.computeHash(keyWord); + long key = computeHash(keyWord); String result = (String)boltDBServer.lookup(key, true); @@ -99,4 +101,10 @@ private void searchMovie(String keyWordString) throws NoSuchAlgorithmException { System.out.println(re.getCause().getMessage()); } } + + public static long computeHash(String pid) throws NoSuchAlgorithmException { + MessageDigest md = MessageDigest.getInstance("MD5"); + BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); + return Math.abs(bigInt.longValue()) % 1000001L; + } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 5ca0155..53c055a 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -233,7 +233,7 @@ public void run() { * The show command prints the current membershipList entries and the current KVStore * entries on the console. */ - else if(commandString.equals("show")) { + else if(commandString.equals("shownodes")) { System.out.println("-------------------------------------------------"); System.out.println("Membership List : "); System.out.println("-------------------------------------------------"); @@ -243,30 +243,41 @@ else if(commandString.equals("show")) { } System.out.println("-------------------------------------------------"); System.out.println(); + } + else if(commandString.equals("showKV")) { System.out.println("-------------------------------------------------"); System.out.println("Key Value Store : "); System.out.println("-------------------------------------------------"); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; long myPredecessor = GroupMembership.membershipList.get(GroupMembership.getPredecessorNode(myHash)).hashValue; + int primaryCount=0,replicaCount=0; for (Map.Entry entry : BoltDBServer.KVStore.entrySet()) { long hashOfKey = computeHash((new Long(entry.getKey())).toString()); System.out.print(entry.getKey() + " ---> " + entry.getValue() + " | Hash of Key - " + hashOfKey + " "); if(myHash > myPredecessor) { - if(hashOfKey > myPredecessor && hashOfKey <= myHash) + if(hashOfKey > myPredecessor && hashOfKey <= myHash) { System.out.println("Primary"); - else + primaryCount++; + } + else { System.out.println("Replica"); + replicaCount++; + } } else { - if(hashOfKey > myPredecessor || hashOfKey <= myHash) + if(hashOfKey > myPredecessor || hashOfKey <= myHash) { System.out.println("Primary"); - else + primaryCount++; + } + else { System.out.println("Replica"); + replicaCount++; + } } - } System.out.println("-------------------------------------------------"); + System.out.println("Primary - " + primaryCount + " Replicas - " + replicaCount + " Total - " + (primaryCount+replicaCount)); System.out.println(); } else if(commandString.equals("ring")) { @@ -282,34 +293,6 @@ else if(commandString.equals("ring")) { System.out.println("-------------------------------------------------"); System.out.println(); } - else { - StringTokenizer stk = new StringTokenizer(commandString); - String checkCommand = stk.nextToken(); - if(checkCommand.equals("checksucc")) - { - long thisNode = Long.parseLong(stk.nextToken()); - long failedNode = Long.parseLong(stk.nextToken()); - System.out.println("inSuccReReplicationSeg output --> " + inSuccReReplicationSeg(thisNode, failedNode)); - } - else if(checkCommand.equals("checkpred")) - { - long thisNode = Long.parseLong(stk.nextToken()); - long failedNode = Long.parseLong(stk.nextToken()); - System.out.println("inPredReReplicationSeg output --> " + inPredReReplicationSeg(thisNode, failedNode)); - } - else if(checkCommand.equals("succ")) - { - long thisNode = Long.parseLong(stk.nextToken()); - int k = Integer.parseInt(stk.nextToken()); - System.out.println("Successor of " + thisNode + " --> " + computeHash(getKthSuccessorNode(thisNode, k))); - } - else if(checkCommand.equals("pred")) - { - long thisNode = Long.parseLong(stk.nextToken()); - int k = Integer.parseInt(stk.nextToken()); - System.out.println("Predecessor of " + thisNode + " --> " + computeHash(getKthPredecessorNode(thisNode, k))); - } - } } } catch (Exception e) { e.printStackTrace(); @@ -426,7 +409,7 @@ public synchronized static void handleCrash(long hashCrashedNode) long myhash = membershipList.get(GroupMembership.pid).hashValue; int successorPosition = inSuccReReplicationSeg(myhash,hashCrashedNode); if (successorPosition != -1) { - System.out.println("successor position:"+successorPosition); + //System.out.println("successor position:"+successorPosition); long startKey, endKey; String targetNode; if(successorPosition == 3) { @@ -440,12 +423,12 @@ public synchronized static void handleCrash(long hashCrashedNode) endKey = membershipList.get(targetNode).hashValue; } - System.out.println("startkey:"+startKey+ " endKey:"+endKey+" targetNode:"+targetNode); + //System.out.println("startkey:"+startKey+ " endKey:"+endKey+" targetNode:"+targetNode); BoltDBProtocol targetRMIServer = null; int i = 0; while (i++ < replicationFactor - 1) { try { - System.out.println("trying to connect to targetNode pid :"+targetNode+" with hostname :"+ membershipList.get(targetNode).hostname ); + //System.out.println("trying to connect to targetNode pid :"+targetNode+" with hostname :"+ membershipList.get(targetNode).hostname ); targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + membershipList.get(targetNode).hostname + "/KVStore"); targetRMIServer.lookupAndInsertInto(membershipList.get(pid).hostname, startKey, endKey); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index b085170..9046d3d 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -114,7 +114,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme //Also update current node's membership list if(receivedMBean.hearbeatLastReceived <= 0 && currentMBean.hearbeatLastReceived > 0) { System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); - log.info("VOLUNTARILY LEFT - - - " + receivedPid); + log.info("["+new Date()+"]VOLUNTARILY LEFT - - - " + receivedPid); currentMBean.hearbeatLastReceived = -1; currentMBean.timeStamp = System.currentTimeMillis(); currentMBean.toBeDeleted = false; @@ -129,6 +129,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme currentMBean.timeStamp = System.currentTimeMillis(); if(currentMBean.toBeDeleted) { System.out.println("JOINED : " + receivedPid); + log.info("["+new Date()+"]JOINED : " + receivedPid); currentMBean.toBeDeleted = false; } GroupMembership.membershipList.put(receivedPid, currentMBean); @@ -147,7 +148,7 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea System.out.println("JOINED : " + receivedPid+" at "+(new Date()).toString()); - log.info("JOINED - - - " + receivedPid); + log.info("["+new Date()+"]JOINED - - - " + receivedPid); // Get the successor of newly joined node if((System.currentTimeMillis() - GroupMembership.startTime) > (GroupMembership.tFail * 1000)) { @@ -225,11 +226,18 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma System.out.println("Inserting key :" + entry.getKey() + " value:" + entry.getValue() + " from Me to " + targetHost); + log.info("["+new Date()+"]Inserting key :" + entry.getKey() + + " value:" + entry.getValue() + " from Me to " + + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(), false); // BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor + if (GroupMembership.membershipList.size() >= 3) { + log.info("["+new Date()+"]Deleting key :" + + entry.getKey() + " from " + + succSuccessorHost); System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); @@ -245,6 +253,9 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma System.out.println("Inserting key :" + entry.getKey() + " value:" + entry.getValue() + " from Me to " + targetHost); + log.info("["+new Date()+"]Inserting key :" + entry.getKey() + + " value:" + entry.getValue() + " from Me to " + + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(), false); // BoltDBServer.KVStore.remove(entry.getKey()); @@ -253,6 +264,9 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); + log.info("["+new Date()+"]Deleting key :" + + entry.getKey() + " from " + + succSuccessorHost); succSuccRMIServer.delete(entry.getKey(), false); } } @@ -286,21 +300,25 @@ private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int prede if (myHash > myPredecessor) { if ( hashOfKey > myPredecessor && hashOfKey <= myHash) { System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); + log.info("["+new Date()+"]Inserting key :" + entry.getKey() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); + log.info("["+new Date()+"]Deleting key :" + entry.getKey() + " from " + kpthSuccHost); kpthSuccRMIServer.delete(entry.getKey(), false); } } else { if ( hashOfKey > myPredecessor || hashOfKey <= myHash) { System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); + log.info("["+new Date()+"]Inserting key :" + entry.getKey() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(),false); System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); + log.info("["+new Date()+"]Deleting key :" + entry.getKey() + " from " + kpthSuccHost); kpthSuccRMIServer.delete(entry.getKey(), false); } } } } -} +} \ No newline at end of file diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index 24407b4..c64724e 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -61,7 +61,7 @@ else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000 & membershipBean.toBeDeleted = true; if (membershipBean.hearbeatLastReceived > 0) { System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); - log.info("CRASHED - - - " + entry.getKey()); + log.info("["+new Date()+"]CRASHED - - - " + entry.getKey()); } } From 8c617ce9fae90641242f4ec718adfc5f673c3e59 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sat, 7 Dec 2013 23:58:41 -0600 Subject: [PATCH 41/48] indexer --- .../uiuc/boltdb/examples/MovieDBIndexer.java | 70 +++++++++++++++++++ 1 file changed, 70 insertions(+) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieDBIndexer.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieDBIndexer.java b/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieDBIndexer.java new file mode 100644 index 0000000..6ef4e04 --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/examples/MovieDBIndexer.java @@ -0,0 +1,70 @@ +package edu.uiuc.boltdb.examples; + +import java.io.BufferedReader; +import java.io.BufferedWriter; +import java.io.FileInputStream; +import java.io.FileReader; +import java.io.FileWriter; +import java.io.IOException; +import java.math.BigInteger; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.security.MessageDigest; +import java.security.NoSuchAlgorithmException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.Properties; +import java.util.StringTokenizer; +import java.util.Map.Entry; + +import edu.uiuc.boltdb.BoltDBProtocol; + +public class MovieDBIndexer { + + /** + * @param args + * @throws IOException + * @throws NoSuchAlgorithmException + * @throws NotBoundException + */ + public static void main(String[] args) throws IOException, NoSuchAlgorithmException, NotBoundException { + // TODO Auto-generated method stub + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.kvstore.server"); + String rawFile = prop.getProperty("boltdb.kvstore.examples.movies.toIndex"); + + if(System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + BoltDBProtocol boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); + + HashMap hmap = new HashMap(); + BufferedReader br = new BufferedReader(new FileReader(rawFile)); + String line; + while((line = br.readLine()) != null) { + line = line.trim(); + StringTokenizer stk = new StringTokenizer(line); + while(stk.hasMoreTokens()) { + long key = computeHash(stk.nextToken()); + String curValue = hmap.get(key); + String value = ((curValue == null)?"":curValue) + "," + line; + hmap.put(key, value); + } + } + Iterator> itr = hmap.entrySet().iterator(); + while(itr.hasNext()) { + Entry entry = itr.next(); + boltDBServer.insert(entry.getKey(), entry.getValue(), true); + System.out.println("Successfully inserted " + entry.getKey() + " --> " + entry.getValue()); + } + br.close(); + } + public static long computeHash(String pid) throws NoSuchAlgorithmException { + MessageDigest md = MessageDigest.getInstance("MD5"); + BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); + return Math.abs(bigInt.longValue()) % 1000001L; + } +} From d106229a58e632fb445d4bf72253c9351d8ad241 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 8 Dec 2013 00:30:52 -0600 Subject: [PATCH 42/48] consistency levels --- .../java/edu/uiuc/boltdb/BoltDBClient.java | 62 ++++-- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 13 +- .../java/edu/uiuc/boltdb/BoltDBServer.java | 183 ++++++++++++------ .../groupmembership/GroupMembership.java | 8 +- .../boltdb/groupmembership/MergeThread.java | 25 +-- 5 files changed, 195 insertions(+), 96 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index dc72a64..5253e92 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -70,11 +70,18 @@ private void runClientShell() throws IOException { } } + private BoltDBProtocol.CONSISTENCY_LEVEL getConsistency(String clevel) { + if(clevel.equals("ONE")) return BoltDBProtocol.CONSISTENCY_LEVEL.ONE; + else if (clevel.equals("QUORUM")) return BoltDBProtocol.CONSISTENCY_LEVEL.QUORUM; + else if (clevel.equals("ALL")) return BoltDBProtocol.CONSISTENCY_LEVEL.ALL; + + return null; + } // This method handles the commands entered by the user in the boltdb-client shell private void handleCommand(String commandString) { try { StringTokenizer stk = new StringTokenizer(commandString); - if(stk.countTokens() < 2) { + if(stk.countTokens() < 3) { printUsage(0); return; } @@ -83,6 +90,13 @@ private void handleCommand(String commandString) { String commandType = stk.nextToken(); if(commandType.equals("insert")) { + String clevel = stk.nextToken(); + if (!clevel.equals("ONE") && !clevel.equals("QUORUM") && !clevel.equals("ALL")) { + printUsage(1); + return; + } + BoltDBProtocol.CONSISTENCY_LEVEL consistencyLevel = getConsistency(clevel); + String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; @@ -97,8 +111,15 @@ private void handleCommand(String commandString) { } value = value.trim(); // Perform Insert Operation on the remote server object - boltDBServer.insert(key, value, true); + boltDBServer.insert(key, new ValueTimeStamp(value, 0), true,consistencyLevel); } else if(commandType.equals("update")) { + String clevel = stk.nextToken(); + if (!clevel.equals("ONE") && !clevel.equals("QUORUM") && !clevel.equals("ALL")) { + printUsage(2); + return; + } + BoltDBProtocol.CONSISTENCY_LEVEL consistencyLevel = getConsistency(clevel); + String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; @@ -113,20 +134,33 @@ private void handleCommand(String commandString) { } value = value.trim(); // Perform Update Operation on the remote server object - boltDBServer.update(key, value, true); + boltDBServer.update(key, new ValueTimeStamp(value, 0), true, consistencyLevel); } else if(commandType.equals("lookup")) { + String clevel = stk.nextToken(); + if (!clevel.equals("ONE") && !clevel.equals("QUORUM") && !clevel.equals("ALL")) { + printUsage(3); + return; + } + BoltDBProtocol.CONSISTENCY_LEVEL consistencyLevel = getConsistency(clevel); + String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; // Perform LookUp Operation on the remote server object - String value = (String)boltDBServer.lookup(key, true); - System.out.println("Look Up Result : " + value); + ValueTimeStamp value = boltDBServer.lookup(key, true, consistencyLevel); + System.out.println("Look Up Result : " + value.value); } else if(commandType.equals("delete")) { + String clevel = stk.nextToken(); + if (!clevel.equals("ONE") && !clevel.equals("QUORUM") && !clevel.equals("ALL")) { + printUsage(4); + return; + } + BoltDBProtocol.CONSISTENCY_LEVEL consistencyLevel = getConsistency(clevel); String keyStr = stk.nextToken(); long key = parseKey(keyStr); if(key == -1) return; // Perform Delete Operation on the remote server object - boltDBServer.delete(key, true); + boltDBServer.delete(key, true, consistencyLevel); System.out.println("Key Value Pair Deleted"); } else { printUsage(0); @@ -161,18 +195,18 @@ private void printUsage(int type) { System.out.println("Invalid Command"); System.out.println("Usage : "); switch(type) { - case 1: System.out.println("insert "); + case 1: System.out.println("insert "); break; - case 2: System.out.println("update "); + case 2: System.out.println("update "); break; - case 3: System.out.println("lookukp "); + case 3: System.out.println("lookukp "); break; - case 4: System.out.println("delete "); + case 4: System.out.println("delete "); break; - default:System.out.println("insert "); - System.out.println("update "); - System.out.println("lookup "); - System.out.println("delete "); + default:System.out.println("insert "); + System.out.println("update "); + System.out.println("lookup "); + System.out.println("delete "); break; } System.out.println(" is an integer value in the range 0 - 1000000"); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index a41aeb2..81e1260 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -20,7 +20,7 @@ public interface BoltDBProtocol extends Remote { * @param canBeForwarded * @throws RemoteException */ - public void insert(long key, String value, boolean canBeForwarded) throws RemoteException; + public Boolean insert(long key, ValueTimeStamp value, boolean canBeForwarded, CONSISTENCY_LEVEL consistencyLevel) throws RemoteException; /** * The lookup api is used to lookup the value associated with a key. @@ -30,7 +30,7 @@ public interface BoltDBProtocol extends Remote { * @return * @throws RemoteException */ - public String lookup(long key, boolean canBeForwarded) throws RemoteException; + public ValueTimeStamp lookup(long key, boolean canBeForwarded, CONSISTENCY_LEVEL consistencyLevel) throws RemoteException; /** * The update api updates the value of the provided key with the new value. @@ -40,7 +40,7 @@ public interface BoltDBProtocol extends Remote { * @param canBeForwarded * @throws RemoteException */ - public void update(long key, String value, boolean canBeForwarded) throws RemoteException; + public Boolean update(long key, ValueTimeStamp value, boolean canBeForwarded, CONSISTENCY_LEVEL consistencyLevel) throws RemoteException; /** * The delete api removes the key-value entry from the store. @@ -49,8 +49,11 @@ public interface BoltDBProtocol extends Remote { * @param canBeForwarded * @throws RemoteException */ - public void delete(long key, boolean canBeForwarded) throws RemoteException; + public Boolean delete(long key, boolean canBeForwarded, CONSISTENCY_LEVEL consistencyLevel) throws RemoteException; public void lookupAndInsertInto(String hostname, long startKeyRange, long endKeyRange) throws RemoteException; - + + public enum CONSISTENCY_LEVEL { + ONE, QUORUM, ALL + } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 4c42dd3..7736f67 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -15,10 +15,21 @@ import java.util.SortedMap; import java.util.TreeMap; import java.util.concurrent.ConcurrentHashMap; +import java.util.concurrent.ConcurrentMap; +import java.util.concurrent.ExecutionException; +import java.util.concurrent.ExecutorCompletionService; +import java.util.concurrent.ExecutorService; +import java.util.concurrent.Executors; +import java.util.concurrent.Future; import org.apache.log4j.Logger; +import edu.uiuc.boltdb.BoltDBProtocol.CONSISTENCY_LEVEL; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.methods.DeleteThread; +import edu.uiuc.boltdb.methods.InsertThread; +import edu.uiuc.boltdb.methods.LookupThread; +import edu.uiuc.boltdb.methods.UpdateThread; /** * This class represents the server component of the distributed key value store. It implements the @@ -44,7 +55,7 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ - public static SortedMap KVStore = Collections.synchronizedSortedMap(new TreeMap()); + public static ConcurrentMap KVStore = new ConcurrentHashMap(); public static void main(String[] args) throws IOException { @@ -75,6 +86,57 @@ private String[] getTargetHosts(long key) throws NoSuchAlgorithmException { } return targetHosts; } + + private int convertConsistencyLevelToInt(CONSISTENCY_LEVEL consistencyLevel) { + switch(consistencyLevel) { + case ALL: + return GroupMembership.replicationFactor; + case ONE: + return 1; + case QUORUM: + return GroupMembership.replicationFactor/2 + 1; + default: + break; + + } + return -1; + } + + private boolean waitForReplicaReplies(ExecutorCompletionService completionService, CONSISTENCY_LEVEL consistencyLevel) throws InterruptedException, ExecutionException { + int replicaRepliesToWaitFor = convertConsistencyLevelToInt(consistencyLevel); + + for(int i = 0; i < GroupMembership.replicationFactor; i++) { + final Future future = completionService.take(); + if(future.get() == true) { + replicaRepliesToWaitFor--; + if (replicaRepliesToWaitFor == 0) { + return true; + } + } + } + return false; + } + + private ValueTimeStamp waitForReplicaRepliesForUpdate(ExecutorCompletionService completionService, CONSISTENCY_LEVEL consistencyLevel) throws InterruptedException, ExecutionException { + int replicaRepliesToWaitFor = convertConsistencyLevelToInt(consistencyLevel); + ValueTimeStamp result = null; + ValueTimeStamp temp; + for(int i = 0; i < GroupMembership.replicationFactor; i++) { + final Future future = completionService.take(); + if((temp = future.get()) != null) { + if (result == null) result = temp; + else { + if(result.timeStamp < temp.timeStamp) + result = temp; + } + replicaRepliesToWaitFor--; + if (replicaRepliesToWaitFor == 0) { + return result; + } + } + } + return null; + } /** * The insert api is used to insert a key and a value into the store. *'canBeForwarded' is a flag to indicate whether the request can be forwarded to @@ -87,32 +149,30 @@ private String[] getTargetHosts(long key) throws NoSuchAlgorithmException { * @throws */ - public void insert(long key, String value, boolean canBeForwarded) throws RemoteException { + public Boolean insert(long key, ValueTimeStamp value, boolean canBeForwarded,CONSISTENCY_LEVEL consistencyLevel) throws RemoteException { if(!canBeForwarded) { if(KVStore.containsKey(key)) throw new RemoteException("Key already present."); KVStore.put(key, value); - return; + return true; } + value.timeStamp = System.currentTimeMillis(); try { // Determine the target host using the getSuccessorNodeOf method String[] targetHosts = getTargetHosts(key); - - for (int i = 0; i < GroupMembership.replicationFactor; i++) { - if (GroupMembership.membershipList.get(targetHosts[i]).hostname.equals(InetAddress.getLocalHost().getHostName())) { - if (KVStore.containsKey(key)) - throw new RemoteException("Key already present."); - KVStore.put(key, value); - } else { - BoltDBProtocol targetServer = (BoltDBProtocol) Naming - .lookup("rmi://" + GroupMembership.membershipList.get(targetHosts[i]).hostname + "/KVStore"); - targetServer.insert(key, value, false); - } + + final ExecutorService pool = Executors.newFixedThreadPool(GroupMembership.replicationFactor); + final ExecutorCompletionService completionService = new ExecutorCompletionService(pool); + + for(int i = 0; i < GroupMembership.replicationFactor; i++) { + completionService.submit(new InsertThread(targetHosts[i],key,value,consistencyLevel)); } - } catch(RemoteException re) { - throw re; + boolean result = waitForReplicaReplies(completionService, consistencyLevel); + pool.shutdown(); + return result; + } catch (Exception e) { log.error("ERROR" , e); throw new RemoteException("Error occured at Server"); @@ -127,26 +187,26 @@ public void insert(long key, String value, boolean canBeForwarded) throws Remote * @return * @throws RemoteException */ - public String lookup(long key, boolean canBeForwarded) throws RemoteException { + public ValueTimeStamp lookup(long key, boolean canBeForwarded, CONSISTENCY_LEVEL consistencyLevel) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); return KVStore.get(key); } - String targetHost = null; + try { - // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; - if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { - if(!KVStore.containsKey(key)) - throw new RemoteException("Key not present."); - return KVStore.get(key); - } else { - BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - return targetServer.lookup(key, false); + String[] targetHosts = getTargetHosts(key); + + final ExecutorService pool = Executors.newFixedThreadPool(GroupMembership.replicationFactor); + final ExecutorCompletionService completionService = new ExecutorCompletionService(pool); + + for(int i = 0; i < GroupMembership.replicationFactor; i++) { + completionService.submit(new LookupThread(targetHosts[i],key,consistencyLevel)); } - } catch(RemoteException re) { - throw re; + + ValueTimeStamp result = waitForReplicaRepliesForUpdate(completionService, consistencyLevel); + pool.shutdown(); + return result; } catch (Exception e) { log.error("ERROR" , e); throw new RemoteException("Error occured at Server"); @@ -161,27 +221,28 @@ public String lookup(long key, boolean canBeForwarded) throws RemoteException { * @param canBeForwarded * @throws RemoteException */ - public void update(long key, String value, boolean canBeForwarded) throws RemoteException { + public Boolean update(long key, ValueTimeStamp value, boolean canBeForwarded, CONSISTENCY_LEVEL consistencyLevel) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); - KVStore.put(key, value); - return; + if(KVStore.get(key).timeStamp < value.timeStamp) + KVStore.put(key, value); + return true; } - String targetHost = null; + value.timeStamp = System.currentTimeMillis(); try { - // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; - if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { - if(!KVStore.containsKey(key)) - throw new RemoteException("Key not present."); - KVStore.put(key, value); - } else { - BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - targetServer.update(key, value, false); + String[] targetHosts = getTargetHosts(key); + + final ExecutorService pool = Executors.newFixedThreadPool(GroupMembership.replicationFactor); + final ExecutorCompletionService completionService = new ExecutorCompletionService(pool); + + for(int i = 0; i < GroupMembership.replicationFactor; i++) { + completionService.submit(new UpdateThread(targetHosts[i],key,value,consistencyLevel)); } - } catch(RemoteException re) { - throw re; + + boolean result = waitForReplicaReplies(completionService, consistencyLevel); + pool.shutdown(); + return result; } catch (Exception e) { log.error("ERROR" , e); throw new RemoteException("Error occured at Server"); @@ -195,27 +256,27 @@ public void update(long key, String value, boolean canBeForwarded) throws Remote * @param canBeForwarded * @throws RemoteException */ - public void delete(long key, boolean canBeForwarded) throws RemoteException { + public Boolean delete(long key, boolean canBeForwarded,CONSISTENCY_LEVEL consistencyLevel) throws RemoteException { if(!canBeForwarded) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); KVStore.remove(key); - return; + return true; } - String targetHost = null; + try { - // Determine the target host using the getSuccessorNodeOf method - targetHost = GroupMembership.membershipList.get(GroupMembership.getSuccessorNode(GroupMembership.computeHash((new Long(key).toString())))).hostname; - if(targetHost.equals(InetAddress.getLocalHost().getHostName())) { - if(!KVStore.containsKey(key)) - throw new RemoteException("Key not present."); - KVStore.remove(key); - } else { - BoltDBProtocol targetServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - targetServer.delete(key, false); + String[] targetHosts = getTargetHosts(key); + + final ExecutorService pool = Executors.newFixedThreadPool(GroupMembership.replicationFactor); + final ExecutorCompletionService completionService = new ExecutorCompletionService(pool); + + for(int i = 0; i < GroupMembership.replicationFactor; i++) { + completionService.submit(new DeleteThread(targetHosts[i],key,consistencyLevel)); } - } catch(RemoteException re) { - throw re; + + boolean result = waitForReplicaReplies(completionService, consistencyLevel); + pool.shutdown(); + return result; } catch (Exception e) { log.error("ERROR" , e); throw new RemoteException("Error occured at Server"); @@ -231,7 +292,7 @@ public void lookupAndInsertInto(String hostname, long startKeyRange, log.error(e.getMessage()); } System.out.println("lookupAndInsert: start - "+startKeyRange+" end - "+ endKeyRange); - for(Entry e : KVStore.entrySet()) { + for(Entry e : KVStore.entrySet()) { try { long hashOfKey = GroupMembership.computeHash(e.getKey().toString()); System.out.println("lookupAndInsert: hashOfkey - "+hashOfKey); @@ -239,13 +300,13 @@ public void lookupAndInsertInto(String hostname, long startKeyRange, if (hashOfKey >= startKeyRange && hashOfKey <= endKeyRange) { System.out.println("Inserting " + hashOfKey + " from " + GroupMembership.pid + " to " + hostname); - targetServer.insert(e.getKey(), e.getValue(), false); + targetServer.insert(e.getKey(), e.getValue(), false,null); } } else { if (hashOfKey >= startKeyRange || hashOfKey <= endKeyRange) { System.out.println("Inserting " + hashOfKey + " from " + GroupMembership.pid + " to " + hostname); - targetServer.insert(e.getKey(), e.getValue(), false); + targetServer.insert(e.getKey(), e.getValue(), false,null); } } } catch (NoSuchAlgorithmException e1) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index a9ef039..ce5f1b9 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -212,11 +212,11 @@ public void run() { long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; String successorHost = GroupMembership.membershipList.get(getSuccessorNode(myHash)).hostname; BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successorHost + "/KVStore"); - Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); + Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { - Entry entry = itr.next(); - successorRMIServer.insert(entry.getKey(), entry.getValue(), false); + Entry entry = itr.next(); + successorRMIServer.insert(entry.getKey(), entry.getValue(), false,null); } BoltDBServer.KVStore.clear(); @@ -248,7 +248,7 @@ else if(commandString.equals("show")) { System.out.println("-------------------------------------------------"); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; long myPredecessor = GroupMembership.membershipList.get(GroupMembership.getPredecessorNode(myHash)).hashValue; - for (Map.Entry entry : BoltDBServer.KVStore.entrySet()) + for (Map.Entry entry : BoltDBServer.KVStore.entrySet()) { long hashOfKey = computeHash((new Long(entry.getKey())).toString()); System.out.print(entry.getKey() + " ---> " + entry.getValue() + " | Hash of Key - " + hashOfKey + " "); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index c51f3bb..8b8504d 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -24,6 +24,7 @@ import edu.uiuc.boltdb.BoltDBProtocol; import edu.uiuc.boltdb.BoltDBServer; +import edu.uiuc.boltdb.ValueTimeStamp; import edu.uiuc.boltdb.groupmembership.beans.MembershipBean; import edu.uiuc.boltdb.groupmembership.beans.UDPBean; @@ -201,7 +202,7 @@ private boolean amITheSuccesorOf(long hashOfNewlyJoinedNode) throws UnknownHostE private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws MalformedURLException, RemoteException, NotBoundException, NoSuchAlgorithmException { //get the rmiserver handle from the rmi registry BoltDBProtocol targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + targetHost + "/KVStore"); - Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); + Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; // Get the rmiserver handle for successor's successor from the rmi registry @@ -212,7 +213,7 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma predecessorHash = GroupMembership.membershipList.get(GroupMembership.getKthPredecessorNode(myHash, 1)).hashValue; while(itr.hasNext()) { - Entry entry = itr.next(); + Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); if (predecessorHash == myHash || amIPrimaryReplicaFor(hashOfKey, myHash, predecessorHash)) { @@ -226,14 +227,14 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma + " value:" + entry.getValue() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), - entry.getValue(), false); + entry.getValue(), false, null); // BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor if (GroupMembership.membershipList.size() >= 3) { System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); - succSuccRMIServer.delete(entry.getKey(), false); + succSuccRMIServer.delete(entry.getKey(), false, null); } } } @@ -246,14 +247,14 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma + " value:" + entry.getValue() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), - entry.getValue(), false); + entry.getValue(), false,null); // BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor if (GroupMembership.membershipList.size() >= 3) { System.out.println("Deleting key :" + entry.getKey() + " from " + succSuccessorHost); - succSuccRMIServer.delete(entry.getKey(), false); + succSuccRMIServer.delete(entry.getKey(), false, null); } } } @@ -279,26 +280,26 @@ private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int prede BoltDBProtocol kpthSuccRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + kpthSuccHost + "/KVStore"); long myPredecessor = GroupMembership.membershipList.get(GroupMembership.getPredecessorNode(myHash)).hashValue; - Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); + Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); while(itr.hasNext()) { - Entry entry = itr.next(); + Entry entry = itr.next(); long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); if (myHash > myPredecessor) { if ( hashOfKey > myPredecessor && hashOfKey <= myHash) { System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + targetRMIServer.insert(entry.getKey(), entry.getValue(),false, null); System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); - kpthSuccRMIServer.delete(entry.getKey(), false); + kpthSuccRMIServer.delete(entry.getKey(), false, null); } } else { if ( hashOfKey > myPredecessor || hashOfKey <= myHash) { System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); - targetRMIServer.insert(entry.getKey(), entry.getValue(),false); + targetRMIServer.insert(entry.getKey(), entry.getValue(),false, null); System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); - kpthSuccRMIServer.delete(entry.getKey(), false); + kpthSuccRMIServer.delete(entry.getKey(), false, null); } } } From 9db471388f6f709cd26a2da9c81a40e22c1912bc Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 8 Dec 2013 01:18:12 -0600 Subject: [PATCH 43/48] nits --- .../main/java/edu/uiuc/boltdb/BoltDBClient.java | 16 ++++++++++++---- .../java/edu/uiuc/boltdb/ValueTimeStamp.java | 4 ++++ .../edu/uiuc/boltdb/methods/LookupThread.java | 5 +++-- .../edu/uiuc/boltdb/methods/UpdateThread.java | 12 +++++++----- 4 files changed, 26 insertions(+), 11 deletions(-) diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java index 5253e92..dd212d8 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBClient.java @@ -111,7 +111,8 @@ private void handleCommand(String commandString) { } value = value.trim(); // Perform Insert Operation on the remote server object - boltDBServer.insert(key, new ValueTimeStamp(value, 0), true,consistencyLevel); + if(!boltDBServer.insert(key, new ValueTimeStamp(value, 0), true,consistencyLevel)) + System.out.println("Key already present"); } else if(commandType.equals("update")) { String clevel = stk.nextToken(); if (!clevel.equals("ONE") && !clevel.equals("QUORUM") && !clevel.equals("ALL")) { @@ -134,7 +135,8 @@ private void handleCommand(String commandString) { } value = value.trim(); // Perform Update Operation on the remote server object - boltDBServer.update(key, new ValueTimeStamp(value, 0), true, consistencyLevel); + if(!boltDBServer.update(key, new ValueTimeStamp(value, 0), true, consistencyLevel)) + System.out.println("Key not present"); } else if(commandType.equals("lookup")) { String clevel = stk.nextToken(); if (!clevel.equals("ONE") && !clevel.equals("QUORUM") && !clevel.equals("ALL")) { @@ -148,6 +150,10 @@ private void handleCommand(String commandString) { if(key == -1) return; // Perform LookUp Operation on the remote server object ValueTimeStamp value = boltDBServer.lookup(key, true, consistencyLevel); + if(value == null) { + System.out.println("Key not present"); + return; + } System.out.println("Look Up Result : " + value.value); } else if(commandType.equals("delete")) { String clevel = stk.nextToken(); @@ -160,8 +166,10 @@ private void handleCommand(String commandString) { long key = parseKey(keyStr); if(key == -1) return; // Perform Delete Operation on the remote server object - boltDBServer.delete(key, true, consistencyLevel); - System.out.println("Key Value Pair Deleted"); + if(boltDBServer.delete(key, true, consistencyLevel)) + System.out.println("Key Value Pair Deleted"); + else + System.out.println("Delete Failed"); } else { printUsage(0); return; diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/ValueTimeStamp.java b/boltdb/src/main/java/edu/uiuc/boltdb/ValueTimeStamp.java index 0b5ff1c..fdff545 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/ValueTimeStamp.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/ValueTimeStamp.java @@ -17,4 +17,8 @@ public ValueTimeStamp(String value, long timeStamp) { this.timeStamp = timeStamp; } + @Override + public String toString() { + return new String("[" + value + " " +timeStamp+ "]"); + } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java index 349200b..4991381 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java @@ -29,7 +29,8 @@ public ValueTimeStamp call() { if (GroupMembership.membershipList.get(targetHost).hostname .equals(InetAddress.getLocalHost().getHostName())) { if(!BoltDBServer.KVStore.containsKey(key)) - throw new RemoteException("Key not present."); + return null; + //throw new RemoteException("Key not present."); return BoltDBServer.KVStore.get(key); } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming @@ -39,7 +40,7 @@ public ValueTimeStamp call() { return targetServer.lookup(key, false, consistencyLevel); } } catch (Exception e) { - System.out.println("Exception in insert thread"); + System.out.println("Exception in lookup thread"); return null; } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java index 5370bdb..e13243c 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java @@ -31,19 +31,21 @@ public Boolean call() { try { if (GroupMembership.membershipList.get(targetHost).hostname.equals(InetAddress.getLocalHost().getHostName())) { if(!BoltDBServer.KVStore.containsKey(key)) - throw new RemoteException("Key not present."); - if(BoltDBServer.KVStore.get(key).timeStamp < value.timeStamp) + return false; + //throw new RemoteException("Key not present."); + + if(BoltDBServer.KVStore.get(key).timeStamp < value.timeStamp) BoltDBServer.KVStore.put(key, value); + return true; } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming .lookup("rmi://" + GroupMembership.membershipList.get(targetHost).hostname + "/KVStore"); - targetServer.update(key, value, false, consistencyLevel); + return targetServer.update(key, value, false, consistencyLevel); } } catch(Exception e) { - System.out.println("Exception in insert thread"); + System.out.println("Exception in update thread"); return false; } - return new Boolean(true); } } From 5589e9143233851a71975fc70e153391f743df35 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 8 Dec 2013 15:19:52 -0600 Subject: [PATCH 44/48] performance --- .../tests/BoltDBPerformanceTest.java | 95 +++++++++++++++++++ 1 file changed, 95 insertions(+) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java b/boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java new file mode 100644 index 0000000..554143e --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java @@ -0,0 +1,95 @@ +package edu.uiuc.boltdb.logquerier.tests; + +import java.io.BufferedReader; +import java.io.FileInputStream; +import java.io.FileReader; +import java.io.IOException; +import java.math.BigInteger; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.security.MessageDigest; +import java.security.NoSuchAlgorithmException; +import java.util.HashMap; +import java.util.Iterator; +import java.util.Properties; +import java.util.StringTokenizer; +import java.util.Map.Entry; + +import edu.uiuc.boltdb.BoltDBProtocol; + +public class BoltDBPerformanceTest { + + /** + * @param args + * @throws IOException + * @throws NoSuchAlgorithmException + * @throws NotBoundException + */ + public static void main(String[] args) throws IOException, NoSuchAlgorithmException, NotBoundException { + // TODO Auto-generated method stub + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.kvstore.server"); + String rawFile = prop.getProperty("boltdb.kvstore.examples.movies.toIndex"); + + if(System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + BoltDBProtocol boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); + + HashMap hmap = new HashMap(); + BufferedReader br = new BufferedReader(new FileReader(rawFile)); + String line; + int count = 0; + while((line = br.readLine()) != null && count < 1000) { + line = line.trim(); + StringTokenizer stk = new StringTokenizer(line); + while(stk.hasMoreTokens() && count < 1000) { + long key = computeHash(stk.nextToken()); + String curValue = hmap.get(key); + if(curValue != null) + continue; + String value = line; + hmap.put(key, value); + count++; + } + } + Iterator> itr = hmap.entrySet().iterator(); + while(itr.hasNext()) { + Entry entry = itr.next(); + boltDBServer.insert(entry.getKey(), entry.getValue(), true); + //System.out.println("Successfully inserted " + entry.getKey() + " --> " + entry.getValue()); + } + + int updateCount = 0; + itr = hmap.entrySet().iterator(); + while(itr.hasNext() && updateCount++ < 100) { + Entry entry = itr.next(); + long startTime = System.currentTimeMillis(); + boltDBServer.update(entry.getKey(), "Some value", true); + long endTime = System.currentTimeMillis(); + System.out.println(endTime-startTime); + } + + System.out.println("------------------------------------------------------------"); + + int deleteCount = 0; + itr = hmap.entrySet().iterator(); + while(itr.hasNext() && deleteCount++ < 100) { + Entry entry = itr.next(); + long startTime = System.currentTimeMillis(); + boltDBServer.delete(entry.getKey(), true); + long endTime = System.currentTimeMillis(); + System.out.println(endTime-startTime); + } + + br.close(); + } + public static long computeHash(String pid) throws NoSuchAlgorithmException { + MessageDigest md = MessageDigest.getInstance("MD5"); + BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); + return Math.abs(bigInt.longValue()) % 1000001L; + } + } From 98e3553e374f5b6d942c2887ef502ebb039370d1 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 8 Dec 2013 17:52:31 -0600 Subject: [PATCH 45/48] most recent read/write --- boltdb/pom.xml | 5 +++ .../java/edu/uiuc/boltdb/BoltDBServer.java | 23 ++++++---- .../groupmembership/GroupMembership.java | 17 +++++++- .../groupmembership/beans/Operation.java | 43 +++++++++++++++++++ .../edu/uiuc/boltdb/methods/DeleteThread.java | 4 ++ .../edu/uiuc/boltdb/methods/InsertThread.java | 4 ++ .../edu/uiuc/boltdb/methods/LookupThread.java | 6 ++- .../edu/uiuc/boltdb/methods/UpdateThread.java | 4 ++ 8 files changed, 94 insertions(+), 12 deletions(-) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/Operation.java diff --git a/boltdb/pom.xml b/boltdb/pom.xml index 6116ab8..e662bdb 100644 --- a/boltdb/pom.xml +++ b/boltdb/pom.xml @@ -62,6 +62,11 @@ log4j log4j 1.2.17 + + + commons-collections + commons-collections + 3.0 diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index b7e5883..8d66460 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -1,20 +1,13 @@ package edu.uiuc.boltdb; import java.io.IOException; -import java.net.InetAddress; -import java.net.MalformedURLException; import java.rmi.Naming; -import java.rmi.NotBoundException; import java.rmi.RemoteException; import java.rmi.registry.LocateRegistry; import java.rmi.server.UnicastRemoteObject; import java.security.NoSuchAlgorithmException; -import java.util.Collections; import java.util.Date; -import java.util.Map; import java.util.Map.Entry; -import java.util.SortedMap; -import java.util.TreeMap; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.ConcurrentMap; import java.util.concurrent.ExecutionException; @@ -23,10 +16,11 @@ import java.util.concurrent.Executors; import java.util.concurrent.Future; +import org.apache.commons.collections.buffer.CircularFifoBuffer; import org.apache.log4j.Logger; -import edu.uiuc.boltdb.BoltDBProtocol.CONSISTENCY_LEVEL; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.groupmembership.beans.Operation; import edu.uiuc.boltdb.methods.DeleteThread; import edu.uiuc.boltdb.methods.InsertThread; import edu.uiuc.boltdb.methods.LookupThread; @@ -49,6 +43,9 @@ public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol private static final long serialVersionUID = 5195393553928167809L; private static org.apache.log4j.Logger log = Logger.getRootLogger(); + public static CircularFifoBuffer readBuffer = new CircularFifoBuffer(10); + public static CircularFifoBuffer writeBuffer = new CircularFifoBuffer(10); + protected BoltDBServer() throws RemoteException { super(); } @@ -155,6 +152,8 @@ public Boolean insert(long key, ValueTimeStamp value, boolean canBeForwarded,CON //throw new RemoteException("Key already present."); return false; KVStore.put(key, value); + if(consistencyLevel != null) + writeBuffer.add(new Operation("INSERT", consistencyLevel, new Date().toString(), key, value.value)); return true; } @@ -191,7 +190,9 @@ public ValueTimeStamp lookup(long key, boolean canBeForwarded, CONSISTENCY_LEVEL if(!canBeForwarded) { if(!KVStore.containsKey(key)) throw new RemoteException("Key not present."); - return KVStore.get(key); + ValueTimeStamp value = KVStore.get(key); + readBuffer.add(new Operation("READ", consistencyLevel, new Date().toString(), key, value.value)); + return value; } try { @@ -227,6 +228,8 @@ public Boolean update(long key, ValueTimeStamp value, boolean canBeForwarded, CO throw new RemoteException("Key not present."); if(KVStore.get(key).timeStamp < value.timeStamp) KVStore.put(key, value); + if(consistencyLevel != null) + writeBuffer.add(new Operation("UPDATE", consistencyLevel, new Date().toString(), key, value.value)); return true; } value.timeStamp = System.currentTimeMillis(); @@ -262,6 +265,8 @@ public Boolean delete(long key, boolean canBeForwarded,CONSISTENCY_LEVEL consist //throw new RemoteException("Key not present."); return false; KVStore.remove(key); + if(consistencyLevel != null) + writeBuffer.add(new Operation("DELETE", consistencyLevel, new Date().toString(), key)); return true; } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index b109abb..73f3619 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -209,7 +209,7 @@ public void run() { scheduler.shutdownNow(); scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); //Move your keys to successor - long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; + /*long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; String successorHost = GroupMembership.membershipList.get(getSuccessorNode(myHash)).hostname; BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successorHost + "/KVStore"); Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); @@ -219,7 +219,7 @@ public void run() { successorRMIServer.insert(entry.getKey(), entry.getValue(), false,null); } BoltDBServer.KVStore.clear(); - + */ MembershipBean mBean = membershipList.get(pid); mBean.hearbeatLastReceived = -1; mBean.timeStamp = System.currentTimeMillis(); @@ -292,6 +292,19 @@ else if(commandString.equals("ring")) { System.out.println("looparound"); System.out.println("-------------------------------------------------"); System.out.println(); + } else if(commandString.equals("show")) { + System.out.println("-------------------------------------------------"); + System.out.println("RECENT READS"); + Iterator itr = BoltDBServer.readBuffer.iterator(); + while(itr.hasNext()) { + System.out.println((Operation)itr.next()); + } + System.out.println("-------------------------------------------------"); + System.out.println("RECENT WRITES"); + itr = BoltDBServer.writeBuffer.iterator(); + while(itr.hasNext()) { + System.out.println((Operation)itr.next()); + } } } } catch (Exception e) { diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/Operation.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/Operation.java new file mode 100644 index 0000000..396c682 --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/beans/Operation.java @@ -0,0 +1,43 @@ +package edu.uiuc.boltdb.groupmembership.beans; + +import edu.uiuc.boltdb.BoltDBProtocol; +import edu.uiuc.boltdb.BoltDBProtocol.CONSISTENCY_LEVEL; + +public class Operation { + + String operation; + BoltDBProtocol.CONSISTENCY_LEVEL consistency; + String time; + long key; + String value; + + public Operation(String operation, BoltDBProtocol.CONSISTENCY_LEVEL consistency, String time, + long key, String value) { + super(); + this.operation = operation; + this.consistency = consistency; + this.time = time; + this.key = key; + this.value = value; + } + + + public Operation(String operation, CONSISTENCY_LEVEL consistency, + String time, long key) { + super(); + this.operation = operation; + this.consistency = consistency; + this.time = time; + this.key = key; + } + + + @Override + public String toString() { + if (operation.equals("DELETE")) { + return "[OPERATION: "+operation+" CONSISTENCY: "+consistency+" TIME: "+time+" KEY: "+key+"]"; + } + return "[OPERATION: "+operation+" CONSISTENCY: "+consistency+" TIME: "+time+" KEY: "+key+" VALUE: "+value+"]"; + } + +} diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java index 14c83c9..983234e 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java @@ -3,12 +3,14 @@ import java.net.InetAddress; import java.rmi.Naming; import java.rmi.RemoteException; +import java.util.Date; import java.util.concurrent.Callable; import edu.uiuc.boltdb.BoltDBProtocol; import edu.uiuc.boltdb.BoltDBServer; import edu.uiuc.boltdb.BoltDBProtocol.CONSISTENCY_LEVEL; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.groupmembership.beans.Operation; public class DeleteThread implements Callable { private String targetHost; @@ -30,6 +32,8 @@ public Boolean call() { return false; //throw new RemoteException("Key not present."); BoltDBServer.KVStore.remove(key); + if(consistencyLevel != null) + BoltDBServer.writeBuffer.add(new Operation("DELETE", consistencyLevel, new Date().toString(), key)); return true; } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/InsertThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/InsertThread.java index 1339eaf..b0dab21 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/InsertThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/InsertThread.java @@ -3,6 +3,7 @@ import java.net.InetAddress; import java.rmi.Naming; import java.rmi.RemoteException; +import java.util.Date; import java.util.concurrent.Callable; import edu.uiuc.boltdb.BoltDBProtocol; @@ -10,6 +11,7 @@ import edu.uiuc.boltdb.BoltDBServer; import edu.uiuc.boltdb.ValueTimeStamp; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.groupmembership.beans.Operation; public class InsertThread implements Callable { private String targetHost; @@ -34,6 +36,8 @@ public Boolean call() { return false; //throw new RemoteException("Key already present."); BoltDBServer.KVStore.put(key, value); + if(consistencyLevel != null) + BoltDBServer.writeBuffer.add(new Operation("INSERT", consistencyLevel, new Date().toString(), key, value.value)); return true; } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java index 4991381..f4b1beb 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/LookupThread.java @@ -3,6 +3,7 @@ import java.net.InetAddress; import java.rmi.Naming; import java.rmi.RemoteException; +import java.util.Date; import java.util.concurrent.Callable; import edu.uiuc.boltdb.BoltDBProtocol; @@ -10,6 +11,7 @@ import edu.uiuc.boltdb.BoltDBProtocol.CONSISTENCY_LEVEL; import edu.uiuc.boltdb.ValueTimeStamp; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.groupmembership.beans.Operation; public class LookupThread implements Callable { private String targetHost; @@ -31,7 +33,9 @@ public ValueTimeStamp call() { if(!BoltDBServer.KVStore.containsKey(key)) return null; //throw new RemoteException("Key not present."); - return BoltDBServer.KVStore.get(key); + ValueTimeStamp value = BoltDBServer.KVStore.get(key); + BoltDBServer.readBuffer.add(new Operation("READ", consistencyLevel, new Date().toString(), key, value.value)); + return value; } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming .lookup("rmi://" diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java index e13243c..63f3160 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/UpdateThread.java @@ -3,12 +3,14 @@ import java.net.InetAddress; import java.rmi.Naming; import java.rmi.RemoteException; +import java.util.Date; import java.util.concurrent.Callable; import edu.uiuc.boltdb.BoltDBProtocol; import edu.uiuc.boltdb.BoltDBServer; import edu.uiuc.boltdb.BoltDBProtocol.CONSISTENCY_LEVEL; import edu.uiuc.boltdb.groupmembership.GroupMembership; +import edu.uiuc.boltdb.groupmembership.beans.Operation; import edu.uiuc.boltdb.ValueTimeStamp; public class UpdateThread implements Callable { @@ -36,6 +38,8 @@ public Boolean call() { if(BoltDBServer.KVStore.get(key).timeStamp < value.timeStamp) BoltDBServer.KVStore.put(key, value); + if(consistencyLevel != null) + BoltDBServer.writeBuffer.add(new Operation("UPDATE", consistencyLevel, new Date().toString(), key, value.value)); return true; } else { BoltDBProtocol targetServer = (BoltDBProtocol) Naming From ee95578484af095bc3afb245d28adaea7889d897 Mon Sep 17 00:00:00 2001 From: "Y.CORP.YAHOO.COM\\ashanka" Date: Sun, 8 Dec 2013 21:52:05 -0600 Subject: [PATCH 46/48] code cleanup and comments --- .../java/edu/uiuc/boltdb/BoltDBProtocol.java | 2 +- .../java/edu/uiuc/boltdb/BoltDBServer.java | 40 ++- .../edu/uiuc/boltdb/examples/StaleClient.java | 111 +++++++ .../groupmembership/GroupMembership.java | 295 +++++++++--------- .../boltdb/groupmembership/MergeThread.java | 32 +- .../RefreshMembershipListThread.java | 2 +- .../edu/uiuc/boltdb/methods/DeleteThread.java | 1 - 7 files changed, 294 insertions(+), 189 deletions(-) create mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/examples/StaleClient.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java index 1ffb97f..5d72676 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBProtocol.java @@ -14,7 +14,7 @@ public interface BoltDBProtocol extends Remote { * The insert api is used to insert a key and a value into the store. *'canBeForwarded' is a flag to indicate whether the request can be forwarded to *other servers to perform the operation. - *Throws an exception if key is already present in the store. + *Returns false if key is already present in the store. * @param key * @param value * @param canBeForwarded diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java index 8d66460..168a0b0 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/BoltDBServer.java @@ -31,11 +31,10 @@ * BoltDBProtocol interface. On startup, it starts the GroupMembership service. It maintains a * ConcurrentHashMap KVStore that stores the key-value pairs that are destined for this host. Since it implements * the BoltDBProtocol, it provides the Remote methods to insert, lookup, update and delete keys. Upon request - * from a client, depending on the target host and the canBeForwarded flag, it performs the operation on - * the local key value store (If it is the target host) or forwards the operation by determining the target - * host from its MembershipList. - * @author Adarsh - * + * from a client, the request is forwarded to all the replicas of the key(Active replication) by spawning + * k threads where k is the replication factor. + * Each request takes in consistency level as parameter and accordingly waits for one or more threads to respond before + * sending back the result to the client. */ public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol { @@ -43,6 +42,7 @@ public class BoltDBServer extends UnicastRemoteObject implements BoltDBProtocol private static final long serialVersionUID = 5195393553928167809L; private static org.apache.log4j.Logger log = Logger.getRootLogger(); + //Buffer to hold most recent reads and writes public static CircularFifoBuffer readBuffer = new CircularFifoBuffer(10); public static CircularFifoBuffer writeBuffer = new CircularFifoBuffer(10); @@ -53,6 +53,7 @@ protected BoltDBServer() throws RemoteException { /** * @param args */ + //The in-memory key value store ! public static ConcurrentMap KVStore = new ConcurrentHashMap(); public static void main(String[] args) throws IOException { @@ -67,6 +68,12 @@ public static void main(String[] args) throws IOException { Naming.rebind ("KVStore", new BoltDBServer()); } + /** + * Gets the hostname of all the replicas of the key + * @param key + * @return + * @throws NoSuchAlgorithmException + */ private String[] getTargetHosts(long key) throws NoSuchAlgorithmException { String targetHost = null; String[] targetHosts = new String[GroupMembership.replicationFactor]; @@ -99,6 +106,14 @@ private int convertConsistencyLevelToInt(CONSISTENCY_LEVEL consistencyLevel) { return -1; } + /** + * Collects results from few replicas depending on the consistency level + * @param completionService + * @param consistencyLevel + * @return + * @throws InterruptedException + * @throws ExecutionException + */ private boolean waitForReplicaReplies(ExecutorCompletionService completionService, CONSISTENCY_LEVEL consistencyLevel) throws InterruptedException, ExecutionException { int replicaRepliesToWaitFor = convertConsistencyLevelToInt(consistencyLevel); @@ -114,7 +129,7 @@ private boolean waitForReplicaReplies(ExecutorCompletionService complet return false; } - private ValueTimeStamp waitForReplicaRepliesForUpdate(ExecutorCompletionService completionService, CONSISTENCY_LEVEL consistencyLevel) throws InterruptedException, ExecutionException { + private ValueTimeStamp waitForReplicaRepliesForLookup(ExecutorCompletionService completionService, CONSISTENCY_LEVEL consistencyLevel) throws InterruptedException, ExecutionException { int replicaRepliesToWaitFor = convertConsistencyLevelToInt(consistencyLevel); ValueTimeStamp result = null; ValueTimeStamp temp; @@ -159,7 +174,7 @@ public Boolean insert(long key, ValueTimeStamp value, boolean canBeForwarded,CON value.timeStamp = System.currentTimeMillis(); try { - // Determine the target host using the getSuccessorNodeOf method + // Determine the target hosts using the getSuccessorNodeOf method String[] targetHosts = getTargetHosts(key); @@ -205,7 +220,7 @@ public ValueTimeStamp lookup(long key, boolean canBeForwarded, CONSISTENCY_LEVEL completionService.submit(new LookupThread(targetHosts[i],key,consistencyLevel)); } - ValueTimeStamp result = waitForReplicaRepliesForUpdate(completionService, consistencyLevel); + ValueTimeStamp result = waitForReplicaRepliesForLookup(completionService, consistencyLevel); pool.shutdown(); return result; } catch (Exception e) { @@ -289,6 +304,9 @@ public Boolean delete(long key, boolean canBeForwarded,CONSISTENCY_LEVEL consist } } + /** + * Private api used only by ndoes to remap keys. + */ public void lookupAndInsertInto(String hostname, long startKeyRange, long endKeyRange) throws RemoteException { BoltDBProtocol targetServer = null; @@ -297,23 +315,17 @@ public void lookupAndInsertInto(String hostname, long startKeyRange, } catch (Exception e) { log.error(e.getMessage()); } - System.out.println("lookupAndInsert: start - "+startKeyRange+" end - "+ endKeyRange); for(Entry e : KVStore.entrySet()) { try { long hashOfKey = GroupMembership.computeHash(e.getKey().toString()); - System.out.println("lookupAndInsert: hashOfkey - "+hashOfKey); if (startKeyRange < endKeyRange) { if (hashOfKey >= startKeyRange && hashOfKey <= endKeyRange) { - System.out.println("Inserting " + hashOfKey + " from " - + GroupMembership.pid + " to " + hostname); log.info("["+new Date()+"]Inserting " + hashOfKey + " from " + GroupMembership.pid + " to " + hostname); targetServer.insert(e.getKey(), e.getValue(), false,null); } } else { if (hashOfKey >= startKeyRange || hashOfKey <= endKeyRange) { - System.out.println("Inserting " + hashOfKey + " from " - + GroupMembership.pid + " to " + hostname); log.info("["+new Date()+"]Inserting " + hashOfKey + " from " + GroupMembership.pid + " to " + hostname); targetServer.insert(e.getKey(), e.getValue(), false,null); diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/examples/StaleClient.java b/boltdb/src/main/java/edu/uiuc/boltdb/examples/StaleClient.java new file mode 100644 index 0000000..9cba93e --- /dev/null +++ b/boltdb/src/main/java/edu/uiuc/boltdb/examples/StaleClient.java @@ -0,0 +1,111 @@ +package edu.uiuc.boltdb.examples; + +import java.io.FileInputStream; +import java.io.FileNotFoundException; +import java.io.IOException; +import java.rmi.Naming; +import java.rmi.NotBoundException; +import java.rmi.RemoteException; +import java.util.Properties; +import java.util.concurrent.Executors; +import java.util.concurrent.ScheduledExecutorService; +import java.util.concurrent.TimeUnit; + +import edu.uiuc.boltdb.BoltDBProtocol; +import edu.uiuc.boltdb.ValueTimeStamp; +import edu.uiuc.boltdb.groupmembership.HeartbeatIncrementerThread; + +public class StaleClient { + + private static volatile long i = 0; + static int stalelookups = 0; + static long noOfwrites = 0; + static long noOfreads = 0; + /** + * @param args + * @throws IOException + * @throws NotBoundException + */ + public static void main(String[] args) throws IOException, NotBoundException { + // TODO Auto-generated method stub + Properties prop = new Properties(); + FileInputStream fis = new FileInputStream("./boltdb.prop"); + prop.load(fis); + fis.close(); + String rmiString = prop.getProperty("boltdb.kvstore.server"); + if(System.getSecurityManager() == null) { + System.setSecurityManager(new SecurityManager()); + } + final BoltDBProtocol boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); + boltDBServer.insert(10, new ValueTimeStamp(String.valueOf(i), 0), true, BoltDBProtocol.CONSISTENCY_LEVEL.ONE); + final int readwait = Integer.parseInt(prop.getProperty("staleclient.readwait")); + final int writewait = Integer.parseInt(prop.getProperty("staleclient.writewait")); + + Runnable writeClient = new Runnable() { + + public void run() { + while(true) { + try { + boltDBServer.update(10, new ValueTimeStamp(String.valueOf(++i), 0), true, BoltDBProtocol.CONSISTENCY_LEVEL.ONE); + noOfwrites++; + Thread.sleep(writewait); + } catch (RemoteException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (InterruptedException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + } + }; + + Runnable readClient = new Runnable() { + + public void run() { + while(true) { + try { + int result = Integer.parseInt(boltDBServer.lookup(10, true, BoltDBProtocol.CONSISTENCY_LEVEL.ONE).value); + noOfreads++; + if(result != i) { + stalelookups++; + } + Thread.sleep(readwait); + } catch (RemoteException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } catch (InterruptedException e) { + // TODO Auto-generated catch block + e.printStackTrace(); + } + } + } + }; + + Runnable printStaleValue = new Runnable() { + + public void run() { + // TODO Auto-generated method stub + System.out.println("Stale values per sec:"+stalelookups +" Writes:"+noOfwrites+" Reads:"+noOfreads); + stalelookups = 0; + noOfreads = 0; + noOfwrites = 0; + } + }; + + ScheduledExecutorService scheduler = Executors + .newSingleThreadScheduledExecutor(); + scheduler.scheduleAtFixedRate(printStaleValue, 0, + Integer.parseInt(prop + .getProperty("staleclient.printfreq")), + TimeUnit.MILLISECONDS); + + Thread writeThread = new Thread(writeClient); + Thread readThread = new Thread(readClient); + writeThread.start(); + readThread.start(); + + + } + +} diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 73f3619..3519b9b 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -110,13 +110,12 @@ public void run() { pid += "-" + args[3]; initializeLogger(args[3]); } - - //Compute the hashvalue of yourself(server) + + // Compute the hashvalue of yourself(server) long hashValue = computeHash(pid); - - + startTime = System.currentTimeMillis(); - + // Insert the current machine into the membership list with // heartbeat=1. This single entry is going to be sent to the contact // node for joining the cluster. @@ -131,9 +130,10 @@ public void run() { FileInputStream fis = new FileInputStream("./boltdb.prop"); prop.load(fis); fis.close(); - + // Set the replicaton factor from the properties file - replicationFactor = Integer.parseInt(prop.getProperty("groupmembership.rfactor")); + replicationFactor = Integer.parseInt(prop + .getProperty("groupmembership.rfactor")); // Start the thread that listens to gossip messages. Thread receiveGossip = new Thread(new ReceiveGossipThread()); @@ -161,8 +161,7 @@ public void run() { } // Get the tFail from property file - tFail = Integer.parseInt(prop - .getProperty("groupmembership.tfail")); + tFail = Integer.parseInt(prop.getProperty("groupmembership.tfail")); // ScheduledExecutorService is used to schedule all the threads // mentioned in the class javadoc with frequency mentioned in @@ -208,18 +207,6 @@ public void run() { receiveGossip.stop(); scheduler.shutdownNow(); scheduler.awaitTermination(100, TimeUnit.MILLISECONDS); - //Move your keys to successor - /*long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; - String successorHost = GroupMembership.membershipList.get(getSuccessorNode(myHash)).hostname; - BoltDBProtocol successorRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" + successorHost + "/KVStore"); - Iterator> itr = BoltDBServer.KVStore.entrySet().iterator(); - - while(itr.hasNext()) { - Entry entry = itr.next(); - successorRMIServer.insert(entry.getKey(), entry.getValue(), false,null); - } - BoltDBServer.KVStore.clear(); - */ MembershipBean mBean = membershipList.get(pid); mBean.hearbeatLastReceived = -1; mBean.timeStamp = System.currentTimeMillis(); @@ -230,80 +217,95 @@ public void run() { break; } /* - * The show command prints the current membershipList entries and the current KVStore - * entries on the console. + * The show command prints the current membershipList entries + * and the current KVStore entries on the console. */ - else if(commandString.equals("shownodes")) { - System.out.println("-------------------------------------------------"); + else if (commandString.equals("shownodes")) { + System.out + .println("-------------------------------------------------"); System.out.println("Membership List : "); - System.out.println("-------------------------------------------------"); - for (Map.Entry entry : membershipList.entrySet()) - { - System.out.println(entry.getValue().hostname + " " + entry.getValue().hashValue); + System.out + .println("-------------------------------------------------"); + for (Map.Entry entry : membershipList + .entrySet()) { + System.out.println(entry.getValue().hostname + " " + + entry.getValue().hashValue); } - System.out.println("-------------------------------------------------"); + System.out + .println("-------------------------------------------------"); System.out.println(); - } - else if(commandString.equals("showKV")) { - System.out.println("-------------------------------------------------"); + } else if (commandString.equals("showKV")) { + System.out + .println("-------------------------------------------------"); System.out.println("Key Value Store : "); - System.out.println("-------------------------------------------------"); - long myHash = GroupMembership.membershipList.get(GroupMembership.pid).hashValue; - long myPredecessor = GroupMembership.membershipList.get(GroupMembership.getPredecessorNode(myHash)).hashValue; - int primaryCount=0,replicaCount=0; - for (Map.Entry entry : BoltDBServer.KVStore.entrySet()) - { - long hashOfKey = computeHash((new Long(entry.getKey())).toString()); - System.out.print(entry.getKey() + " ---> " + entry.getValue() + " | Hash of Key - " + hashOfKey + " "); - if(myHash > myPredecessor) { - if(hashOfKey > myPredecessor && hashOfKey <= myHash) { - System.out.println("Primary"); - primaryCount++; - } - else { - System.out.println("Replica"); - replicaCount++; - } - } - else { - if(hashOfKey > myPredecessor || hashOfKey <= myHash) { - System.out.println("Primary"); - primaryCount++; - } - else { - System.out.println("Replica"); - replicaCount++; - } - } + System.out + .println("-------------------------------------------------"); + long myHash = GroupMembership.membershipList + .get(GroupMembership.pid).hashValue; + long myPredecessor = GroupMembership.membershipList + .get(GroupMembership.getPredecessorNode(myHash)).hashValue; + int primaryCount = 0, replicaCount = 0; + for (Map.Entry entry : BoltDBServer.KVStore + .entrySet()) { + long hashOfKey = computeHash((new Long(entry.getKey())) + .toString()); + System.out.print(entry.getKey() + " ---> " + + entry.getValue() + " | Hash of Key - " + + hashOfKey + " "); + if (myHash > myPredecessor) { + if (hashOfKey > myPredecessor + && hashOfKey <= myHash) { + System.out.println("Primary"); + primaryCount++; + } else { + System.out.println("Replica"); + replicaCount++; + } + } else { + if (hashOfKey > myPredecessor + || hashOfKey <= myHash) { + System.out.println("Primary"); + primaryCount++; + } else { + System.out.println("Replica"); + replicaCount++; + } + } } - System.out.println("-------------------------------------------------"); - System.out.println("Primary - " + primaryCount + " Replicas - " + replicaCount + " Total - " + (primaryCount+replicaCount)); + System.out + .println("-------------------------------------------------"); + System.out.println("Primary - " + primaryCount + + " Replicas - " + replicaCount + " Total - " + + (primaryCount + replicaCount)); System.out.println(); - } - else if(commandString.equals("ring")) { - System.out.println("-------------------------------------------------"); + } else if (commandString.equals("ring")) { + System.out + .println("-------------------------------------------------"); System.out.println("Node Ring : "); int noOfNodes = membershipList.size(); long node = computeHash(this.pid); - while(noOfNodes-- > 0) { + while (noOfNodes-- > 0) { System.out.print(node + " --> "); node = computeHash(getSuccessorNode(node)); } System.out.println("looparound"); - System.out.println("-------------------------------------------------"); + System.out + .println("-------------------------------------------------"); System.out.println(); - } else if(commandString.equals("show")) { - System.out.println("-------------------------------------------------"); + } else if (commandString.equals("show")) { + System.out + .println("-------------------------------------------------"); System.out.println("RECENT READS"); Iterator itr = BoltDBServer.readBuffer.iterator(); - while(itr.hasNext()) { - System.out.println((Operation)itr.next()); + while (itr.hasNext()) { + System.out.println((Operation) itr.next()); } - System.out.println("-------------------------------------------------"); + System.out + .println("-------------------------------------------------"); System.out.println("RECENT WRITES"); itr = BoltDBServer.writeBuffer.iterator(); - while(itr.hasNext()) { - System.out.println((Operation)itr.next()); + while (itr.hasNext()) { + System.out.println((Operation) itr.next()); } } } @@ -312,163 +314,168 @@ else if(commandString.equals("ring")) { } } - + /** - * Computes the MD5 hash of the pid,transforms it into an integer - * and hashes it in the range 0-1 million. + * Computes the MD5 hash of the pid,transforms it into an integer and hashes + * it in the range 0-1 million. + * * @param pid * @return * @throws NoSuchAlgorithmException */ public static long computeHash(String pid) throws NoSuchAlgorithmException { - if(pid.length() <= 6 && !pid.isEmpty()) + if (pid.length() <= 6 && !pid.isEmpty()) return Long.parseLong(pid); - + MessageDigest md = MessageDigest.getInstance("MD5"); BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); return Math.abs(bigInt.longValue()) % 1000001L; } - + /** * Returns the node which is the successor of a key. + * * @param keyHash * @return */ public static String getSuccessorNode(long aNode) { - Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); - //Set the minimum clockwise distance to be maximum possible value + Iterator> itr = GroupMembership.membershipList + .entrySet().iterator(); + // Set the minimum clockwise distance to be maximum possible value long minClockwiseDistance = 1000000L; String successorNode = new String(); - while(itr.hasNext()) { - Entry entry = itr.next(); - //Ignore if the entry is yourself(Server) - if(entry.getValue().hashValue == aNode) continue; + while (itr.hasNext()) { + Entry entry = itr.next(); + // Ignore if the entry is yourself(Server) + if (entry.getValue().hashValue == aNode) + continue; long hashCurrent = entry.getValue().hashValue; - //compute the clockwise distance - long clockWiseDistance = aNode > hashCurrent ? 1000000l - (aNode - hashCurrent) : hashCurrent - aNode; - //Update minimum clockwise distance if required - if(minClockwiseDistance > clockWiseDistance) { + // compute the clockwise distance + long clockWiseDistance = aNode > hashCurrent ? 1000000l - (aNode - hashCurrent) + : hashCurrent - aNode; + // Update minimum clockwise distance if required + if (minClockwiseDistance > clockWiseDistance) { minClockwiseDistance = clockWiseDistance; successorNode = entry.getKey(); } } return successorNode; } - - + /** * Returns the node which is the predecessor of a key. + * * @param keyHash * @return */ public static String getPredecessorNode(long aNode) { - Iterator> itr = GroupMembership.membershipList.entrySet().iterator(); - //Set the maximum clockwise distance to be minimum possible value + Iterator> itr = GroupMembership.membershipList + .entrySet().iterator(); + // Set the maximum clockwise distance to be minimum possible value long maxClockwiseDistance = 0L; String predecessorNode = new String(); - while(itr.hasNext()) { - Entry entry = itr.next(); - //Ignore if the entry is yourself(Server) - if(entry.getValue().hashValue == aNode) continue; + while (itr.hasNext()) { + Entry entry = itr.next(); + // Ignore if the entry is yourself(Server) + if (entry.getValue().hashValue == aNode) + continue; long hashCurrent = entry.getValue().hashValue; - //compute the clockwise distance - long clockWiseDistance = aNode > hashCurrent ? 1000000L - (aNode - hashCurrent) : hashCurrent - aNode; - //Update minimum clockwise distance if required - if(maxClockwiseDistance < clockWiseDistance) { + // compute the clockwise distance + long clockWiseDistance = aNode > hashCurrent ? 1000000L - (aNode - hashCurrent) + : hashCurrent - aNode; + // Update minimum clockwise distance if required + if (maxClockwiseDistance < clockWiseDistance) { maxClockwiseDistance = clockWiseDistance; predecessorNode = entry.getKey(); } } return predecessorNode; } - - public static int inSuccReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException - { + + public static int inSuccReReplicationSeg(long thisNode, long failedNode) + throws NoSuchAlgorithmException { int k = replicationFactor; - while(k-- > 0) { - if((failedNode=computeHash(getSuccessorNode(failedNode))) == thisNode) + while (k-- > 0) { + if ((failedNode = computeHash(getSuccessorNode(failedNode))) == thisNode) return (replicationFactor - k); } return -1; } - - public static int inPredReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException - { + + public static int inPredReReplicationSeg(long thisNode, long failedNode) + throws NoSuchAlgorithmException { int k = replicationFactor; - while(k-- > 1) { - if((failedNode=computeHash(getPredecessorNode(failedNode))) == thisNode) + while (k-- > 1) { + if ((failedNode = computeHash(getPredecessorNode(failedNode))) == thisNode) return (replicationFactor - k); } return -1; } - - public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorithmException - { + + public static String getKthSuccessorNode(long aNode, int k) + throws NoSuchAlgorithmException { String successorNode = new String(); - while(k-- > 0) - { + while (k-- > 0) { successorNode = getSuccessorNode(aNode); aNode = computeHash(successorNode); } return successorNode; } - - + public synchronized static void handleCrash(long hashCrashedNode) throws NoSuchAlgorithmException, MalformedURLException, NotBoundException { - //TODO doesnt work for k=1,2; && need to compute hash of keys before comparing at all places - if(membershipList.size() <= 3) return; + if (membershipList.size() <= 3) + return; long myhash = membershipList.get(GroupMembership.pid).hashValue; - int successorPosition = inSuccReReplicationSeg(myhash,hashCrashedNode); + int successorPosition = inSuccReReplicationSeg(myhash, hashCrashedNode); if (successorPosition != -1) { - //System.out.println("successor position:"+successorPosition); long startKey, endKey; String targetNode; - if(successorPosition == 3) { - startKey = membershipList.get(getPredecessorNode(hashCrashedNode)).hashValue + 1; + if (successorPosition == replicationFactor) { + startKey = membershipList + .get(getPredecessorNode(hashCrashedNode)).hashValue + 1; endKey = hashCrashedNode; targetNode = getSuccessorNode(hashCrashedNode); - } - else { - targetNode = getKthPredecessorNode(hashCrashedNode, replicationFactor - successorPosition); - startKey = membershipList.get(getPredecessorNode(membershipList.get(targetNode).hashValue)).hashValue + 1; + } else { + targetNode = getKthPredecessorNode(hashCrashedNode, + replicationFactor - successorPosition); + startKey = membershipList.get(getPredecessorNode(membershipList + .get(targetNode).hashValue)).hashValue + 1; endKey = membershipList.get(targetNode).hashValue; } - - //System.out.println("startkey:"+startKey+ " endKey:"+endKey+" targetNode:"+targetNode); + BoltDBProtocol targetRMIServer = null; int i = 0; while (i++ < replicationFactor - 1) { try { - //System.out.println("trying to connect to targetNode pid :"+targetNode+" with hostname :"+ membershipList.get(targetNode).hostname ); targetRMIServer = (BoltDBProtocol) Naming.lookup("rmi://" - + membershipList.get(targetNode).hostname + "/KVStore"); - targetRMIServer.lookupAndInsertInto(membershipList.get(pid).hostname, startKey, endKey); + + membershipList.get(targetNode).hostname + + "/KVStore"); + targetRMIServer.lookupAndInsertInto( + membershipList.get(pid).hostname, startKey, endKey); break; } catch (RemoteException e1) { - System.out.println("Exception while connecting to "+targetNode+ " "+e1.getMessage()); + System.out.println("Exception while connecting to " + + targetNode + " " + e1.getMessage()); targetNode = getSuccessorNode(GroupMembership.membershipList .get(targetNode).hashValue); continue; } } - - if(targetRMIServer == null) { + + if (targetRMIServer == null) { System.out.println("Problem replicating keys during crash"); log.error("Problem replicating keys during crash"); return; } } } - - - public static String getKthPredecessorNode(long aNode, int k) throws NoSuchAlgorithmException - { + public static String getKthPredecessorNode(long aNode, int k) + throws NoSuchAlgorithmException { String predecessorNode = new String(); - while(k-- > 0) - { + while (k-- > 0) { predecessorNode = getPredecessorNode(aNode); aNode = computeHash(predecessorNode); } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java index e49714b..6975508 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/MergeThread.java @@ -66,8 +66,6 @@ public void run() } catch (Exception e) { e.printStackTrace(); } - - //System.out.println("\nAFTER MERGE : "+GroupMembership.membershipList); } /** @@ -114,7 +112,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme //VOLUNTARILY LEAVE : If the incoming entry has heartbeat less than zero,then log 'VOLUNTARILY LEFT' message. //Also update current node's membership list if(receivedMBean.hearbeatLastReceived <= 0 && currentMBean.hearbeatLastReceived > 0) { - System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); + //System.out.println("VOLUNTARILY LEFT : " + receivedPid+ " at "+(new Date()).toString()); log.info("["+new Date()+"]VOLUNTARILY LEFT - - - " + receivedPid); currentMBean.hearbeatLastReceived = -1; currentMBean.timeStamp = System.currentTimeMillis(); @@ -129,7 +127,7 @@ private void mergeIncomingMembershipList() throws UnknownHostException, Malforme currentMBean.hearbeatLastReceived = receivedMBean.hearbeatLastReceived; currentMBean.timeStamp = System.currentTimeMillis(); if(currentMBean.toBeDeleted) { - System.out.println("JOINED : " + receivedPid); + //System.out.println("JOINED : " + receivedPid); log.info("["+new Date()+"]JOINED : " + receivedPid); currentMBean.toBeDeleted = false; } @@ -147,17 +145,14 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea System.currentTimeMillis(), receivedMBean.hashValue, false); - System.out.println("JOINED : " + receivedPid+" at "+(new - Date()).toString()); + //System.out.println("JOINED : " + receivedPid+" at "+(new + // Date()).toString()); log.info("["+new Date()+"]JOINED - - - " + receivedPid); // Get the successor of newly joined node if((System.currentTimeMillis() - GroupMembership.startTime) > (GroupMembership.tFail * 1000)) { boolean amISuccessor = amITheSuccesorOf(receivedMBean.hashValue); if (amISuccessor) { - // If you are the successor,move keys accordingly. - //System.out.println("hey I'm the succ of newly joined node:" - // + receivedHost); moveKeysSucc(receivedHost, mBean.hashValue); } else if (GroupMembership.membershipList.size() >= 3) { int amIInPredReReplicationSeg = GroupMembership @@ -166,9 +161,6 @@ else if(!GroupMembership.membershipList.containsKey(receivedPid) && receivedMBea .get(GroupMembership.pid).hashValue, mBean.hashValue); if (amIInPredReReplicationSeg != -1) { - //System.out.println("hey I'm the " - // + amIInPredReReplicationSeg - // + " pred of newly joined node:" + receivedHost); moveKeysPred(receivedHost, mBean.hashValue, amIInPredReReplicationSeg); } @@ -224,9 +216,6 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma // and less than newly joined server. if (myHash > hashOfNewJoinedNode) { if (hashOfKey > myHash || hashOfKey <= hashOfNewJoinedNode) { - System.out.println("Inserting key :" + entry.getKey() - + " value:" + entry.getValue() + " from Me to " - + targetHost); log.info("["+new Date()+"]Inserting key :" + entry.getKey() + " value:" + entry.getValue() + " from Me to " + targetHost); @@ -239,9 +228,6 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma log.info("["+new Date()+"]Deleting key :" + entry.getKey() + " from " + succSuccessorHost); - System.out.println("Deleting key :" - + entry.getKey() + " from " - + succSuccessorHost); succSuccRMIServer.delete(entry.getKey(), false, null); } } @@ -251,9 +237,6 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma // then move all the keys in between the two servers hashes. else { if (hashOfKey > myHash && hashOfKey <= hashOfNewJoinedNode) { - System.out.println("Inserting key :" + entry.getKey() - + " value:" + entry.getValue() + " from Me to " - + targetHost); log.info("["+new Date()+"]Inserting key :" + entry.getKey() + " value:" + entry.getValue() + " from Me to " + targetHost); @@ -262,9 +245,6 @@ private void moveKeysSucc(String targetHost, long hashOfNewJoinedNode) throws Ma // BoltDBServer.KVStore.remove(entry.getKey()); // Delete this key in successor's successor if (GroupMembership.membershipList.size() >= 3) { - System.out.println("Deleting key :" - + entry.getKey() + " from " - + succSuccessorHost); log.info("["+new Date()+"]Deleting key :" + entry.getKey() + " from " + succSuccessorHost); @@ -300,23 +280,19 @@ private void moveKeysPred(String targetHost, long hashOfNewJoinedNode, int prede long hashOfKey = GroupMembership.computeHash(entry.getKey().toString()); if (myHash > myPredecessor) { if ( hashOfKey > myPredecessor && hashOfKey <= myHash) { - System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); log.info("["+new Date()+"]Inserting key :" + entry.getKey() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(),false, null); - System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); log.info("["+new Date()+"]Deleting key :" + entry.getKey() + " from " + kpthSuccHost); kpthSuccRMIServer.delete(entry.getKey(), false, null); } } else { if ( hashOfKey > myPredecessor || hashOfKey <= myHash) { - System.out.println("Inserting key :" + entry.getKey() + " from Me to " + targetHost); log.info("["+new Date()+"]Inserting key :" + entry.getKey() + " from Me to " + targetHost); targetRMIServer.insert(entry.getKey(), entry.getValue(),false, null); log.info("["+new Date()+"]Deleting key :" + entry.getKey() + " from " + kpthSuccHost); - System.out.println("Deleting key :" + entry.getKey() + " from " + kpthSuccHost); kpthSuccRMIServer.delete(entry.getKey(), false, null); } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java index c64724e..a442aa1 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/RefreshMembershipListThread.java @@ -60,7 +60,7 @@ else if (System.currentTimeMillis() - membershipBean.timeStamp >= tFail * 1000 & { membershipBean.toBeDeleted = true; if (membershipBean.hearbeatLastReceived > 0) { - System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); + //System.out.println("CRASHED : " + entry.getKey() +" at " + new Date().toString()); log.info("["+new Date()+"]CRASHED - - - " + entry.getKey()); } } diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java b/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java index 983234e..e3d7e05 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/methods/DeleteThread.java @@ -2,7 +2,6 @@ import java.net.InetAddress; import java.rmi.Naming; -import java.rmi.RemoteException; import java.util.Date; import java.util.concurrent.Callable; From 44b0912df117eee0fee9268a0c49a460e7f52c25 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 8 Dec 2013 22:03:59 -0600 Subject: [PATCH 47/48] deleted --- .../tests/BoltDBPerformanceTest.java | 95 ------------------- 1 file changed, 95 deletions(-) delete mode 100644 boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java b/boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java deleted file mode 100644 index 554143e..0000000 --- a/boltdb/src/main/java/edu/uiuc/boltdb/logquerier/tests/BoltDBPerformanceTest.java +++ /dev/null @@ -1,95 +0,0 @@ -package edu.uiuc.boltdb.logquerier.tests; - -import java.io.BufferedReader; -import java.io.FileInputStream; -import java.io.FileReader; -import java.io.IOException; -import java.math.BigInteger; -import java.rmi.Naming; -import java.rmi.NotBoundException; -import java.security.MessageDigest; -import java.security.NoSuchAlgorithmException; -import java.util.HashMap; -import java.util.Iterator; -import java.util.Properties; -import java.util.StringTokenizer; -import java.util.Map.Entry; - -import edu.uiuc.boltdb.BoltDBProtocol; - -public class BoltDBPerformanceTest { - - /** - * @param args - * @throws IOException - * @throws NoSuchAlgorithmException - * @throws NotBoundException - */ - public static void main(String[] args) throws IOException, NoSuchAlgorithmException, NotBoundException { - // TODO Auto-generated method stub - Properties prop = new Properties(); - FileInputStream fis = new FileInputStream("./boltdb.prop"); - prop.load(fis); - fis.close(); - String rmiString = prop.getProperty("boltdb.kvstore.server"); - String rawFile = prop.getProperty("boltdb.kvstore.examples.movies.toIndex"); - - if(System.getSecurityManager() == null) { - System.setSecurityManager(new SecurityManager()); - } - BoltDBProtocol boltDBServer = (BoltDBProtocol) Naming.lookup("rmi://" + rmiString + "/KVStore"); - - HashMap hmap = new HashMap(); - BufferedReader br = new BufferedReader(new FileReader(rawFile)); - String line; - int count = 0; - while((line = br.readLine()) != null && count < 1000) { - line = line.trim(); - StringTokenizer stk = new StringTokenizer(line); - while(stk.hasMoreTokens() && count < 1000) { - long key = computeHash(stk.nextToken()); - String curValue = hmap.get(key); - if(curValue != null) - continue; - String value = line; - hmap.put(key, value); - count++; - } - } - Iterator> itr = hmap.entrySet().iterator(); - while(itr.hasNext()) { - Entry entry = itr.next(); - boltDBServer.insert(entry.getKey(), entry.getValue(), true); - //System.out.println("Successfully inserted " + entry.getKey() + " --> " + entry.getValue()); - } - - int updateCount = 0; - itr = hmap.entrySet().iterator(); - while(itr.hasNext() && updateCount++ < 100) { - Entry entry = itr.next(); - long startTime = System.currentTimeMillis(); - boltDBServer.update(entry.getKey(), "Some value", true); - long endTime = System.currentTimeMillis(); - System.out.println(endTime-startTime); - } - - System.out.println("------------------------------------------------------------"); - - int deleteCount = 0; - itr = hmap.entrySet().iterator(); - while(itr.hasNext() && deleteCount++ < 100) { - Entry entry = itr.next(); - long startTime = System.currentTimeMillis(); - boltDBServer.delete(entry.getKey(), true); - long endTime = System.currentTimeMillis(); - System.out.println(endTime-startTime); - } - - br.close(); - } - public static long computeHash(String pid) throws NoSuchAlgorithmException { - MessageDigest md = MessageDigest.getInstance("MD5"); - BigInteger bigInt = new BigInteger(1, md.digest(pid.getBytes())); - return Math.abs(bigInt.longValue()) % 1000001L; - } - } From 78c5d21ec4b056cd7490dce80ea0a53f44db0471 Mon Sep 17 00:00:00 2001 From: Adarsh Date: Sun, 8 Dec 2013 22:25:56 -0600 Subject: [PATCH 48/48] changes --- README.md | 52 ++++++++++++++++--- .../groupmembership/GroupMembership.java | 18 +++++++ 2 files changed, 63 insertions(+), 7 deletions(-) diff --git a/README.md b/README.md index a53be1c..f8cf1ff 100644 --- a/README.md +++ b/README.md @@ -1,9 +1,13 @@ -Steps to run the membership service - +----------------------------------------------------------------------------------------------------------------- +Steps to run the BoltDB KeyValue Store Server - +----------------------------------------------------------------------------------------------------------------- -1) Copy the boltdb-0.0.1-SNAPSHOT.jar, gson-1.7.1.jar, log4j-1.2.17.jar, dgroupmembership and boltdb.prop - files into a folder. +1) Copy the boltdb-0.0.1-SNAPSHOT.jar, gson-1.7.1.jar, log4j-1.2.17.jar, commons-collections-3.0.jar, boltdb-server, server.policy + BoltDBServer_Stub.class and boltdb.prop files into a folder. 2) cd into the folder to which you copied the above files. -3) Open the boltdb.prop file in a text editor and set the properties +3) Open the server.policy file and change the path in the policy file to the path of the current folder( where + the jar resides) +4) Open the boltdb.prop file in a text editor and set the properties * "groupmembership.contact" - This is the hostname/ipaddress of the contact machine. * "groupmembership.tfail" - The time out for marking a process as failed * "groupmembership.heartbeat.freq" - The frequency at which the local heartbeat should be @@ -12,18 +16,50 @@ Steps to run the membership service - membership list should be refreshed (mark failures and remove marked entries). * "groupmembership.gossip.freq" - The gossip frequency. * "groupmembership.lossrate" - The message loss rate to be simulated. + * "groupmembership.rfactor" - The replication factor -4) Run the command - "./dgroupmembership -contact true -id machine.1 +5) Run the command - "./boltdb-server -contact true -id machine.1 * "-contact" option is for specifying whether or not this daemon is the contact machine daemon.(In this case, it is "true". For the other daemons, specify "-contact" as "false") * "-id" is a unique id for the daemon and this unique id will be used to name the log file on this machine. -5) While running the service, if you wish to voluntarily leave the system, type "leave" and hit enter. If you - want to crash the process, press Ctrl+C. +6) On the boltdb-server> prompt - + * If you wish to voluntarily leave the system, type "leave" and hit enter. + * If you wish to print out the membership list type "shownodes" and hit enter + * If you wish to print out the contents of the key value store type "showKV" and hit enter. + * If you wish to print out 10 most recent reads and writes, type "show" and hit enter +----------------------------------------------------------------------------------------------------------------- + + +----------------------------------------------------------------------------------------------------------------- +Steps to run the BoltDB KeyValue Store Client - +----------------------------------------------------------------------------------------------------------------- + +1) Copy the boltdb-0.0.1-SNAPSHOT.jar, gson-1.7.1.jar, log4j-1.2.17.jar, commons-collections-3.0.jar, boltdb-server, server.policy + BoltDBServer_Stub.class and boltdb.prop files into a folder. +2) cd into the folder to which you copied the above files. +3) Open the client.policy file and change the path in the policy file to the path of the current folder( where + the jar resides) +4) Open the boltdb.prop file in a text editor and set the properties + * "boltdb.kvstore.server" - This is the hostname/ipaddress of the server to which the client talks. + * "boltdb.kvstore.clevel" - This is the consistency level. Possible values - ONE, QUORUM, ALL +5) Run the command - "./boltdb-client +6) On the boltdb-client> prompt - + * "insert " - Inserts the key and value onto the Distributed Key Value Store with the given consistency level + * "update " - Updates the key and value onto the Distributed Key Value Store with the given consistency level + * "lookup " - Looks Up the key in the Distributed Key Value Store with the given consistency level + * "delete " - Deletes the key from the Distributed Key Value Store with the given consistency level +----------------------------------------------------------------------------------------------------------------- + + + +----------------------------------------------------------------------------------------------------------------- Steps to run the Log Querier service - +----------------------------------------------------------------------------------------------------------------- Start the LogQuerier server - + 1) Copy the boltdb-0.0.1-SNAPSHOT.jar, dgrep and boltdb.prop files into a folder. (If you have already copied these files in the previous step - while running the GroupMembership daemon, you should be fine) 2) cd into the folder to which you copied the above files. @@ -34,6 +70,7 @@ Start the LogQuerier server - Query logs using the LogQuerier client - + 1) Copy the boltdb-0.0.1-SNAPSHOT.jar, dgrep and boltdb.prop files into a folder (If you have already copied these files in the previous step - while running the GroupMembership daemon, you should be fine) 2) cd into the folder to which you copied the above files. @@ -44,3 +81,4 @@ Query logs using the LogQuerier client - * To look for joins, type the command "./dgrep -key JOINED" * To look for crashes, type the command "./dgrep -key CRASHED" * To look for leavs, type the command "./dgrep -key LEFT" +----------------------------------------------------------------------------------------------------------------- diff --git a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java index 3519b9b..4c6b8ca 100644 --- a/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java +++ b/boltdb/src/main/java/edu/uiuc/boltdb/groupmembership/GroupMembership.java @@ -392,6 +392,9 @@ public static String getPredecessorNode(long aNode) { return predecessorNode; } + /* + * This method is called by a node to check if its in the successor rereplication segment + */ public static int inSuccReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException { int k = replicationFactor; @@ -401,6 +404,10 @@ public static int inSuccReReplicationSeg(long thisNode, long failedNode) } return -1; } + + /* + * This method is called by a node to check if its in the predecessor rereplication segment + */ public static int inPredReReplicationSeg(long thisNode, long failedNode) throws NoSuchAlgorithmException { @@ -411,6 +418,10 @@ public static int inPredReReplicationSeg(long thisNode, long failedNode) } return -1; } + + /* + * This method is used to get the kth successor of a node + */ public static String getKthSuccessorNode(long aNode, int k) throws NoSuchAlgorithmException { @@ -421,6 +432,10 @@ public static String getKthSuccessorNode(long aNode, int k) } return successorNode; } + + /* + * This method is called to handle a crash + */ public synchronized static void handleCrash(long hashCrashedNode) throws NoSuchAlgorithmException, MalformedURLException, @@ -472,6 +487,9 @@ public synchronized static void handleCrash(long hashCrashedNode) } } + /* + * This method gets the kth predecessor of a node + */ public static String getKthPredecessorNode(long aNode, int k) throws NoSuchAlgorithmException { String predecessorNode = new String();