@Override public boolean isPushSupported() { return stream.getSession().isPushEnabled(); }
@Override public void failed(Throwable x) { if (stream != null) { stream.close(); stream.getSession().removeStream(stream); } super.failed(x); }
@Override public void failed(Throwable x) { if (stream != null) { stream.close(); stream.getSession().removeStream(stream); } super.failed(x); }
private void sendDataFrame(ByteBuffer content, boolean lastContent, boolean endStream, Callback callback) { if (LOG.isDebugEnabled()) { LOG.debug("HTTP2 Response #{}/{}: {} content bytes{}", stream.getId(), Integer.toHexString(stream.getSession().hashCode()), content.remaining(), lastContent ? " (last chunk)" : ""); } DataFrame frame = new DataFrame(stream.getId(), content, endStream); stream.data(frame, callback); }
private void sendHeadersFrame(MetaData.Response info, boolean endStream, Callback callback) { if (LOG.isDebugEnabled()) { LOG.debug("HTTP2 Response #{}/{}:{}{} {}{}{}", stream.getId(), Integer.toHexString(stream.getSession().hashCode()), System.lineSeparator(), HttpVersion.HTTP_2, info.getStatus(), System.lineSeparator(), info.getFields()); } HeadersFrame frame = new HeadersFrame(stream.getId(), info, null, endStream); stream.headers(frame, callback); }
private void sendTrailersFrame(MetaData metaData, Callback callback) { if (LOG.isDebugEnabled()) { LOG.debug("HTTP2 Response #{}/{}: trailers", stream.getId(), Integer.toHexString(stream.getSession().hashCode())); } HeadersFrame frame = new HeadersFrame(stream.getId(), metaData, null, true); stream.headers(frame, callback); }
@Override public void abort(Throwable failure) { IStream stream = this.stream; if (LOG.isDebugEnabled()) LOG.debug("HTTP2 Response #{}/{} aborted", stream == null ? -1 : stream.getId(), stream == null ? -1 : Integer.toHexString(stream.getSession().hashCode())); if (stream != null) stream.reset(new ResetFrame(stream.getId(), ErrorCode.INTERNAL_ERROR.code), Callback.NOOP); }
@Override public void succeeded() { boolean commit; Callback callback = null; synchronized (this) { commit = this.commit; if (state == State.WRITING) { this.state = State.IDLE; callback = this.callback; this.callback = null; this.commit = false; } } if (LOG.isDebugEnabled()) LOG.debug("HTTP2 Response #{}/{} {} {}", stream.getId(), Integer.toHexString(stream.getSession().hashCode()), commit ? "commit" : "flush", callback == null ? "failure" : "success"); if (callback != null) callback.succeeded(); }
private boolean onIdleTimeout(Throwable failure) { boolean result; Callback callback = null; synchronized (this) { // Ignore idle timeouts if not writing, // as the application may be suspended. result = state == State.WRITING; if (result) { this.state = State.TIMEOUT; callback = this.callback; this.callback = null; this.failure = failure; } } if (LOG.isDebugEnabled()) LOG.debug(String.format("HTTP2 Response #%d/%h idle timeout", stream.getId(), stream.getSession()), failure); if (result) callback.failed(failure); return result; } }
@Override public void close() { IStream stream = getStream(); if (LOG.isDebugEnabled()) LOG.debug("HTTP2 Request #{}/{} rejected", stream.getId(), Integer.toHexString(stream.getSession().hashCode())); stream.reset(new ResetFrame(stream.getId(), ErrorCode.ENHANCE_YOUR_CALM_ERROR.code), Callback.NOOP); // Consume the existing queued data frames to // avoid stalling the session flow control. consumeInput(); } }
@Override public void failed(Throwable failure) { boolean commit; Callback callback = null; synchronized (this) { commit = this.commit; // Only fail pending writes, as we // may need to write an error page. if (state == State.WRITING) { this.state = State.FAILED; callback = this.callback; this.callback = null; this.failure = failure; } } if (LOG.isDebugEnabled()) LOG.debug(String.format("HTTP2 Response #%d/%h %s %s", stream.getId(), stream.getSession(), commit ? "commit" : "flush", callback == null ? "ignored" : "failed"), failure); if (callback != null) callback.failed(failure); }
@Override public void onDataSending(IStream stream, int length) { if (length == 0) return; ISession session = stream.getSession(); int oldSessionWindow = session.updateSendWindow(-length); int newSessionWindow = oldSessionWindow - length; if (LOG.isDebugEnabled()) LOG.debug("Sending, session send window {} -> {} for {}", oldSessionWindow, newSessionWindow, session); if (newSessionWindow <= 0) onSessionStalled(session); int oldStreamWindow = stream.updateSendWindow(-length); int newStreamWindow = oldStreamWindow - length; if (LOG.isDebugEnabled()) LOG.debug("Sending, stream send window {} -> {} for {}", oldStreamWindow, newStreamWindow, stream); if (newStreamWindow <= 0) onStreamStalled(stream); }
@Override public void onDataSending(IStream stream, int length) { if (length == 0) return; ISession session = stream.getSession(); int oldSessionWindow = session.updateSendWindow(-length); int newSessionWindow = oldSessionWindow - length; if (LOG.isDebugEnabled()) LOG.debug("Sending, session send window {} -> {} for {}", oldSessionWindow, newSessionWindow, session); if (newSessionWindow <= 0) onSessionStalled(session); int oldStreamWindow = stream.updateSendWindow(-length); int newStreamWindow = oldStreamWindow - length; if (LOG.isDebugEnabled()) LOG.debug("Sending, stream send window {} -> {} for {}", oldStreamWindow, newStreamWindow, stream); if (newStreamWindow <= 0) onStreamStalled(stream); }
@Override public void push(final MetaData.Request request) { if (!stream.getSession().isPushEnabled()) { if (LOG.isDebugEnabled()) LOG.debug("HTTP/2 Push disabled for {}", request); return; } if (LOG.isDebugEnabled()) LOG.debug("HTTP/2 Push {}", request); stream.push(new PushPromiseFrame(stream.getId(), 0, request), new Promise<Stream>() { @Override public void succeeded(Stream pushStream) { connection.push(connector, (IStream)pushStream, request); } @Override public void failed(Throwable x) { if (LOG.isDebugEnabled()) LOG.debug("Could not push " + request, x); } }, new Stream.Listener.Adapter()); // TODO: handle reset from the client ? }