?? chordimpl.java
字號:
}
// determine ID for key
ID id = this.hashFunction.getHashKey(key);
Entry entryToInsert = new Entry(id, s);
boolean debug = this.logger.isEnabledFor(DEBUG);
if (debug) {
this.logger.debug("Inserting new entry with id " + id);
}
boolean inserted = false;
while (!inserted) {
// find successor of id
Node responsibleNode;
// try {
responsibleNode = this.findSuccessor(id);
if (debug) {
this.logger.debug("Invoking insertEntry method on node "
+ responsibleNode.getNodeID());
}
// invoke insertEntry method
try {
responsibleNode.insertEntry(entryToInsert);
inserted = true;
} catch (CommunicationException e1) {
if (debug) {
this.logger
.debug(
"An error occured while invoking the insertEntry method "
+ " on the appropriate node! Insert operation "
+ "failed!", e1);
}
continue;
}
}
this.logger.debug("New entry was inserted!");
}
public final Set<Serializable> retrieve(Key key) {
// check parameters
if (key == null) {
NullPointerException e = new NullPointerException(
"Key must not have value null!");
this.logger.error("Null pointer", e);
throw e;
}
// determine ID for key
ID id = this.hashFunction.getHashKey(key);
boolean debug = this.logger.isEnabledFor(DEBUG);
if (debug) {
this.logger.debug("Retrieving entries with id " + id);
}
Set<Entry> result = null;
boolean retrieved = false;
while (!retrieved) {
// find successor of id
Node responsibleNode = null;
responsibleNode = findSuccessor(id);
// invoke retrieveEntry method
try {
result = responsibleNode.retrieveEntries(id);
// cause while loop to end.
retrieved = true;
} catch (CommunicationException e1) {
if (debug) {
this.logger
.debug(
"An error occured while invoking the retrieveEntry method "
+ " on the appropriate node! Retrieve operation "
+ "failed!", e1);
}
continue;
}
}
Set<Serializable> values = new HashSet<Serializable>();
if (result != null) {
for (Entry entry : result) {
values.add(entry.getValue());
}
}
this.logger.debug("Entries were retrieved!");
return values;
}
public final void remove(Key key, Serializable s) {
// check parameters
if (key == null || s == null) {
throw new NullPointerException(
"Neither parameter may have value null!");
}
// determine ID for key
ID id = this.hashFunction.getHashKey(key);
Entry entryToRemove = new Entry(id, s);
boolean removed = false;
while (!removed) {
boolean debug = this.logger.isEnabledFor(DEBUG);
if (debug) {
this.logger.debug("Removing entry with id " + id
+ " and value " + s);
}
// find successor of id
Node responsibleNode;
responsibleNode = findSuccessor(id);
if (debug) {
this.logger.debug("Invoking removeEntry method on node "
+ responsibleNode.getNodeID());
}
// invoke removeEntry method
try {
responsibleNode.removeEntry(entryToRemove);
removed = true;
} catch (CommunicationException e1) {
if (debug) {
this.logger
.debug(
"An error occured while invoking the removeEntry method "
+ " on the appropriate node! Remove operation "
+ "failed!", e1);
}
continue;
}
}
this.logger.debug("Entry was removed!");
}
/**
* Returns a human-readable string representation containing this node's
* node ID and URL.
*
* @see java.lang.Object#toString()
*/
@Override
public final String toString() {
return "Chord node: id = "
+ (this.localID == null ? "null" : this.localID.toString())
+ ", url = "
+ (this.localURL == null ? "null" : this.localURL.toString()
+ "\n");
}
/**
* Returns the Chord node which is responsible for the given key.
*
* @param key
* Key for which the successor is searched for.
* @throws NullPointerException
* If given ID is <code>null</code>.
* @return Responsible node.
*/
final Node findSuccessor(ID key) {
if (key == null) {
NullPointerException e = new NullPointerException(
"ID to find successor for may not be null!");
this.logger.error("Null pointer.", e);
throw e;
}
boolean debug = this.logger.isEnabledFor(DEBUG);
// check if the local node is the only node in the network
Node successor = this.references.getSuccessor();
if (successor == null) {
if (this.logger.isEnabledFor(INFO)) {
this.logger
.info("I appear to be the only node in the network, so I am "
+ "my own "
+ "successor; return reference on me: "
+ this.getID());
}
return this.localNode;
}
// check if the key to look up lies between this node and its successor
else if (key.isInInterval(this.getID(), successor.getNodeID())
|| key.equals(successor.getNodeID())) {
if (debug) {
this.logger
.debug("The requested key lies between my own and my "
+ "successor's node id; therefore return my successor.");
}
// try to reach successor
try {
// successor.ping(); // if methods returns, successor is alive.
// ping removed on 17.09.2007. sven
if (debug) {
this.logger.debug("Returning my successor "
+ successor.getNodeID() + " of type "
+ successor.getClass());
}
return successor;
} catch (Exception e) {
// not successful, delete node from successor list and finger
// table, and set new successor, if available
this.logger
.warn("Successor did not respond! Removing it from all "
+ "lists and retrying...");
this.references.removeReference(successor);
return findSuccessor(key);
}
}
// ask closest preceding node found in local references for closest
// preceding node concerning the key to look up
else {
Node closestPrecedingNode = this.references
.getClosestPrecedingNode(key);
try {
if (debug) {
this.logger
.debug("Asking closest preceding node known to this node for closest preceding node "
+ closestPrecedingNode.getNodeID()
+ " concerning key " + key + " to look up");
}
return closestPrecedingNode.findSuccessor(key);
} catch (CommunicationException e) {
this.logger
.error("Communication failure while requesting successor "
+ "for key "
+ key
+ " from node "
+ closestPrecedingNode.toString()
+ " - looking up successor for failed node "
+ closestPrecedingNode.toString());
this.references.removeReference(closestPrecedingNode);
return findSuccessor(key);
}
}
}
/* Implementation of Report interface */
public final String printEntries() {
return this.entries.toString();
}
public final String printFingerTable() {
return this.references.printFingerTable();
}
public final String printSuccessorList() {
return this.references.printSuccessorList();
}
public final String printReferences() {
return this.references.toString();
}
public final String printPredecessor() {
Node pre = this.references.getPredecessor();
if (pre == null) {
return "Predecessor: null";
} else {
return "Predecessor: " + pre.toString();
}
}
public void retrieve(final Key key, final ChordCallback callback) {
final Chord chord = this;
this.asyncExecutor.execute(new Runnable() {
public void run() {
Throwable t = null;
Set<Serializable> result = null;
try {
result = chord.retrieve(key);
} catch (ServiceException e) {
t = e;
} catch (Throwable th) {
t = th;
}
callback.retrieved(key, result, t);
}
});
}
public void insert(final Key key, final Serializable entry,
final ChordCallback callback) {
final Chord chord = this;
this.asyncExecutor.execute(new Runnable() {
public void run() {
Throwable t = null;
try {
chord.insert(key, entry);
} catch (ServiceException e) {
t = e;
} catch (Throwable th) {
t = th;
}
callback.inserted(key, entry, t);
}
});
}
public void remove(final Key key, final Serializable entry,
final ChordCallback callback) {
final Chord chord = this;
this.asyncExecutor.execute(new Runnable() {
public void run() {
Throwable t = null;
try {
chord.remove(key, entry);
} catch (ServiceException e) {
t = e;
} catch (Throwable th) {
t = th;
}
callback.removed(key, entry, t);
}
});
}
public ChordRetrievalFuture retrieveAsync(Key key) {
return ChordRetrievalFutureImpl.create(this.asyncExecutor, this, key);
}
public ChordFuture insertAsync(Key key, Serializable entry) {
return ChordInsertFuture.create(this.asyncExecutor, this, key, entry);
}
public ChordFuture removeAsync(Key key, Serializable entry) {
return ChordRemoveFuture.create(this.asyncExecutor, this, key, entry);
}
}
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -