DefaultClientRequestContext extends NonWrappingRequestContext implements ClientRequestContext { private String toStringSlow(@Nullable Channel ch, @Nullable RequestLogAccess parent) { final String creqId = id().shortText(); final String preqId = parent != null ? parent.context().id().shortText() : null; final String sreqId = root() != null ? root().id().shortText() : null; final String chanId = ch != null ? ch.id().asShortText() : null; final String proto = sessionProtocol().uriText(); final String authority = endpoint != null ? endpoint.authority() : "UNKNOWN"; final String path = path(); final String method = method().name(); final StringBuilder buf = TemporaryThreadLocals.get().stringBuilder(); buf.append("[creqId=").append(creqId); if (parent != null) { buf.append(", preqId=").append(preqId); } if (sreqId != null) { buf.append(", sreqId=").append(sreqId); } if (ch != null) { buf.append(", chanId=").append(chanId) .append(", laddr="); TextFormatter.appendSocketAddress(buf, ch.localAddress()); buf.append(", raddr="); TextFormatter.appendSocketAddress(buf, ch.remoteAddress()); } buf.append("][") .append(proto).append(": .append(']'); return buf.toString(); } DefaultClientRequestContext(
            EventLoop eventLoop, MeterRegistry meterRegistry, SessionProtocol sessionProtocol,
            RequestId id, HttpMethod method, String path, @Nullable String query, @Nullable String fragment,
            ClientOptions options, @Nullable HttpRequest req, @Nullable RpcRequest rpcReq,
            TimeoutScheduler responseTimeoutScheduler,
            long requestStartTimeNanos, long requestStartTimeMicros);  DefaultClientRequestContext(
            MeterRegistry meterRegistry, SessionProtocol sessionProtocol,
            RequestId id, HttpMethod method, String path, @Nullable String query, @Nullable String fragment,
            ClientOptions options, @Nullable HttpRequest req, @Nullable RpcRequest rpcReq,
            long requestStartTimeNanos, long requestStartTimeMicros); private  DefaultClientRequestContext(
            @Nullable EventLoop eventLoop, MeterRegistry meterRegistry,
            SessionProtocol sessionProtocol, RequestId id, HttpMethod method, String path,
            @Nullable String query, @Nullable String fragment, ClientOptions options,
            @Nullable HttpRequest req, @Nullable RpcRequest rpcReq,
            @Nullable ServiceRequestContext root, @Nullable TimeoutScheduler responseTimeoutScheduler,
            long requestStartTimeNanos, long requestStartTimeMicros); private  DefaultClientRequestContext(DefaultClientRequestContext ctx,
                                        RequestId id,
                                        @Nullable HttpRequest req,
                                        @Nullable RpcRequest rpcReq,
                                        @Nullable Endpoint endpoint); CompletableFuture<Boolean> init(EndpointGroup endpointGroup); @Nullable @Override ServiceRequestContext root(); @Override ClientRequestContext newDerivedContext(RequestId id,
                                                  @Nullable HttpRequest req,
                                                  @Nullable RpcRequest rpcReq,
                                                  @Nullable Endpoint endpoint); @Override ContextAwareEventLoop eventLoop(); @Override ByteBufAllocator alloc(); @Nullable @Override SSLSession sslSession(); @Override ClientOptions options(); @Override EndpointGroup endpointGroup(); @Override Endpoint endpoint(); @Override @Nullable String fragment(); @Override long writeTimeoutMillis(); @Override void setWriteTimeoutMillis(long writeTimeoutMillis); @Override void setWriteTimeout(Duration writeTimeout); @Override long responseTimeoutMillis(); @Override void clearResponseTimeout(); @Override void setResponseTimeoutMillis(TimeoutMode mode, long responseTimeoutMillis); @Override void setResponseTimeout(TimeoutMode mode, Duration responseTimeout); @Override long maxResponseLength(); @Override void setMaxResponseLength(long maxResponseLength); @Override HttpHeaders additionalRequestHeaders(); @Override void setAdditionalRequestHeader(CharSequence name, Object value); @Override void addAdditionalRequestHeader(CharSequence name, Object value); @Override void mutateAdditionalRequestHeaders(Consumer<HttpHeadersBuilder> mutator); @Override RequestLogAccess log(); @Override RequestLogBuilder logBuilder(); @Override void timeoutNow(); @Override boolean isTimedOut(); @Override CompletableFuture<Void> whenResponseTimingOut(); @Override CompletableFuture<Void> whenResponseTimedOut(); @Override String toString();  }
@Test void testToStringSlow() { final HttpRequest req = HttpRequest.of(HttpMethod.GET, "/"); final DefaultClientRequestContext ctxWithChannel = (DefaultClientRequestContext) ClientRequestContext.of(req); final DefaultClientRequestContext ctxWithNoChannel = newContext(); assertThat(ctxWithNoChannel.channel()).isNull(); final String strWithNoChannel = ctxWithNoChannel.toString(); assertThat(strWithNoChannel).doesNotContain("chanId="); assertThat(ctxWithNoChannel.toString()).isSameAs(strWithNoChannel); ctxWithNoChannel.logBuilder().session(ctxWithChannel.channel(), ctxWithChannel.sessionProtocol(), null); final String strWithChannel = ctxWithNoChannel.toString(); assertThat(strWithChannel).contains("chanId="); assertThat(ctxWithNoChannel.toString()).isSameAs(strWithChannel); assertThat(ctxWithNoChannel.log().parent()).isNull(); final String strWithNoParentLog = ctxWithNoChannel.toString(); assertThat(strWithNoParentLog).doesNotContain("preqId="); assertThat(ctxWithNoChannel.toString()).isSameAs(strWithNoParentLog); ctxWithChannel.logBuilder().addChild(ctxWithNoChannel.log()); final String strWithParentLog = ctxWithNoChannel.toString(); assertThat(strWithParentLog).contains("preqId="); assertThat(ctxWithNoChannel.toString()).isSameAs(strWithParentLog); }