/* This code is part of Freenet. It is distributed under the GNU General
* Public License, version 2 (or at your option any later version). See
* http://www.gnu.org/ for further details of the GPL. */
package freenet.node;
import freenet.client.InsertException;
import freenet.client.async.ClientContext;
import freenet.client.async.ClientRequestScheduler;
import freenet.keys.ClientKey;
import freenet.support.Logger;
import freenet.support.io.NativeThread;
import freenet.support.io.ResumeFailedException;
/**
* Callback interface for a low level insert, which is immediately sendable. These
* should be registered on the ClientRequestScheduler when we want to send them. It will
* then, when it is time to send, create a thread, send the request, and call the
* callback below.
*/
public abstract class SendableInsert extends SendableRequest {
private static final long serialVersionUID = 1L;
public SendableInsert(boolean persistent, boolean realTimeFlag) {
super(persistent, realTimeFlag);
}
/** Called when we successfully insert the data */
public abstract void onSuccess(SendableRequestItem keyNum, ClientKey key, ClientContext context);
/** Called when we don't! */
public abstract void onFailure(LowLevelPutException e, SendableRequestItem keyNum, ClientContext context);
@Override
public void internalError(Throwable t, RequestScheduler sched, ClientContext context, boolean persistent) {
Logger.error(this, "Internal error on "+this+" : "+t, t);
sched.callFailure(this, new LowLevelPutException(LowLevelPutException.INTERNAL_ERROR, t.getMessage(), t), NativeThread.MAX_PRIORITY, persistent);
}
@Override
public final boolean isInsert() {
return true;
}
@Override
public ClientRequestScheduler getScheduler(ClientContext context) {
if(isSSK())
return context.getSskInsertScheduler(realTimeFlag);
else
return context.getChkInsertScheduler(realTimeFlag);
}
public abstract boolean canWriteClientCache();
public abstract boolean localRequestOnly();
public abstract boolean forkOnCacheable();
/** Encoded a key */
public abstract void onEncode(SendableRequestItem token, ClientKey key, ClientContext context);
public abstract boolean isEmpty();
@Override
public long getWakeupTime(ClientContext context, long now) {
if(isEmpty()) return -1;
return 0;
}
private transient boolean resumed = false;
public final void onResume(ClientContext context) throws InsertException, ResumeFailedException {
synchronized(this) {
if(resumed) return;
resumed = true;
}
innerOnResume(context);
}
protected abstract void innerOnResume(ClientContext context) throws InsertException, ResumeFailedException;
}