diff --git a/annotation-processor/src/main/java/com/linecorp/armeria/server/annotation/processor/DocumentationProcessor.java b/annotation-processor/src/main/java/com/linecorp/armeria/server/annotation/processor/DocumentationProcessor.java index 9530a6a6139..6f9b9387f78 100644 --- a/annotation-processor/src/main/java/com/linecorp/armeria/server/annotation/processor/DocumentationProcessor.java +++ b/annotation-processor/src/main/java/com/linecorp/armeria/server/annotation/processor/DocumentationProcessor.java @@ -38,6 +38,7 @@ import javax.lang.model.SourceVersion; import javax.lang.model.element.ElementKind; import javax.lang.model.element.ExecutableElement; +import javax.lang.model.element.QualifiedNameable; import javax.lang.model.element.TypeElement; import javax.lang.model.element.VariableElement; import javax.tools.Diagnostic.Kind; @@ -148,7 +149,9 @@ private void processAnnotation(TypeElement annotationElement, RoundEnvironment r } private void processMethod(ExecutableElement method) throws IOException { - final String className = ((TypeElement) method.getEnclosingElement()).getQualifiedName().toString(); + final QualifiedNameable enclosingElement = (QualifiedNameable) method.getEnclosingElement(); + assert enclosingElement != null; + final String className = enclosingElement.getQualifiedName().toString(); final Properties properties = readProperties(className); final String docComment = processingEnv.getElementUtils().getDocComment(method); if (docComment == null || !docComment.contains("@param")) { diff --git a/brave/brave6/src/main/java/com/linecorp/armeria/common/brave/RequestContextCurrentTraceContext.java b/brave/brave6/src/main/java/com/linecorp/armeria/common/brave/RequestContextCurrentTraceContext.java index 429a698ebca..7029bb413a4 100644 --- a/brave/brave6/src/main/java/com/linecorp/armeria/common/brave/RequestContextCurrentTraceContext.java +++ b/brave/brave6/src/main/java/com/linecorp/armeria/common/brave/RequestContextCurrentTraceContext.java @@ -174,7 +174,7 @@ public Scope newScope(@Nullable TraceContext currentSpan) { @UnstableApi @Override - public Scope decorateScope(TraceContext context, Scope scope) { + public Scope decorateScope(@Nullable TraceContext context, Scope scope) { // If a `Scope` is decorated, `ScopeDecorator`s populate some contexts as such as MDC, which are stored // to a thread-local. The activated contexts will be removed when `decoratedScope.close()` is called. // If `Scope.NOOP` is specified, CurrentTraceContext.decorateScope() performs nothing. diff --git a/brave/brave6/src/main/java/com/linecorp/armeria/internal/common/brave/TraceContextUtil.java b/brave/brave6/src/main/java/com/linecorp/armeria/internal/common/brave/TraceContextUtil.java index 67f94a5fc62..ad3f5890b52 100644 --- a/brave/brave6/src/main/java/com/linecorp/armeria/internal/common/brave/TraceContextUtil.java +++ b/brave/brave6/src/main/java/com/linecorp/armeria/internal/common/brave/TraceContextUtil.java @@ -39,7 +39,7 @@ public static TraceContext traceContext(RequestContext ctx) { return ctx.attr(TRACE_CONTEXT_KEY); } - public static void setTraceContext(RequestContext ctx, TraceContext traceContext) { + public static void setTraceContext(RequestContext ctx, @Nullable TraceContext traceContext) { ctx.setAttr(TRACE_CONTEXT_KEY, traceContext); } diff --git a/build.gradle b/build.gradle index 0d84aa0a092..2a28be232be 100644 --- a/build.gradle +++ b/build.gradle @@ -186,15 +186,12 @@ configure(projectsWithFlags('java')) { tasks.withType(JavaCompile) { options.errorprone.excludedPaths = '.*/gen-src/.*' options.errorprone.nullaway { - if (name.toLowerCase().contains("test")) { - // Disable NullAway for tests for now. + if (name.contains("Test") || name.contains("Jmh")) { + // Disable NullAway for tests and benchmarks for now. disable() } else if (name.matches(/compileJava[0-9]+.*/)) { // Disable MR-JAR classes which seem to confuse NullAway and break the build. disable() - } else if (project != project(':core')) { - // TODO(trustin): Enable NullAway for all projects once we fix all violations. - warn() } else { error() assertsEnabled = true diff --git a/consul/src/main/java/com/linecorp/armeria/internal/consul/HealthClient.java b/consul/src/main/java/com/linecorp/armeria/internal/consul/HealthClient.java index 1b6ec8d3594..a650643983b 100644 --- a/consul/src/main/java/com/linecorp/armeria/internal/consul/HealthClient.java +++ b/consul/src/main/java/com/linecorp/armeria/internal/consul/HealthClient.java @@ -110,6 +110,16 @@ CompletableFuture> healthyEndpoints(String serviceName, @Nullable @Nullable private static Endpoint toEndpoint(HealthService healthService) { + if (healthService.service == null) { + return null; + } + if (healthService.node == null) { + return null; + } + + assert healthService.service != null; + assert healthService.node != null; + if (!Strings.isNullOrEmpty(healthService.service.address)) { return Endpoint.of(healthService.service.address, healthService.service.port); } else if (!Strings.isNullOrEmpty(healthService.node.address)) { @@ -122,9 +132,11 @@ private static Endpoint toEndpoint(HealthService healthService) { @JsonIgnoreProperties(ignoreUnknown = true) @JsonInclude(Include.NON_NULL) private static final class HealthService { + @Nullable @JsonProperty("Node") Node node; + @Nullable @JsonProperty("Service") Service service; } @@ -132,21 +144,27 @@ private static final class HealthService { @JsonIgnoreProperties(ignoreUnknown = true) @JsonInclude(Include.NON_NULL) private static final class Node { + @Nullable @JsonProperty("ID") String id; + @Nullable @JsonProperty("Node") String node; + @Nullable @JsonProperty("Address") String address; + @Nullable @JsonProperty("Datacenter") String datacenter; + @Nullable @JsonProperty("TaggedAddresses") Object taggedAddresses; + @Nullable @JsonProperty("Meta") Map meta; } @@ -154,27 +172,34 @@ private static final class Node { @JsonIgnoreProperties(ignoreUnknown = true) @JsonInclude(Include.NON_NULL) public static final class Service { + @Nullable @JsonProperty("ID") String id; + @Nullable @JsonProperty("Service") String service; + @Nullable @JsonProperty("Tags") String[] tags; + @Nullable @JsonProperty("Address") String address; + @Nullable @JsonProperty("TaggedAddresses") Object taggedAddresses; + @Nullable @JsonProperty("Meta") Map meta; @JsonProperty("Port") int port; + @Nullable @JsonProperty("Weights") Map weights; } diff --git a/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaConfigurationUtil.java b/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaConfigurationUtil.java index 6559c47e698..1833209b6ca 100644 --- a/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaConfigurationUtil.java +++ b/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaConfigurationUtil.java @@ -127,7 +127,10 @@ static void configureServer(ServerBuilder serverBuilder, ArmeriaSettings setting } if (settings.getPorts().isEmpty()) { - serverBuilder.port(new ServerPort(DEFAULT_PORT.getPort(), DEFAULT_PORT.getProtocols())); + final int port = DEFAULT_PORT.getPort(); + final List protocols = DEFAULT_PORT.getProtocols(); + assert protocols != null; + serverBuilder.port(new ServerPort(port, protocols)); } else { configurePorts(serverBuilder, settings.getPorts()); } @@ -445,8 +448,9 @@ private static void configureAccessLog(ServerBuilder serverBuilder, AccessLog ac } else if ("combined".equals(accessLog.getType())) { serverBuilder.accessLogWriter(AccessLogWriter.combined(), true); } else if ("custom".equals(accessLog.getType())) { - serverBuilder - .accessLogWriter(AccessLogWriter.custom(accessLog.getFormat()), true); + final String format = accessLog.getFormat(); + assert format != null; + serverBuilder.accessLogWriter(AccessLogWriter.custom(format), true); } } diff --git a/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaServerFactory.java b/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaServerFactory.java index c448f63e881..6bf4868c3b2 100644 --- a/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaServerFactory.java +++ b/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ArmeriaServerFactory.java @@ -64,6 +64,7 @@ class ArmeriaServerFactory extends AbstractServerFactory { public static final String TYPE = "armeria"; private static final Logger logger = LoggerFactory.getLogger(ArmeriaServerFactory.class); + @Nullable @JsonUnwrapped private @Valid ArmeriaSettings armeriaSettings; @@ -80,6 +81,7 @@ class ArmeriaServerFactory extends AbstractServerFactory { @JsonProperty private boolean jerseyEnabled = true; + @Nullable @JsonIgnore public ServerBuilder getServerBuilder() { return serverBuilder; @@ -184,6 +186,7 @@ private ScheduledThreadPoolExecutor newBlockingTaskExecutor() { return blockingTaskExecutor; } + @Nullable ArmeriaSettings getArmeriaSettings() { return armeriaSettings; } diff --git a/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ManagedArmeriaServer.java b/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ManagedArmeriaServer.java index 04aaa97f271..a031b6d27c1 100644 --- a/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ManagedArmeriaServer.java +++ b/dropwizard2/src/main/java/com/linecorp/armeria/dropwizard/ManagedArmeriaServer.java @@ -65,6 +65,7 @@ class ManagedArmeriaServer implements Managed { public void start() throws Exception { logger.trace("Getting Armeria Server Builder"); final ServerBuilder sb = ((ArmeriaServerFactory) serverFactory).getServerBuilder(); + assert sb != null; logger.trace("Calling Server Configurator"); serverConfigurator.configure(sb); server = sb.build(); diff --git a/eureka/src/main/java/com/linecorp/armeria/client/eureka/EurekaEndpointGroup.java b/eureka/src/main/java/com/linecorp/armeria/client/eureka/EurekaEndpointGroup.java index d615d758da1..631817fd1a7 100644 --- a/eureka/src/main/java/com/linecorp/armeria/client/eureka/EurekaEndpointGroup.java +++ b/eureka/src/main/java/com/linecorp/armeria/client/eureka/EurekaEndpointGroup.java @@ -21,6 +21,7 @@ import java.io.IOException; import java.net.URI; import java.util.List; +import java.util.Objects; import java.util.Set; import java.util.StringJoiner; import java.util.concurrent.CompletableFuture; @@ -284,7 +285,7 @@ private static Function> responseConverter( } else if (appName != null) { filter = instanceInfo -> appName.equals(instanceInfo.getAppName()); } else { - filter = instanceInfo -> instanceId.equals(instanceInfo.getInstanceId()); + filter = instanceInfo -> Objects.equals(instanceId, instanceInfo.getInstanceId()); } } final StringJoiner joiner = new StringJoiner(","); diff --git a/eureka/src/main/java/com/linecorp/armeria/internal/common/eureka/InstanceInfo.java b/eureka/src/main/java/com/linecorp/armeria/internal/common/eureka/InstanceInfo.java index a8edb005be8..22d18108f1a 100644 --- a/eureka/src/main/java/com/linecorp/armeria/internal/common/eureka/InstanceInfo.java +++ b/eureka/src/main/java/com/linecorp/armeria/internal/common/eureka/InstanceInfo.java @@ -43,6 +43,7 @@ public final class InstanceInfo { private static final Logger logger = LoggerFactory.getLogger(InstanceInfo.class); + @Nullable private final String instanceId; @Nullable diff --git a/eureka/src/main/java/com/linecorp/armeria/server/eureka/EurekaUpdatingListener.java b/eureka/src/main/java/com/linecorp/armeria/server/eureka/EurekaUpdatingListener.java index 712c044b3ba..d5f1a93f13b 100644 --- a/eureka/src/main/java/com/linecorp/armeria/server/eureka/EurekaUpdatingListener.java +++ b/eureka/src/main/java/com/linecorp/armeria/server/eureka/EurekaUpdatingListener.java @@ -133,6 +133,7 @@ public static EurekaUpdatingListenerBuilder builder( private final EurekaWebClient client; private final InstanceInfo initialInstanceInfo; + @Nullable private InstanceInfo instanceInfo; @Nullable private volatile ScheduledFuture heartBeatFuture; @@ -335,8 +336,9 @@ public void serverStopping(Server server) throws Exception { if (heartBeatFuture != null) { heartBeatFuture.cancel(false); } + final InstanceInfo instanceInfo = this.instanceInfo; final String appName = this.appName; - if (appName != null) { + if (instanceInfo != null && appName != null) { final String instanceId = instanceInfo.getInstanceId(); assert instanceId != null; client.cancel(appName, instanceId).aggregate().handle((res, cause) -> { diff --git a/graphql-protocol/src/main/java/com/linecorp/armeria/common/graphql/protocol/DefaultGraphqlRequest.java b/graphql-protocol/src/main/java/com/linecorp/armeria/common/graphql/protocol/DefaultGraphqlRequest.java index b102d5e54a0..c8139d6ae6c 100644 --- a/graphql-protocol/src/main/java/com/linecorp/armeria/common/graphql/protocol/DefaultGraphqlRequest.java +++ b/graphql-protocol/src/main/java/com/linecorp/armeria/common/graphql/protocol/DefaultGraphqlRequest.java @@ -44,6 +44,7 @@ public String query() { return query; } + @Nullable @Override public String operationName() { return operationName; diff --git a/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlErrorHandler.java b/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlErrorHandler.java index 33fde0a1242..b73326f1039 100644 --- a/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlErrorHandler.java +++ b/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlErrorHandler.java @@ -22,6 +22,8 @@ import javax.annotation.Nonnull; +import com.google.common.collect.ImmutableMap; + import com.linecorp.armeria.common.HttpResponse; import com.linecorp.armeria.common.HttpStatus; import com.linecorp.armeria.common.MediaType; @@ -42,7 +44,7 @@ enum DefaultGraphqlErrorHandler implements GraphqlErrorHandler { public HttpResponse handle( ServiceRequestContext ctx, ExecutionInput input, - ExecutionResult result, + @Nullable ExecutionResult result, @Nullable Throwable cause) { final MediaType produceType = GraphqlUtil.produceType(ctx.request().headers()); @@ -60,11 +62,11 @@ public HttpResponse handle( return HttpResponse.ofJson(HttpStatus.INTERNAL_SERVER_ERROR, produceType, specification); } - if (result.getErrors().stream().anyMatch(ValidationError.class::isInstance)) { + if (result != null && result.getErrors().stream().anyMatch(ValidationError.class::isInstance)) { return HttpResponse.ofJson(HttpStatus.BAD_REQUEST, produceType, result.toSpecification()); } - return HttpResponse.ofJson(produceType, result.toSpecification()); + return HttpResponse.ofJson(produceType, result != null ? result.toSpecification() : ImmutableMap.of()); } private static Map toSpecification(Throwable cause) { diff --git a/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlService.java b/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlService.java index f225af0edfa..d1edffc6a35 100644 --- a/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlService.java +++ b/graphql/src/main/java/com/linecorp/armeria/server/graphql/DefaultGraphqlService.java @@ -139,7 +139,9 @@ private HttpResponse execute( })); } catch (Throwable cause) { cause = Exceptions.peel(cause); - return errorHandler.handle(ctx, input, null, cause); + final HttpResponse res = errorHandler.handle(ctx, input, null, cause); + assert res != null : "DefaultGraphqlService.handle() returned null?"; + return res; } } diff --git a/graphql/src/main/java/com/linecorp/armeria/server/graphql/GraphqlWSSubProtocol.java b/graphql/src/main/java/com/linecorp/armeria/server/graphql/GraphqlWSSubProtocol.java index b7c0c2691a2..7188f48891d 100644 --- a/graphql/src/main/java/com/linecorp/armeria/server/graphql/GraphqlWSSubProtocol.java +++ b/graphql/src/main/java/com/linecorp/armeria/server/graphql/GraphqlWSSubProtocol.java @@ -374,6 +374,7 @@ private static void writeError(WebSocketWriter out, String operationId, Throwabl "id", operationId, "payload", ImmutableList.of( new GraphQLError() { + @Nullable @Override public String getMessage() { return t.getMessage(); @@ -430,4 +431,3 @@ public Throwable fillInStackTrace() { } } } - diff --git a/grpc-protocol/src/main/java/com/linecorp/armeria/common/grpc/protocol/DeframedMessage.java b/grpc-protocol/src/main/java/com/linecorp/armeria/common/grpc/protocol/DeframedMessage.java index 2ec4a959d55..1a0b13bce89 100644 --- a/grpc-protocol/src/main/java/com/linecorp/armeria/common/grpc/protocol/DeframedMessage.java +++ b/grpc-protocol/src/main/java/com/linecorp/armeria/common/grpc/protocol/DeframedMessage.java @@ -124,6 +124,7 @@ public void close() { if (buf != null) { buf.release(); } else { + assert stream != null; try { stream.close(); } catch (IOException e) { diff --git a/grpc-protocol/src/main/java/com/linecorp/armeria/server/grpc/protocol/AbstractUnsafeUnaryGrpcService.java b/grpc-protocol/src/main/java/com/linecorp/armeria/server/grpc/protocol/AbstractUnsafeUnaryGrpcService.java index f57380f8983..4aa8515eb14 100644 --- a/grpc-protocol/src/main/java/com/linecorp/armeria/server/grpc/protocol/AbstractUnsafeUnaryGrpcService.java +++ b/grpc-protocol/src/main/java/com/linecorp/armeria/server/grpc/protocol/AbstractUnsafeUnaryGrpcService.java @@ -142,6 +142,7 @@ protected final HttpResponse doPost(ServiceRequestContext ctx, HttpRequest req) final HttpData content = framer.writePayload(responseMessage); final ResponseHeaders responseHeaders = RESPONSE_HEADERS_MAP.get( serializationFormat); + assert responseHeaders != null; if (UnaryGrpcSerializationFormats.isGrpcWeb(serializationFormat)) { // Send trailer as a part of the body for gRPC-web. final HttpData serializedTrailers = framer.writePayload( diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ArmeriaChannel.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ArmeriaChannel.java index 248eb034b1d..8d28796ac7a 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ArmeriaChannel.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ArmeriaChannel.java @@ -239,6 +239,9 @@ private DefaultClientRequestContext newContext(HttpMethod method, HttpReq assert reqTarget != null : path; RequestTargetCache.putForClient(path, reqTarget); + final RequestOptions requestOptions = REQUEST_OPTIONS_MAP.get(methodDescriptor.getType()); + assert requestOptions != null; + return new DefaultClientRequestContext( meterRegistry, sessionProtocol, @@ -248,7 +251,7 @@ private DefaultClientRequestContext newContext(HttpMethod method, HttpReq options(), req, null, - REQUEST_OPTIONS_MAP.get(methodDescriptor.getType()), + requestOptions, System.nanoTime(), SystemInfo.currentTimeMicros()); } diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/GrpcClientFactory.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/GrpcClientFactory.java index b9ba5626a82..1e04f8db90d 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/GrpcClientFactory.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/GrpcClientFactory.java @@ -47,6 +47,8 @@ import com.linecorp.armeria.client.grpc.GrpcClientStubFactory; import com.linecorp.armeria.client.grpc.protocol.UnaryGrpcClient; import com.linecorp.armeria.client.retry.RetryingClient; +import com.linecorp.armeria.common.HttpResponse; +import com.linecorp.armeria.common.HttpStatus; import com.linecorp.armeria.common.Scheme; import com.linecorp.armeria.common.SerializationFormat; import com.linecorp.armeria.common.SessionProtocol; @@ -200,7 +202,7 @@ private static ClientBuilderParams addTrailersExtractor( originalDecoration.decorators(); boolean foundRetryingClient = false; - final HttpClient noopClient = (ctx, req) -> null; + final HttpClient noopClient = (ctx, req) -> HttpResponse.of(HttpStatus.OK); for (Function decorator : decorators) { final HttpClient decorated = decorator.apply(noopClient); if (decorated instanceof RetryingClient) { diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/JavaGrpcClientStubFactory.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/JavaGrpcClientStubFactory.java index 5a01344104b..998a7ae681d 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/JavaGrpcClientStubFactory.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/JavaGrpcClientStubFactory.java @@ -22,6 +22,7 @@ import java.lang.reflect.Method; import com.linecorp.armeria.client.grpc.GrpcClientStubFactory; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.Exceptions; import io.grpc.Channel; @@ -32,6 +33,7 @@ */ public final class JavaGrpcClientStubFactory implements GrpcClientStubFactory { + @Nullable @Override public ServiceDescriptor findServiceDescriptor(Class clientType) { final String clientTypeName = clientType.getName(); @@ -59,6 +61,7 @@ public ServiceDescriptor findServiceDescriptor(Class clientType) { @Override public Object newClientStub(Class clientType, Channel channel) { final Method stubFactoryMethod = GrpcClientFactoryUtil.findStubFactoryMethod(clientType); + assert stubFactoryMethod != null : "No stub factory method found for " + clientType; try { return stubFactoryMethod.invoke(null, channel); } catch (IllegalAccessException | InvocationTargetException e) { diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/NullGrpcClientStubFactory.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/NullGrpcClientStubFactory.java index e0cfde8d555..031a28ac1ef 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/NullGrpcClientStubFactory.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/NullGrpcClientStubFactory.java @@ -17,7 +17,6 @@ package com.linecorp.armeria.internal.client.grpc; import com.linecorp.armeria.client.grpc.GrpcClientStubFactory; -import com.linecorp.armeria.common.annotation.Nullable; import io.grpc.Channel; import io.grpc.ServiceDescriptor; @@ -31,7 +30,6 @@ public ServiceDescriptor findServiceDescriptor(Class clientType) { throw new UnsupportedOperationException(); } - @Nullable @Override public Object newClientStub(Class clientType, Channel channel) { throw new UnsupportedOperationException(); diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ReactorGrpcClientStubFactory.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ReactorGrpcClientStubFactory.java index 682beee88f3..e9852df8362 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ReactorGrpcClientStubFactory.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ReactorGrpcClientStubFactory.java @@ -22,6 +22,7 @@ import java.lang.reflect.Method; import com.linecorp.armeria.client.grpc.GrpcClientStubFactory; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.Exceptions; import io.grpc.Channel; @@ -32,6 +33,7 @@ */ public final class ReactorGrpcClientStubFactory implements GrpcClientStubFactory { + @Nullable @Override public ServiceDescriptor findServiceDescriptor(Class clientType) { final String clientTypeName = clientType.getName(); @@ -53,6 +55,7 @@ public ServiceDescriptor findServiceDescriptor(Class clientType) { @Override public Object newClientStub(Class clientType, Channel channel) { final Method stubFactoryMethod = GrpcClientFactoryUtil.findStubFactoryMethod(clientType); + assert stubFactoryMethod != null : "No stub factory method found for " + clientType; try { return stubFactoryMethod.invoke(null, channel); } catch (IllegalAccessException | InvocationTargetException e) { diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ScalaPbGrpcClientStubFactory.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ScalaPbGrpcClientStubFactory.java index d84b2ad1647..8e9657c25e1 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ScalaPbGrpcClientStubFactory.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ScalaPbGrpcClientStubFactory.java @@ -22,6 +22,7 @@ import java.lang.reflect.Method; import com.linecorp.armeria.client.grpc.GrpcClientStubFactory; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.Exceptions; import io.grpc.Channel; @@ -32,6 +33,7 @@ */ public final class ScalaPbGrpcClientStubFactory implements GrpcClientStubFactory { + @Nullable @Override public ServiceDescriptor findServiceDescriptor(Class clientType) { final Class stubClass = clientType.getEnclosingClass(); @@ -50,6 +52,7 @@ public ServiceDescriptor findServiceDescriptor(Class clientType) { @Override public Object newClientStub(Class clientType, Channel channel) { final Method stubFactoryMethod = GrpcClientFactoryUtil.findStubFactoryMethod(clientType); + assert stubFactoryMethod != null : "No stub factory method found for " + clientType; try { return stubFactoryMethod.invoke(null, channel); } catch (IllegalAccessException | InvocationTargetException e) { diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ServiceDescriptorResolutionException.java b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ServiceDescriptorResolutionException.java index 23d1e6864c5..eaff46d76eb 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ServiceDescriptorResolutionException.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/client/grpc/ServiceDescriptorResolutionException.java @@ -36,6 +36,6 @@ public ServiceDescriptorResolutionException(String stubFactoryName, Throwable ca @Override public String toString() { - return stubFactoryName + '=' + getCause().toString(); + return stubFactoryName + '=' + getCause(); } } diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/GrpcMessageMarshaller.java b/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/GrpcMessageMarshaller.java index 3b5a23778cf..6a5f73ea09c 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/GrpcMessageMarshaller.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/GrpcMessageMarshaller.java @@ -103,6 +103,7 @@ public ByteBuf serializeRequest(I message) throws IOException { ByteStreams.copy(is, os); } } else { + assert jsonMarshaller != null; jsonMarshaller.serializeMessage(requestMarshaller, message, os); } } @@ -133,10 +134,13 @@ public I deserializeRequest(DeframedMessage message, boolean grpcWebText) throws } } } + + assert messageStream != null; try (InputStream msg = messageStream) { if (isProto) { return method.parseRequest(msg); } else { + assert jsonMarshaller != null; return jsonMarshaller.deserializeMessage(requestMarshaller, msg); } } @@ -157,6 +161,7 @@ public ByteBuf serializeResponse(O message) throws IOException { ByteStreams.copy(is, os); } } else { + assert jsonMarshaller != null; jsonMarshaller.serializeMessage(responseMarshaller, message, os); } } @@ -188,10 +193,13 @@ public O deserializeResponse(DeframedMessage message, boolean grpcWebText) throw } } } + + assert messageStream != null; try (InputStream msg = messageStream) { if (isProto) { return method.parseResponse(msg); } else { + assert jsonMarshaller != null; return jsonMarshaller.deserializeMessage(responseMarshaller, msg); } } @@ -231,6 +239,7 @@ private ByteBuf serializeProto(PrototypeMarshaller marshaller, Message me try (ByteBufOutputStream os = new ByteBufOutputStream(buf)) { @SuppressWarnings("unchecked") final T cast = (T) message; + assert jsonMarshaller != null; jsonMarshaller.serializeMessage(marshaller, cast, os); success = true; } finally { @@ -275,6 +284,7 @@ private Message deserializeProto(PrototypeMarshaller marshaller, ByteBuf } } else { try (ByteBufInputStream is = new ByteBufInputStream(buf, /* releaseOnClose */ false)) { + assert jsonMarshaller != null; return (Message) jsonMarshaller.deserializeMessage(marshaller, is); } } diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/MetadataUtil.java b/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/MetadataUtil.java index e4b75be0e38..2ca8d888645 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/MetadataUtil.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/common/grpc/MetadataUtil.java @@ -33,6 +33,7 @@ import com.linecorp.armeria.common.HttpHeaderNames; import com.linecorp.armeria.common.HttpHeaders; import com.linecorp.armeria.common.HttpHeadersBuilder; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.grpc.protocol.GrpcHeaderNames; import io.grpc.InternalMetadata; @@ -70,8 +71,8 @@ public final class MetadataUtil { * Copies the headers in the gRPC {@link Metadata} to the Armeria {@link HttpHeadersBuilder}. Headers will * be added, without replacing any currently present in the {@link HttpHeaders}. */ - public static void fillHeaders(Metadata metadata, HttpHeadersBuilder builder) { - if (InternalMetadata.headerCount(metadata) == 0) { + public static void fillHeaders(@Nullable Metadata metadata, HttpHeadersBuilder builder) { + if (metadata == null || InternalMetadata.headerCount(metadata) == 0) { return; } diff --git a/grpc/src/main/java/com/linecorp/armeria/internal/server/grpc/AbstractServerCall.java b/grpc/src/main/java/com/linecorp/armeria/internal/server/grpc/AbstractServerCall.java index 9d1b914d54b..de1cc4d974d 100644 --- a/grpc/src/main/java/com/linecorp/armeria/internal/server/grpc/AbstractServerCall.java +++ b/grpc/src/main/java/com/linecorp/armeria/internal/server/grpc/AbstractServerCall.java @@ -522,6 +522,7 @@ private void doSendHeaders(Metadata metadata) { if (compressor != Codec.Identity.NONE || InternalMetadata.headerCount(metadata) > 0) { headers = headers.withMutations(builder -> { if (compressor != Codec.Identity.NONE) { + assert compressor != null; builder.set(GrpcHeaderNames.GRPC_ENCODING, compressor.getMessageEncoding()); } MetadataUtil.fillHeaders(metadata, builder); @@ -548,7 +549,7 @@ protected final HttpData toPayload(O message) throws IOException { } protected final HttpObject responseTrailers(ServiceRequestContext ctx, Status status, - Metadata metadata, boolean trailersOnly) { + @Nullable Metadata metadata, boolean trailersOnly) { final HttpHeadersBuilder defaultTrailers = trailersOnly ? defaultResponseHeaders.toBuilder() : HttpHeaders.builder(); final HttpHeaders trailers = statusToTrailers(ctx, defaultTrailers, status, metadata); @@ -564,7 +565,8 @@ protected final HttpObject responseTrailers(ServiceRequestContext ctx, Status st // Returns ResponseHeaders if headersSent == false or HttpHeaders otherwise. public static HttpHeaders statusToTrailers( - ServiceRequestContext ctx, HttpHeadersBuilder trailersBuilder, Status status, Metadata metadata) { + ServiceRequestContext ctx, HttpHeadersBuilder trailersBuilder, + Status status, @Nullable Metadata metadata) { try { MetadataUtil.fillHeaders(metadata, trailersBuilder); } catch (Exception e) { diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/AbstractUnframedGrpcService.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/AbstractUnframedGrpcService.java index 4970e7f658c..31344b324ca 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/AbstractUnframedGrpcService.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/AbstractUnframedGrpcService.java @@ -63,6 +63,7 @@ import io.grpc.ServerServiceDefinition; import io.grpc.Status; import io.grpc.Status.Code; +import io.netty.buffer.ByteBuf; import io.netty.util.AttributeKey; /** @@ -249,7 +250,9 @@ public void onSubscribe(Subscription subscription) { @Override public void onNext(DeframedMessage message) { // We know that we don't support compression, so this is always a ByteBuf. - HttpData unframedContent = HttpData.wrap(message.buf()); + final ByteBuf buf = message.buf(); + assert buf != null; + HttpData unframedContent = HttpData.wrap(buf); if (responseBodyConverter != null) { unframedContent = responseBodyConverter.apply(unframedContent); } diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/DeferredListener.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/DeferredListener.java index 3f24a173430..a61aaa7bfa2 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/DeferredListener.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/DeferredListener.java @@ -69,6 +69,7 @@ final class DeferredListener extends ServerCall.Listener { } this.delegate = delegate; + assert pendingQueue != null; try { for (;;) { final Consumer> task = pendingQueue.poll(); @@ -142,6 +143,7 @@ private void maybeAddPendingTask(Consumer> task) { } private void addPendingTask(Consumer> task) { + assert pendingQueue != null; pendingQueue.add(task); } diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/FramedGrpcService.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/FramedGrpcService.java index 0ad408da047..ceefac2f1bf 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/FramedGrpcService.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/FramedGrpcService.java @@ -217,10 +217,12 @@ protected HttpResponse doPost(ServiceRequestContext ctx, HttpRequest req) throws final ServerMethodDefinition method = methodDefinition(ctx); if (method == null) { + final ResponseHeaders defaultHeaders = this.defaultHeaders.get(serializationFormat); + assert defaultHeaders != null; return HttpResponse.of( (ResponseHeaders) AbstractServerCall.statusToTrailers( ctx, - defaultHeaders.get(serializationFormat).toBuilder(), + defaultHeaders.toBuilder(), Status.UNIMPLEMENTED.withDescription( "Method not found: " + ctx.config().route().patternString()), new Metadata())); @@ -241,9 +243,11 @@ protected HttpResponse doPost(ServiceRequestContext ctx, HttpRequest req) throws final GrpcExceptionHandlerFunction exceptionHandler = registry.getExceptionHandler(method); assert exceptionHandler != null; final Status status = Status.INVALID_ARGUMENT.withCause(e); + final ResponseHeaders defaultHeaders = this.defaultHeaders.get(serializationFormat); + assert defaultHeaders != null; return HttpResponse.of( (ResponseHeaders) AbstractServerCall.statusToTrailers( - ctx, defaultHeaders.get(serializationFormat).toBuilder(), + ctx, defaultHeaders.toBuilder(), applyExceptionHandler(ctx, exceptionHandler, status, e, metadata), metadata)); } @@ -339,9 +343,14 @@ private AbstractServerCall newServerCall( ServiceRequestContext ctx, HttpRequest req, HttpResponse res, @Nullable CompletableFuture resFuture, SerializationFormat serializationFormat, @Nullable Executor blockingExecutor) { + final MethodDescriptor methodDescriptor = methodDef.getMethodDescriptor(); - final GrpcExceptionHandlerFunction exceptionHandler = registry.getExceptionHandler( - methodDef); + final GrpcExceptionHandlerFunction exceptionHandler = registry.getExceptionHandler(methodDef); + assert exceptionHandler != null; + final GrpcJsonMarshaller jsonMarshaller = jsonMarshallers.get(methodDescriptor.getServiceName()); + final ResponseHeaders defaultHeaders = this.defaultHeaders.get(serializationFormat); + assert defaultHeaders != null; + if (methodDescriptor.getType() == MethodType.UNARY) { assert resFuture != null; return new UnaryServerCall<>( @@ -356,9 +365,9 @@ private AbstractServerCall newServerCall( maxResponseMessageLength, ctx, serializationFormat, - jsonMarshallers.get(methodDescriptor.getServiceName()), + jsonMarshaller, unsafeWrapRequestBuffers, - defaultHeaders.get(serializationFormat), + defaultHeaders, exceptionHandler, blockingExecutor, autoCompression, @@ -375,9 +384,9 @@ private AbstractServerCall newServerCall( maxResponseMessageLength, ctx, serializationFormat, - jsonMarshallers.get(methodDescriptor.getServiceName()), + jsonMarshaller, unsafeWrapRequestBuffers, - defaultHeaders.get(serializationFormat), + defaultHeaders, exceptionHandler, blockingExecutor, autoCompression, @@ -412,6 +421,7 @@ public void serviceAdded(ServiceConfig cfg) { } } + @Nullable @Override public ServerMethodDefinition methodDefinition(ServiceRequestContext ctx) { // method could be set in HttpJsonTranscodingService. diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/GrpcDecoratingService.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/GrpcDecoratingService.java index 6aa73eee97d..25fa68d7d30 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/GrpcDecoratingService.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/GrpcDecoratingService.java @@ -100,6 +100,7 @@ public List services() { return delegate.services(); } + @Nullable @Override public ServerMethodDefinition methodDefinition(ServiceRequestContext ctx) { return delegate.methodDefinition(ctx); diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/HandlerRegistry.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/HandlerRegistry.java index 6044ef4c969..81cb6795459 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/HandlerRegistry.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/HandlerRegistry.java @@ -132,8 +132,10 @@ private HandlerRegistry(List services, return methods.get(methodName); } - String simpleMethodName(MethodDescriptor methodName) { - return simpleMethodNames.get(methodName); + String simpleMethodName(MethodDescriptor methodDescriptor) { + final String simpleMethodName = simpleMethodNames.get(methodDescriptor); + assert simpleMethodName != null : "No simple name found for " + methodDescriptor.getFullMethodName(); + return simpleMethodName; } List services() { diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/HttpJsonTranscodingService.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/HttpJsonTranscodingService.java index 78f804bf00c..10f66fff195 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/HttpJsonTranscodingService.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/HttpJsonTranscodingService.java @@ -506,6 +506,7 @@ private HttpJsonTranscodingService(GrpcService delegate, .contains(HttpJsonTranscodingQueryParamMatchRule.ORIGINAL_FIELD); } + @Nullable @Override public HttpEndpointSpecification httpEndpointSpecification(Route route) { requireNonNull(route, "route"); @@ -537,6 +538,7 @@ public Set routes() { return routes; } + @Nullable @Override public ServerMethodDefinition methodDefinition(ServiceRequestContext ctx) { final TranscodingSpec spec = routeAndSpecs.get(ctx.config().mappedRoute()); diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/JsonUnframedGrpcErrorHandler.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/JsonUnframedGrpcErrorHandler.java index e3b3b7d0137..571d2877510 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/JsonUnframedGrpcErrorHandler.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/JsonUnframedGrpcErrorHandler.java @@ -135,6 +135,7 @@ public HttpResponse handle(ServiceRequestContext ctx, Status status, AggregatedH final String grpcMessage = status.getDescription(); final Throwable cause = responseCause(ctx); final HttpStatus httpStatus = statusMappingFunction.apply(ctx, status, cause); + assert httpStatus != null : "Default statusMappingFunction returned null?"; final HttpHeaders trailers = !response.trailers().isEmpty() ? response.trailers() : response.headers(); final String grpcStatusDetailsBin = trailers.get(GrpcHeaderNames.GRPC_STATUS_DETAILS_BIN); diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/StreamingServerCall.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/StreamingServerCall.java index 61833562348..04a40c999e0 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/StreamingServerCall.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/StreamingServerCall.java @@ -84,7 +84,7 @@ final class StreamingServerCall extends AbstractServerCall ServiceRequestContext ctx, SerializationFormat serializationFormat, @Nullable GrpcJsonMarshaller jsonMarshaller, boolean unsafeWrapRequestBuffers, ResponseHeaders defaultHeaders, - @Nullable GrpcExceptionHandlerFunction exceptionHandler, + GrpcExceptionHandlerFunction exceptionHandler, @Nullable Executor blockingExecutor, boolean autoCompress, boolean useMethodMarshaller) { super(req, method, simpleMethodName, compressorRegistry, decompressorRegistry, res, diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/TextUnframedGrpcErrorHandler.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/TextUnframedGrpcErrorHandler.java index 674703470bb..034c26c6d15 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/TextUnframedGrpcErrorHandler.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/TextUnframedGrpcErrorHandler.java @@ -76,6 +76,7 @@ public HttpResponse handle(ServiceRequestContext ctx, Status status, AggregatedH final String grpcMessage = status.getDescription(); final Throwable cause = responseCause(ctx); final HttpStatus httpStatus = statusMappingFunction.apply(ctx, status, cause); + assert httpStatus != null : "Default statusMappingFunction returned null?"; final ResponseHeaders responseHeaders = ResponseHeaders.builder(httpStatus) .contentType(MediaType.PLAIN_TEXT_UTF_8) .addInt(GrpcHeaderNames.GRPC_STATUS, diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnaryServerCall.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnaryServerCall.java index 6f8516f6d13..1ab5de2adc4 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnaryServerCall.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnaryServerCall.java @@ -70,7 +70,7 @@ final class UnaryServerCall extends AbstractServerCall { ServiceRequestContext ctx, SerializationFormat serializationFormat, @Nullable GrpcJsonMarshaller jsonMarshaller, boolean unsafeWrapRequestBuffers, ResponseHeaders defaultHeaders, - @Nullable GrpcExceptionHandlerFunction exceptionHandler, + GrpcExceptionHandlerFunction exceptionHandler, @Nullable Executor blockingExecutor, boolean autoCompress, boolean useMethodMarshaller) { diff --git a/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnframedGrpcService.java b/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnframedGrpcService.java index d945e368df9..6d0577107bc 100644 --- a/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnframedGrpcService.java +++ b/grpc/src/main/java/com/linecorp/armeria/server/grpc/UnframedGrpcService.java @@ -29,6 +29,7 @@ import com.linecorp.armeria.common.RequestHeaders; import com.linecorp.armeria.common.RequestHeadersBuilder; import com.linecorp.armeria.common.SerializationFormat; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.grpc.GrpcSerializationFormats; import com.linecorp.armeria.common.grpc.protocol.GrpcHeaderNames; import com.linecorp.armeria.common.logging.RequestLogProperty; @@ -73,6 +74,7 @@ final class UnframedGrpcService extends AbstractUnframedGrpcService { checkArgument(delegate.isFramed(), "Decorated service must be a framed GrpcService."); } + @Nullable @Override public ServerMethodDefinition methodDefinition(ServiceRequestContext ctx) { return delegate.methodDefinition(ctx); diff --git a/grpc/src/test/java/com/linecorp/armeria/server/grpc/DeferredListenerTest.java b/grpc/src/test/java/com/linecorp/armeria/server/grpc/DeferredListenerTest.java index 47d9ea0f1c5..f81c7aa3f22 100644 --- a/grpc/src/test/java/com/linecorp/armeria/server/grpc/DeferredListenerTest.java +++ b/grpc/src/test/java/com/linecorp/armeria/server/grpc/DeferredListenerTest.java @@ -37,6 +37,7 @@ import com.linecorp.armeria.common.HttpRequest; import com.linecorp.armeria.common.HttpResponse; import com.linecorp.armeria.common.ResponseHeaders; +import com.linecorp.armeria.common.grpc.GrpcExceptionHandlerFunction; import com.linecorp.armeria.common.grpc.GrpcSerializationFormats; import com.linecorp.armeria.server.ServiceRequestContext; @@ -112,7 +113,8 @@ private static UnaryServerCall newServerCall( DecompressorRegistry.getDefaultInstance(), HttpResponse.streaming(), new CompletableFuture<>(), 0, 0, ctx, GrpcSerializationFormats.PROTO, null, false, - ResponseHeaders.of(200), null, blockingTaskExecutor, false, false); + ResponseHeaders.of(200), GrpcExceptionHandlerFunction.of(), + blockingTaskExecutor, false, false); } private static class TestListener extends ServerCall.Listener { diff --git a/grpc/src/test/java/com/linecorp/armeria/server/grpc/StreamingServerCallTest.java b/grpc/src/test/java/com/linecorp/armeria/server/grpc/StreamingServerCallTest.java index 401fefb2725..7e3a6130bb4 100644 --- a/grpc/src/test/java/com/linecorp/armeria/server/grpc/StreamingServerCallTest.java +++ b/grpc/src/test/java/com/linecorp/armeria/server/grpc/StreamingServerCallTest.java @@ -54,6 +54,7 @@ import com.linecorp.armeria.common.HttpResponseWriter; import com.linecorp.armeria.common.HttpStatus; import com.linecorp.armeria.common.ResponseHeaders; +import com.linecorp.armeria.common.grpc.GrpcExceptionHandlerFunction; import com.linecorp.armeria.common.grpc.GrpcSerializationFormats; import com.linecorp.armeria.common.grpc.protocol.DeframedMessage; import com.linecorp.armeria.common.util.EventLoopGroups; @@ -296,7 +297,7 @@ void deferResponseHeaders_streaming_nonResponseMessage() { ResponseHeaders.builder(HttpStatus.OK) .contentType(GrpcSerializationFormats.PROTO.mediaType()) .build(), - /* exceptionMappings */ null, + GrpcExceptionHandlerFunction.of(), /* blockingExecutor */ null, false, false); @@ -366,7 +367,7 @@ private StreamingServerCall newServerCall(HttpRes ResponseHeaders.builder(HttpStatus.OK) .contentType(GrpcSerializationFormats.PROTO.mediaType()) .build(), - /* exceptionMappings */ null, + GrpcExceptionHandlerFunction.of(), /* blockingExecutor */ null, false, false); diff --git a/grpc/src/test/java/com/linecorp/armeria/server/grpc/UnaryServerCallTest.java b/grpc/src/test/java/com/linecorp/armeria/server/grpc/UnaryServerCallTest.java index da838a1c01a..f531569573d 100644 --- a/grpc/src/test/java/com/linecorp/armeria/server/grpc/UnaryServerCallTest.java +++ b/grpc/src/test/java/com/linecorp/armeria/server/grpc/UnaryServerCallTest.java @@ -52,6 +52,7 @@ import com.linecorp.armeria.common.HttpStatus; import com.linecorp.armeria.common.RequestHeaders; import com.linecorp.armeria.common.ResponseHeaders; +import com.linecorp.armeria.common.grpc.GrpcExceptionHandlerFunction; import com.linecorp.armeria.common.grpc.GrpcSerializationFormats; import com.linecorp.armeria.common.grpc.protocol.DeframedMessage; import com.linecorp.armeria.common.util.EventLoopGroups; @@ -329,7 +330,7 @@ void decodeMultipleChunks() { ResponseHeaders.builder(HttpStatus.OK) .contentType(GrpcSerializationFormats.PROTO.mediaType()) .build(), - /* exceptionMappings */ null, + GrpcExceptionHandlerFunction.of(), /* blockingExecutor */ null, /* autoCompress */ false, /* useMethodMarshaller */ false); @@ -375,7 +376,7 @@ private UnaryServerCall newServerCall( ResponseHeaders.builder(HttpStatus.OK) .contentType(GrpcSerializationFormats.PROTO.mediaType()) .build(), - /* exceptionMappings */ null, + GrpcExceptionHandlerFunction.of(), /* blockingExecutor */ null, /* autoCompress */ false, /* useMethodMarshaller */ false); diff --git a/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/CheckerCommand.java b/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/CheckerCommand.java index e6f8d0d4d2c..d85d36f7337 100644 --- a/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/CheckerCommand.java +++ b/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/CheckerCommand.java @@ -48,6 +48,7 @@ import picocli.CommandLine; import picocli.CommandLine.Command; +@SuppressWarnings("NullAway") @Command(name = "checker", mixinStandardHelpOptions = true) public class CheckerCommand implements Runnable { diff --git a/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/ControlCommand.java b/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/ControlCommand.java index 246a8d98f1c..6106478f771 100644 --- a/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/ControlCommand.java +++ b/it/kubernetes-chaos-tests/src/main/java/com/linecorp/armeria/kubernetes/it/ControlCommand.java @@ -44,6 +44,7 @@ import picocli.CommandLine; import picocli.CommandLine.Command; +@SuppressWarnings("NullAway") @Command(name = "control", mixinStandardHelpOptions = true) public class ControlCommand implements Runnable { diff --git a/jetty/jetty11/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java b/jetty/jetty11/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java index d0d26be85da..8413b5b3aa3 100644 --- a/jetty/jetty11/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java +++ b/jetty/jetty11/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java @@ -411,6 +411,7 @@ public void send(MetaData.Request unused, MetaData.@Nullable Response response, final int length = content != null ? content.remaining() : 0; if (ctx.request().headers().method() != HttpMethod.HEAD && length != 0) { final HttpData data; + assert content != null; if (content.hasArray()) { final int from = content.arrayOffset() + content.position(); content.position(content.position() + length); diff --git a/jetty/jetty9/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java b/jetty/jetty9/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java index 824e27a5843..ec38c96e23c 100644 --- a/jetty/jetty9/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java +++ b/jetty/jetty9/src/main/java/com/linecorp/armeria/server/jetty/JettyService.java @@ -421,6 +421,7 @@ public void send(MetaData.@Nullable Response info, boolean head, final int length = content != null ? content.remaining() : 0; if (!head && length != 0) { final HttpData data; + assert content != null; if (content.hasArray()) { final int from = content.arrayOffset() + content.position(); content.position(content.position() + length); diff --git a/junit5/src/main/java/com/linecorp/armeria/internal/testing/SelfSignedCertificateRuleDelegate.java b/junit5/src/main/java/com/linecorp/armeria/internal/testing/SelfSignedCertificateRuleDelegate.java index 94bd4674002..56ecf114893 100644 --- a/junit5/src/main/java/com/linecorp/armeria/internal/testing/SelfSignedCertificateRuleDelegate.java +++ b/junit5/src/main/java/com/linecorp/armeria/internal/testing/SelfSignedCertificateRuleDelegate.java @@ -181,35 +181,32 @@ public void after() { * Returns the generated {@link X509Certificate}. */ public X509Certificate certificate() { - ensureCertificate(); - return certificate.cert(); + return ensureCertificate().cert(); } /** * Returns the self-signed certificate file. */ public File certificateFile() { - ensureCertificate(); - return certificate.certificate(); + return ensureCertificate().certificate(); } /** * Returns the {@link PrivateKey} of the self-signed certificate. */ public PrivateKey privateKey() { - ensureCertificate(); - return certificate.key(); + return ensureCertificate().key(); } /** * Returns the private key file of the self-signed certificate. */ public File privateKeyFile() { - ensureCertificate(); - return certificate.privateKey(); + return ensureCertificate().privateKey(); } - private void ensureCertificate() { + private SelfSignedCertificate ensureCertificate() { checkState(certificate != null, "certificate not created"); + return certificate; } } diff --git a/junit5/src/main/java/com/linecorp/armeria/internal/testing/ServerRuleDelegate.java b/junit5/src/main/java/com/linecorp/armeria/internal/testing/ServerRuleDelegate.java index 3b6e661d309..f865b68c033 100644 --- a/junit5/src/main/java/com/linecorp/armeria/internal/testing/ServerRuleDelegate.java +++ b/junit5/src/main/java/com/linecorp/armeria/internal/testing/ServerRuleDelegate.java @@ -89,6 +89,7 @@ public void after() { public Server start() { final Server oldServer = server.get(); if (!isStopped(oldServer)) { + assert oldServer != null; return oldServer; } @@ -149,6 +150,7 @@ public Server server() { if (isStopped(server)) { throw new IllegalStateException("server did not start."); } + assert server != null; return server; } @@ -364,7 +366,9 @@ public WebClient webClient() { if (this.webClient.compareAndSet(null, newWebClient)) { return newWebClient; } else { - return this.webClient.get(); + final WebClient oldWebClient = this.webClient.get(); + assert oldWebClient != null; + return oldWebClient; } } @@ -430,7 +434,9 @@ public WebSocketClient webSocketClient() { if (this.webSocketClient.compareAndSet(null, newWebSocketClient)) { return newWebSocketClient; } else { - return this.webSocketClient.get(); + final WebSocketClient oldWebClient = this.webSocketClient.get(); + assert oldWebClient != null; + return oldWebClient; } } diff --git a/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/ArmeriaWebSocket.java b/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/ArmeriaWebSocket.java index 069bd80b2d8..49b5df31431 100644 --- a/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/ArmeriaWebSocket.java +++ b/kubernetes/src/main/java/com/linecorp/armeria/client/kubernetes/ArmeriaWebSocket.java @@ -52,6 +52,7 @@ public boolean send(ByteBuffer buffer) { // 'buffer' may be mutated by the caller, so we need to copy it. final ByteBufAllocator alloc = ClientRequestContext.mapCurrent(RequestContext::alloc, () -> ByteBufAllocator.DEFAULT); + assert alloc != null; final ByteBuf data = alloc.buffer(buffer.remaining()).writeBytes(buffer.duplicate()); final int dataLength = data.readableBytes(); pending.addAndGet(dataLength); diff --git a/logback/logback12/src/main/java/com/linecorp/armeria/common/logback/UnionMap.java b/logback/logback12/src/main/java/com/linecorp/armeria/common/logback/UnionMap.java index 8f3eb47b992..345e11e4bb5 100644 --- a/logback/logback12/src/main/java/com/linecorp/armeria/common/logback/UnionMap.java +++ b/logback/logback12/src/main/java/com/linecorp/armeria/common/logback/UnionMap.java @@ -83,6 +83,7 @@ public boolean containsValue(Object value) { return first.containsValue(value) || second.containsValue(value); } + @Nullable @Override public V get(Object key) { final V value = first.get(key); diff --git a/oauth2/src/main/java/com/linecorp/armeria/client/auth/oauth2/OAuth2ResourceOwnerPasswordCredentialsGrantBuilder.java b/oauth2/src/main/java/com/linecorp/armeria/client/auth/oauth2/OAuth2ResourceOwnerPasswordCredentialsGrantBuilder.java index 2856f8d6238..8c349671145 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/client/auth/oauth2/OAuth2ResourceOwnerPasswordCredentialsGrantBuilder.java +++ b/oauth2/src/main/java/com/linecorp/armeria/client/auth/oauth2/OAuth2ResourceOwnerPasswordCredentialsGrantBuilder.java @@ -65,6 +65,7 @@ public OAuth2ResourceOwnerPasswordCredentialsGrantBuilder userCredentials( * Builds a new instance of {@link OAuth2ResourceOwnerPasswordCredentialsGrant} using configured parameters. */ public OAuth2ResourceOwnerPasswordCredentialsGrant build() { + final Supplier> userCredentialsSupplier = this.userCredentialsSupplier; checkState(userCredentialsSupplier != null, "userCredentialsSupplier must be set."); final ClientAuthentication clientAuthentication = buildClientAuthentication(); final Supplier accessTokenRequestSupplier = () -> { diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/DefaultTokenOperationRequest.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/DefaultTokenOperationRequest.java index ab043478c2f..996bf1e1aae 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/DefaultTokenOperationRequest.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/DefaultTokenOperationRequest.java @@ -53,6 +53,7 @@ public String token() { return token; } + @Nullable @Override public String tokenTypeHint() { return tokenTypeHint; diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidClientException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidClientException.java index 1a5e73165be..e5af4f04c57 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidClientException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidClientException.java @@ -44,7 +44,7 @@ public final class InvalidClientException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public InvalidClientException(String errorDescription, @Nullable String errorUri) { + public InvalidClientException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -62,7 +62,8 @@ public InvalidClientException(String errorDescription, @Nullable String errorUri * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public InvalidClientException(String errorDescription, @Nullable String errorUri, Throwable cause) { + public InvalidClientException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidGrantException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidGrantException.java index 77f9cc704da..eb3bcfc8921 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidGrantException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidGrantException.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.common.auth.oauth2; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; /** @@ -40,7 +41,7 @@ public final class InvalidGrantException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public InvalidGrantException(String errorDescription, String errorUri) { + public InvalidGrantException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -58,7 +59,8 @@ public InvalidGrantException(String errorDescription, String errorUri) { * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public InvalidGrantException(String errorDescription, String errorUri, Throwable cause) { + public InvalidGrantException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidRequestException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidRequestException.java index 505df73c72b..ae496906a5e 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidRequestException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidRequestException.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.common.auth.oauth2; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; /** @@ -40,7 +41,7 @@ public final class InvalidRequestException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public InvalidRequestException(String errorDescription, String errorUri) { + public InvalidRequestException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -58,7 +59,8 @@ public InvalidRequestException(String errorDescription, String errorUri) { * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public InvalidRequestException(String errorDescription, String errorUri, Throwable cause) { + public InvalidRequestException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidScopeException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidScopeException.java index 32005b38d2a..66436bb3034 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidScopeException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/InvalidScopeException.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.common.auth.oauth2; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; /** @@ -39,7 +40,7 @@ public final class InvalidScopeException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public InvalidScopeException(String errorDescription, String errorUri) { + public InvalidScopeException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -57,7 +58,8 @@ public InvalidScopeException(String errorDescription, String errorUri) { * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public InvalidScopeException(String errorDescription, String errorUri, Throwable cause) { + public InvalidScopeException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/TokenRequestException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/TokenRequestException.java index 5dcb4b44fd3..053a171bea5 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/TokenRequestException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/TokenRequestException.java @@ -100,7 +100,7 @@ public static TokenRequestException parse(String rawResponse) { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public TokenRequestException(String errorDescription, @Nullable String errorUri) { + public TokenRequestException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription); this.errorUri = errorUri; } @@ -119,7 +119,8 @@ public TokenRequestException(String errorDescription, @Nullable String errorUri) * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public TokenRequestException(String errorDescription, @Nullable String errorUri, Throwable cause) { + public TokenRequestException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, cause); this.errorUri = errorUri; } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnauthorizedClientException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnauthorizedClientException.java index 0f3cfc36319..63498dbcc2c 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnauthorizedClientException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnauthorizedClientException.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.common.auth.oauth2; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; /** @@ -38,7 +39,7 @@ public final class UnauthorizedClientException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public UnauthorizedClientException(String errorDescription, String errorUri) { + public UnauthorizedClientException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -56,7 +57,8 @@ public UnauthorizedClientException(String errorDescription, String errorUri) { * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public UnauthorizedClientException(String errorDescription, String errorUri, Throwable cause) { + public UnauthorizedClientException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedGrantTypeException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedGrantTypeException.java index 3443e0cf204..20357354e02 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedGrantTypeException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedGrantTypeException.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.common.auth.oauth2; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; /** @@ -39,7 +40,7 @@ public final class UnsupportedGrantTypeException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public UnsupportedGrantTypeException(String errorDescription, String errorUri) { + public UnsupportedGrantTypeException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -58,7 +59,8 @@ public UnsupportedGrantTypeException(String errorDescription, String errorUri) { * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public UnsupportedGrantTypeException(String errorDescription, String errorUri, Throwable cause) { + public UnsupportedGrantTypeException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedTokenTypeException.java b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedTokenTypeException.java index 9cf67c62aa1..721430c20ea 100644 --- a/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedTokenTypeException.java +++ b/oauth2/src/main/java/com/linecorp/armeria/common/auth/oauth2/UnsupportedTokenTypeException.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.common.auth.oauth2; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; /** @@ -40,7 +41,7 @@ public final class UnsupportedTokenTypeException extends TokenRequestException { * thus MUST NOT include characters outside * the set {@code %x21} / {@code %x23-5B} / {@code %x5D-7E}. */ - public UnsupportedTokenTypeException(String errorDescription, String errorUri) { + public UnsupportedTokenTypeException(@Nullable String errorDescription, @Nullable String errorUri) { super(errorDescription, errorUri); } @@ -59,7 +60,8 @@ public UnsupportedTokenTypeException(String errorDescription, String errorUri) { * @param cause the cause (which is saved for later retrieval by the {@link #getCause()} method). * (A {@code null} value is permitted, and indicates that the cause is nonexistent or unknown.) */ - public UnsupportedTokenTypeException(String errorDescription, String errorUri, Throwable cause) { + public UnsupportedTokenTypeException(@Nullable String errorDescription, @Nullable String errorUri, + @Nullable Throwable cause) { super(errorDescription, errorUri, cause); } } diff --git a/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufRequestConverterFunctionProvider.java b/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufRequestConverterFunctionProvider.java index 010c8978f91..6ee397e7aca 100644 --- a/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufRequestConverterFunctionProvider.java +++ b/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufRequestConverterFunctionProvider.java @@ -24,6 +24,7 @@ import com.google.protobuf.Message; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; import com.linecorp.armeria.server.annotation.RequestConverterFunction; import com.linecorp.armeria.server.annotation.RequestConverterFunctionProvider; @@ -35,6 +36,7 @@ @UnstableApi public final class ProtobufRequestConverterFunctionProvider implements RequestConverterFunctionProvider { + @Nullable @Override public RequestConverterFunction createRequestConverterFunction(Type requestType, RequestConverterFunction requestConverter) { diff --git a/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunction.java b/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunction.java index 80ca7b2705d..372f0c0ece7 100644 --- a/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunction.java +++ b/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunction.java @@ -97,6 +97,8 @@ public final class ProtobufResponseConverterFunction implements ResponseConverte // Should never reach here. fromPublisher = null; } + + assert fromPublisher != null; fromPublisherMH = fromPublisher; MethodHandle fromStream; @@ -110,6 +112,8 @@ public final class ProtobufResponseConverterFunction implements ResponseConverte // Should never reach here. fromStream = null; } + + assert fromStream != null; fromStreamMH = fromStream; MethodHandle fromObject; @@ -122,6 +126,8 @@ public final class ProtobufResponseConverterFunction implements ResponseConverte // Should never reach here. fromObject = null; } + + assert fromObject != null; fromObjectMH = fromObject; } @@ -175,6 +181,7 @@ public HttpResponse convertResponse(ServiceRequestContext ctx, ResponseHeaders h @Nullable Object result, HttpHeaders trailers) throws Exception { final MediaType contentType = headers.contentType(); final boolean isJson = isJson(contentType); + assert contentType != null; if (isJsonSeq(contentType)) { checkArgument(result != null, "a null value is not allowed for %s", contentType); diff --git a/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunctionProvider.java b/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunctionProvider.java index 194fccf6edc..fba79b3ac2e 100644 --- a/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunctionProvider.java +++ b/protobuf/src/main/java/com/linecorp/armeria/server/protobuf/ProtobufResponseConverterFunctionProvider.java @@ -27,6 +27,7 @@ import com.google.protobuf.Message; import com.google.protobuf.MessageLite; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.annotation.UnstableApi; import com.linecorp.armeria.server.annotation.ResponseConverterFunction; import com.linecorp.armeria.server.annotation.ResponseConverterFunctionProvider; @@ -37,6 +38,7 @@ @UnstableApi public final class ProtobufResponseConverterFunctionProvider implements ResponseConverterFunctionProvider { + @Nullable @Override public ResponseConverterFunction createResponseConverterFunction(Type returnType) { if (isSupportedType(returnType)) { diff --git a/resteasy/src/main/java/com/linecorp/armeria/internal/common/resteasy/HttpMessageSubscriberAdapter.java b/resteasy/src/main/java/com/linecorp/armeria/internal/common/resteasy/HttpMessageSubscriberAdapter.java index e4edd1992b4..416ad38ce92 100644 --- a/resteasy/src/main/java/com/linecorp/armeria/internal/common/resteasy/HttpMessageSubscriberAdapter.java +++ b/resteasy/src/main/java/com/linecorp/armeria/internal/common/resteasy/HttpMessageSubscriberAdapter.java @@ -53,6 +53,8 @@ public void onSubscribe(Subscription subscription) { @Override public void onNext(HttpObject httpObject) { + assert subscription != null; + final boolean eos = httpObject.isEndOfStream(); if (httpObject instanceof HttpHeaders) { subscriber.onHeaders((HttpHeaders) httpObject); diff --git a/retrofit2/src/main/java/com/linecorp/armeria/client/retrofit2/ArmeriaCallFactory.java b/retrofit2/src/main/java/com/linecorp/armeria/client/retrofit2/ArmeriaCallFactory.java index 569e9146136..1746e2cf6db 100644 --- a/retrofit2/src/main/java/com/linecorp/armeria/client/retrofit2/ArmeriaCallFactory.java +++ b/retrofit2/src/main/java/com/linecorp/armeria/client/retrofit2/ArmeriaCallFactory.java @@ -171,12 +171,14 @@ public Request request() { return request; } - private synchronized void createRequest() { + private synchronized HttpResponse createRequest() { if (httpResponse != null) { throw new IllegalStateException("executed already"); } executionStateUpdater.compareAndSet(this, ExecutionState.IDLE, ExecutionState.RUNNING); - httpResponse = doCall(callFactory, request); + final HttpResponse newResponse = doCall(callFactory, request); + httpResponse = newResponse; + return newResponse; } @Override @@ -194,8 +196,7 @@ public Response execute() throws IOException { @Override public void enqueue(Callback callback) { - createRequest(); - httpResponse.subscribe(callFactory.subscriberFactory.create(this, callback, request)); + createRequest().subscribe(callFactory.subscriberFactory.create(this, callback, request)); } @Override diff --git a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextAssembly.java b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextAssembly.java index a916d657dbb..46224738fc1 100644 --- a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextAssembly.java +++ b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextAssembly.java @@ -233,7 +233,10 @@ public static synchronized void disable() { private abstract static class ConditionalOnCurrentRequestContextFunction implements Function { @Override public final T apply(T t) { - return RequestContext.mapCurrent(requestContext -> applyActual(t, requestContext), () -> t); + final T result = RequestContext.mapCurrent(requestContext -> applyActual(t, requestContext), + () -> t); + assert result != null; + return result; } abstract T applyActual(T t, RequestContext ctx); diff --git a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextCompletableObserver.java b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextCompletableObserver.java index 60965d9c53c..b826c69611f 100644 --- a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextCompletableObserver.java +++ b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextCompletableObserver.java @@ -17,6 +17,7 @@ package com.linecorp.armeria.common.rxjava2; import com.linecorp.armeria.common.RequestContext; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.SafeCloseable; import io.reactivex.CompletableObserver; @@ -26,6 +27,7 @@ final class RequestContextCompletableObserver implements CompletableObserver, Disposable { private final CompletableObserver actual; private final RequestContext assemblyContext; + @Nullable private Disposable disposable; RequestContextCompletableObserver(CompletableObserver actual, RequestContext assemblyContext) { @@ -60,11 +62,13 @@ public void onComplete() { @Override public boolean isDisposed() { + assert disposable != null; return disposable.isDisposed(); } @Override public void dispose() { + assert disposable != null; disposable.dispose(); } } diff --git a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextMaybeObserver.java b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextMaybeObserver.java index 9682251614b..3014e971df7 100644 --- a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextMaybeObserver.java +++ b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextMaybeObserver.java @@ -17,6 +17,7 @@ package com.linecorp.armeria.common.rxjava2; import com.linecorp.armeria.common.RequestContext; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.SafeCloseable; import io.reactivex.MaybeObserver; @@ -26,6 +27,7 @@ final class RequestContextMaybeObserver implements MaybeObserver, Disposable { private final MaybeObserver actual; private final RequestContext assemblyContext; + @Nullable private Disposable disposable; RequestContextMaybeObserver(MaybeObserver actual, RequestContext assemblyContext) { @@ -67,11 +69,13 @@ public void onComplete() { @Override public boolean isDisposed() { + assert disposable != null; return disposable.isDisposed(); } @Override public void dispose() { + assert disposable != null; disposable.dispose(); } } diff --git a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextSingleObserver.java b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextSingleObserver.java index d29e851441c..d98e3776feb 100644 --- a/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextSingleObserver.java +++ b/rxjava2/src/main/java/com/linecorp/armeria/common/rxjava2/RequestContextSingleObserver.java @@ -17,6 +17,7 @@ package com.linecorp.armeria.common.rxjava2; import com.linecorp.armeria.common.RequestContext; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.SafeCloseable; import io.reactivex.SingleObserver; @@ -26,6 +27,7 @@ final class RequestContextSingleObserver implements SingleObserver, Disposable { private final SingleObserver actual; private final RequestContext assemblyContext; + @Nullable private Disposable disposable; RequestContextSingleObserver(SingleObserver actual, RequestContext assemblyContext) { @@ -60,11 +62,13 @@ public void onSuccess(T value) { @Override public boolean isDisposed() { + assert disposable != null; return disposable.isDisposed(); } @Override public void dispose() { + assert disposable != null; disposable.dispose(); } } diff --git a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextAssembly.java b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextAssembly.java index a4c0a384a43..92799f8617e 100644 --- a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextAssembly.java +++ b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextAssembly.java @@ -222,7 +222,10 @@ private RequestContextAssembly() {} private abstract static class ConditionalOnCurrentRequestContextFunction implements Function { @Override public final T apply(T t) { - return RequestContext.mapCurrent(requestContext -> applyActual(t, requestContext), () -> t); + final T result = RequestContext.mapCurrent(requestContext -> applyActual(t, requestContext), + () -> t); + assert result != null; + return result; } abstract T applyActual(T t, RequestContext ctx); diff --git a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextCompletableObserver.java b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextCompletableObserver.java index 15b6cf9324c..09c0219f1c5 100644 --- a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextCompletableObserver.java +++ b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextCompletableObserver.java @@ -17,6 +17,7 @@ package com.linecorp.armeria.common.rxjava3; import com.linecorp.armeria.common.RequestContext; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.SafeCloseable; import io.reactivex.rxjava3.core.CompletableObserver; @@ -26,6 +27,7 @@ final class RequestContextCompletableObserver implements CompletableObserver, Disposable { private final CompletableObserver actual; private final RequestContext assemblyContext; + @Nullable private Disposable disposable; RequestContextCompletableObserver(CompletableObserver actual, RequestContext assemblyContext) { @@ -60,11 +62,13 @@ public void onComplete() { @Override public boolean isDisposed() { + assert disposable != null; return disposable.isDisposed(); } @Override public void dispose() { + assert disposable != null; disposable.dispose(); } } diff --git a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextMaybeObserver.java b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextMaybeObserver.java index 62e0536f4a2..2edfa55d1b7 100644 --- a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextMaybeObserver.java +++ b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextMaybeObserver.java @@ -17,6 +17,7 @@ package com.linecorp.armeria.common.rxjava3; import com.linecorp.armeria.common.RequestContext; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.SafeCloseable; import io.reactivex.rxjava3.core.MaybeObserver; @@ -26,6 +27,7 @@ final class RequestContextMaybeObserver implements MaybeObserver, Disposable { private final MaybeObserver actual; private final RequestContext assemblyContext; + @Nullable private Disposable disposable; RequestContextMaybeObserver(MaybeObserver actual, RequestContext assemblyContext) { @@ -67,11 +69,13 @@ public void onComplete() { @Override public boolean isDisposed() { + assert disposable != null; return disposable.isDisposed(); } @Override public void dispose() { + assert disposable != null; disposable.dispose(); } } diff --git a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextSingleObserver.java b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextSingleObserver.java index c7bf7b8416d..6bf9b3bd0ef 100644 --- a/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextSingleObserver.java +++ b/rxjava3/src/main/java/com/linecorp/armeria/common/rxjava3/RequestContextSingleObserver.java @@ -17,6 +17,7 @@ package com.linecorp.armeria.common.rxjava3; import com.linecorp.armeria.common.RequestContext; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.util.SafeCloseable; import io.reactivex.rxjava3.core.SingleObserver; @@ -26,6 +27,7 @@ final class RequestContextSingleObserver implements SingleObserver, Disposable { private final SingleObserver actual; private final RequestContext assemblyContext; + @Nullable private Disposable disposable; RequestContextSingleObserver(SingleObserver actual, RequestContext assemblyContext) { @@ -60,11 +62,13 @@ public void onSuccess(T value) { @Override public boolean isDisposed() { + assert disposable != null; return disposable.isDisposed(); } @Override public void dispose() { + assert disposable != null; disposable.dispose(); } } diff --git a/saml/src/main/java/com/linecorp/armeria/server/saml/SamlDecorator.java b/saml/src/main/java/com/linecorp/armeria/server/saml/SamlDecorator.java index 71de8d07548..e02baf91bb4 100644 --- a/saml/src/main/java/com/linecorp/armeria/server/saml/SamlDecorator.java +++ b/saml/src/main/java/com/linecorp/armeria/server/saml/SamlDecorator.java @@ -198,6 +198,7 @@ private AuthnRequest createAuthRequest(SamlIdentityProviderConfig idp, String de // The ProtocolBinding attribute is mutually exclusive with the AssertionConsumerServiceIndex attribute // and is typically accompanied by the AssertionConsumerServiceURL attribute. final SamlPortConfig portConfig = portConfigHolder.config(); + assert portConfig != null; final SamlEndpoint acsEndpoint = idp.acsEndpoint() != null ? idp.acsEndpoint() : sp.defaultAcsConfig().endpoint(); authnRequest.setAssertionConsumerServiceURL(acsEndpoint.toUriString(portConfig.scheme().uriText(), diff --git a/saml/src/main/java/com/linecorp/armeria/server/saml/SamlIdentityProviderConfigBuilder.java b/saml/src/main/java/com/linecorp/armeria/server/saml/SamlIdentityProviderConfigBuilder.java index cc0f9b7d74e..43b36adfa90 100644 --- a/saml/src/main/java/com/linecorp/armeria/server/saml/SamlIdentityProviderConfigBuilder.java +++ b/saml/src/main/java/com/linecorp/armeria/server/saml/SamlIdentityProviderConfigBuilder.java @@ -161,11 +161,14 @@ public SamlServiceProviderBuilder and() { * Builds a {@link SamlIdentityProviderConfig}. */ SamlIdentityProviderConfig build(CredentialResolverAdapter credentialResolver) { - checkState(entityId != null, "entity ID of the identity provider is not set"); + checkState(entityId != null, "entity ID of the identity provider is not set."); + checkState(ssoEndpoint != null, "SSO endpoint is not set."); // Use the entityId as a default key name. final Credential signing = credentialResolver.apply(firstNonNull(signingKey, entityId)); + checkState(signing != null, "CredentialResolver.apply() returned null for a signing key."); final Credential encryption = credentialResolver.apply(firstNonNull(encryptionKey, entityId)); + checkState(encryption != null, "CredentialResolver.apply() returned null for an encryption key."); return new SamlIdentityProviderConfig(entityId, signing, diff --git a/saml/src/main/java/com/linecorp/armeria/server/saml/SamlService.java b/saml/src/main/java/com/linecorp/armeria/server/saml/SamlService.java index 0cae39487a8..f9ab8f3b44d 100644 --- a/saml/src/main/java/com/linecorp/armeria/server/saml/SamlService.java +++ b/saml/src/main/java/com/linecorp/armeria/server/saml/SamlService.java @@ -169,6 +169,8 @@ public HttpResponse serve(ServiceRequestContext ctx, HttpRequest req) throws Exc } final SamlPortConfig portConfig = portConfigHolder.config(); + assert portConfig != null; + final boolean isTls = ctx.sessionProtocol().isTls(); if (portConfig.scheme().isTls() != isTls) { if (isTls) { diff --git a/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/ArmeriaSpringActuatorAutoConfiguration.java b/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/ArmeriaSpringActuatorAutoConfiguration.java index 73661095477..3e7aa5f17c2 100644 --- a/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/ArmeriaSpringActuatorAutoConfiguration.java +++ b/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/ArmeriaSpringActuatorAutoConfiguration.java @@ -323,6 +323,7 @@ private static Integer obtainManagementServerPort(ServerBuilder serverBuilder, ManagementServerProperties properties) { Object internalServices = null; if (MANAGEMENT_SERVER_PORT_METHOD != null) { + assert INTERNAL_SERVICES_CLASS != null; internalServices = findBean(beanFactory, INTERNAL_SERVICES_CLASS); } @@ -338,6 +339,7 @@ private static Integer obtainManagementServerPort(ServerBuilder serverBuilder, return managementPort.getPort(); } + assert MANAGEMENT_SERVER_PORT_METHOD != null; try { final Port port = (Port) MANAGEMENT_SERVER_PORT_METHOD.invoke(internalServices); if (port == null) { @@ -352,6 +354,10 @@ private static Integer obtainManagementServerPort(ServerBuilder serverBuilder, @Nullable private static Integer getExposedInternalServicePort(BeanFactory beanFactory, ArmeriaSettings armeriaSettings) { + if (INTERNAL_SERVICES_CLASS == null) { + return null; + } + final Object internalServices = findBean(beanFactory, INTERNAL_SERVICES_CLASS); if (internalServices == null) { return null; @@ -365,6 +371,8 @@ private static Integer getExposedInternalServicePort(BeanFactory beanFactory, if (!actuatorEnabled) { return null; } + + assert internalServiceProperties != null; return internalServiceProperties.getPort(); } @@ -381,7 +389,7 @@ private static T findBean(BeanFactory beanFactory, Class clazz) { private static void addLocalManagementPortPropertyAlias(ConfigurableEnvironment environment, Integer port) { environment.getPropertySources().addLast(new PropertySource("Management Server") { - + @Nullable @Override public Object getProperty(String name) { if ("local.management.port".equals(name)) { diff --git a/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/CorsEndpointProperties.java b/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/CorsEndpointProperties.java index d77908339de..d23b4d3b0c1 100644 --- a/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/CorsEndpointProperties.java +++ b/spring/boot3-actuator-autoconfigure/src/main/java/com/linecorp/armeria/spring/actuate/CorsEndpointProperties.java @@ -39,6 +39,8 @@ import org.springframework.boot.context.properties.ConfigurationProperties; import org.springframework.boot.convert.DurationUnit; +import com.linecorp.armeria.common.annotation.Nullable; + /** * Fork of writeSubscriber) { synchronized (this) { - Assert.state(this.writeSubscriber == null, "Only one write subscriber supported"); + checkState(this.writeSubscriber == null, "Only one write subscriber supported"); this.writeSubscriber = writeSubscriber; if (error != null || (completed && item == null)) { this.writeSubscriber.onSubscribe(Operators.emptySubscription()); diff --git a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerMutualTlsTest.java b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerMutualTlsTest.java index 9097f5ea454..db1d50f1ec0 100644 --- a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerMutualTlsTest.java +++ b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerMutualTlsTest.java @@ -86,6 +86,7 @@ public void mutualTlsAttrs(SessionProtocol sessionProtocol) throws Exception { final AggregatedHttpResponse res = client.get("/jsp/mutual_tls.jsp").aggregate().join(); final SSLSession sslSession = server().requestContextCaptor().take().sslSession(); + assert sslSession != null; final String expectedId; if (sslSession.getId() != null) { expectedId = BaseEncoding.base16().encode(sslSession.getId()); diff --git a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerTest.java b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerTest.java index 31ad581316b..1eb21b47876 100644 --- a/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerTest.java +++ b/testing-internal/src/main/java/com/linecorp/armeria/internal/testing/webapp/WebAppContainerTest.java @@ -131,7 +131,7 @@ public void japanesePath() throws Exception { final AggregatedHttpResponse response = server().blockingWebClient().get( "/jsp/" + URLEncoder.encode("日本語", "UTF-8") + "/index.jsp"); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); final String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -149,7 +149,7 @@ public void getWithQueryString() throws Exception { AggregatedHttpResponse response = server().blockingWebClient().get( "/jsp/query_string.jsp?foo=%31&bar=%32"); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -160,7 +160,7 @@ public void getWithQueryString() throws Exception { response = server().blockingWebClient().get( "/jsp/query_string.jsp?foo=%33&bar=%34"); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -176,7 +176,7 @@ public void postWithQueryString() throws Exception { HttpMethod.POST, "jsp/query_string.jsp?foo=3").contentType(MediaType.FORM_DATA).build(); AggregatedHttpResponse response = server().blockingWebClient().execute(headers, "bar=4"); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -188,7 +188,7 @@ public void postWithQueryString() throws Exception { HttpMethod.POST, "jsp/query_string.jsp?foo=5").contentType(MediaType.FORM_DATA).build(); response = server().blockingWebClient().execute(headers, "bar=6"); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -204,7 +204,7 @@ public void echoPost() throws Exception { server().blockingWebClient(cb -> cb.responseTimeoutMillis(0)) .post("/jsp/echo_post.jsp", HttpData.ofUtf8("test")); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); final String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -219,7 +219,7 @@ public void echoPostWithEmptyBody() throws Exception { final AggregatedHttpResponse response = server().blockingWebClient().post( "/jsp/echo_post.jsp", HttpData.empty()); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); final String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).isEqualTo( @@ -234,7 +234,7 @@ public void addressesAndPorts_127001() throws Exception { final AggregatedHttpResponse response = WebClient.of(server().httpUri()).blocking() .get("/jsp/addrs_and_ports.jsp"); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); final String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).matches( @@ -256,7 +256,7 @@ public void addressesAndPorts_localhost() throws Exception { "localhost:1111"); final AggregatedHttpResponse response = WebClient.of(server().httpUri()).blocking().execute(headers); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/html"); + assertThat(String.valueOf(response.contentType())).startsWith("text/html"); final String actualContent = CR_OR_LF.matcher(response.contentUtf8()) .replaceAll(""); assertThat(actualContent).matches( @@ -285,7 +285,7 @@ public void largeResponse() throws Exception { protected void testLarge(String path, boolean requiresContentLength) throws IOException { final AggregatedHttpResponse response = server().blockingWebClient().get(path); assertThat(response.status()).isSameAs(HttpStatus.OK); - assertThat(response.contentType().toString()).startsWith("text/plain"); + assertThat(String.valueOf(response.contentType())).startsWith("text/plain"); if (requiresContentLength) { // Check if the content-length header matches. assertThat(response.headers().contentLength()).isEqualTo(response.content().length()); @@ -307,6 +307,7 @@ public void tlsAttrs(SessionProtocol sessionProtocol) throws Exception { final AggregatedHttpResponse res = client.get("/jsp/tls.jsp").aggregate().join(); final SSLSession sslSession = server().requestContextCaptor().take().sslSession(); + assert sslSession != null; final String expectedId; if (sslSession.getId() != null) { expectedId = BaseEncoding.base16().encode(sslSession.getId()); diff --git a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/ThriftReply.java b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/ThriftReply.java index e55558fa04c..d6bb1eae583 100644 --- a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/ThriftReply.java +++ b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/ThriftReply.java @@ -88,6 +88,7 @@ public boolean isException() { if (isException()) { throw new IllegalStateException("not a reply but an exception"); } + assert result != null; return result; } @@ -100,6 +101,7 @@ public TApplicationException exception() { if (!isException()) { throw new IllegalStateException("not an exception but a reply"); } + assert exception != null; return exception; } diff --git a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/text/TTextProtocol.java b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/text/TTextProtocol.java index aefc75b8dbf..f20ca6ab13e 100644 --- a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/text/TTextProtocol.java +++ b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/common/thrift/text/TTextProtocol.java @@ -442,6 +442,7 @@ public TMessage readMessageBegin() throws TException { } catch (IOException e) { throw new TException("Could not parse input, is it valid json?", e); } + assert root != null; if (!root.isObject()) { throw new TException("The top level of the input must be a json object with method and args!"); } diff --git a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/common/thrift/DefaultThriftProtocolFactoryProvider.java b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/common/thrift/DefaultThriftProtocolFactoryProvider.java index 136d28e9b7d..18b845a5dea 100644 --- a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/common/thrift/DefaultThriftProtocolFactoryProvider.java +++ b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/common/thrift/DefaultThriftProtocolFactoryProvider.java @@ -24,6 +24,7 @@ import com.google.common.collect.ImmutableSet; import com.linecorp.armeria.common.SerializationFormat; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.thrift.ThriftProtocolFactories; import com.linecorp.armeria.common.thrift.ThriftProtocolFactoryProvider; import com.linecorp.armeria.common.thrift.ThriftSerializationFormats; @@ -46,6 +47,7 @@ protected Set serializationFormats() { return SERIALIZATION_FORMATS; } + @Nullable @Override protected TProtocolFactory protocolFactory(SerializationFormat serializationFormat, int maxStringLength, int maxContainerLength) { diff --git a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocServicePlugin.java b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocServicePlugin.java index 4679254d179..8a06435d717 100644 --- a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocServicePlugin.java +++ b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocServicePlugin.java @@ -365,6 +365,7 @@ public Set> supportedExampleRequestTypes() { return ImmutableSet.of(TBase.class); } + @Nullable @Override public String guessServiceName(Object exampleRequest) { final TBase exampleTBase = asTBase(exampleRequest); @@ -375,6 +376,7 @@ public String guessServiceName(Object exampleRequest) { return exampleTBase.getClass().getEnclosingClass().getName(); } + @Nullable @Override public String guessServiceMethodName(Object exampleRequest) { final TBase exampleTBase = asTBase(exampleRequest); @@ -387,6 +389,7 @@ public String guessServiceMethodName(Object exampleRequest) { typeName.length() - REQUEST_STRUCT_SUFFIX.length()); } + @Nullable @Override public String serializeExampleRequest(String serviceName, String methodName, Object exampleRequest) { diff --git a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocStringExtractor.java b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocStringExtractor.java index fd6356b1d21..6b6374a0f9c 100644 --- a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocStringExtractor.java +++ b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/internal/server/thrift/ThriftDocStringExtractor.java @@ -65,6 +65,7 @@ protected Map getDocStringsFromFiles(Map files) final Map namespaces = (Map) json.getOrDefault("namespaces", ImmutableMap.of()); final String packageName = (String) namespaces.get("java"); + assert packageName != null : "Missing namespace for Java? " + namespaces; json.forEach((key, children) -> { if (children instanceof Collection) { @SuppressWarnings("unchecked") diff --git a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/server/thrift/THttpService.java b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/server/thrift/THttpService.java index 6f3fd41be10..a41eaa945ae 100644 --- a/thrift/thrift0.13/src/main/java/com/linecorp/armeria/server/thrift/THttpService.java +++ b/thrift/thrift0.13/src/main/java/com/linecorp/armeria/server/thrift/THttpService.java @@ -16,6 +16,7 @@ package com.linecorp.armeria.server.thrift; +import static com.google.common.base.MoreObjects.firstNonNull; import static com.google.common.base.Preconditions.checkState; import static com.google.common.collect.ImmutableMap.toImmutableMap; import static java.util.Objects.requireNonNull; @@ -504,8 +505,9 @@ private void decodeAndInvoke( try (HttpData content = req.content()) { final ByteBuf buf = content.byteBuf(); final TByteBufTransport inTransport = new TByteBufTransport(buf); - final TProtocol inProto = requestProtocolFactories.get(serializationFormat) - .getProtocol(inTransport); + final TProtocolFactory protocolFactory = requestProtocolFactories.get(serializationFormat); + assert protocolFactory != null; + final TProtocol inProto = protocolFactory.getProtocol(inTransport); final TMessage header; final TBase args; @@ -525,7 +527,7 @@ private void decodeAndInvoke( if (e instanceof TProtocolException && ((TProtocolException) e).getType() == TProtocolException.SIZE_LIMIT) { httpStatus = HttpStatus.REQUEST_ENTITY_TOO_LARGE; - message = e.getMessage(); + message = firstNonNull(e.getMessage(), httpStatus.toString()); } else { httpStatus = HttpStatus.BAD_REQUEST; message = "Failed to decode a " + serializationFormat + " header"; @@ -774,8 +776,9 @@ private HttpData encodeSuccess(ServiceRequestContext ctx, RpcResponse reply, boolean success = false; try { final TTransport transport = new TByteBufTransport(buf); - final TProtocol outProto = responseProtocolFactories.get(serializationFormat) - .getProtocol(transport); + final TProtocolFactory protocolFactory = responseProtocolFactories.get(serializationFormat); + assert protocolFactory != null; + final TProtocol outProto = protocolFactory.getProtocol(transport); final TMessage header = new TMessage(methodName, TMessageType.REPLY, seqId); outProto.writeMessageBegin(header); result.write(outProto); @@ -822,8 +825,9 @@ private HttpData encodeException(ServiceRequestContext ctx, boolean success = false; try { final TTransport transport = new TByteBufTransport(buf); - final TProtocol outProto = responseProtocolFactories.get(serializationFormat) - .getProtocol(transport); + final TProtocolFactory protocolFactory = responseProtocolFactories.get(serializationFormat); + assert protocolFactory != null; + final TProtocol outProto = protocolFactory.getProtocol(transport); final TMessage header = new TMessage(methodName, TMessageType.EXCEPTION, seqId); outProto.writeMessageBegin(header); appException.write(outProto); diff --git a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java index 12a7b017384..e11756065ae 100644 --- a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java +++ b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java @@ -27,6 +27,8 @@ import org.apache.tomcat.util.net.AbstractEndpoint; import org.apache.tomcat.util.net.SocketWrapperBase; +import com.linecorp.armeria.common.annotation.Nullable; + import jakarta.servlet.ServletConnection; /** @@ -87,6 +89,7 @@ protected boolean isTrailerFieldsReady() { return false; } + @Nullable @Override protected ServletConnection getServletConnection() { return null; @@ -102,6 +105,7 @@ protected AbstractEndpoint.Handler.SocketState dispatchEndRequest() throws IOExc throw new UnsupportedOperationException(); } + @Nullable @Override protected AbstractEndpoint.Handler.SocketState service(SocketWrapperBase socketWrapper) throws IOException { diff --git a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ManagedTomcatService.java b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ManagedTomcatService.java index 600582f98d5..aec032492eb 100644 --- a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ManagedTomcatService.java +++ b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/ManagedTomcatService.java @@ -135,11 +135,13 @@ void stop() throws Exception { postStopTask.accept(connector); } + @Nullable @Override public Connector connector() { return connector; } + @Nullable @Override String hostName() { return hostName; diff --git a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatService.java b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatService.java index 5b89435f336..13d3c159d61 100644 --- a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatService.java +++ b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatService.java @@ -513,6 +513,7 @@ private Request convertRequest(ServiceRequestContext ctx, String mappedPath, Agg coyoteReq.setLocalPort(localAddr.getPort()); final String hostHeader = req.authority(); + assert hostHeader != null; final int colonPos = hostHeader.indexOf(':'); if (colonPos < 0) { coyoteReq.serverName().setString(hostHeader); diff --git a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatUtil.java b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatUtil.java index f9f6361eba9..e5f4723f96f 100644 --- a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatUtil.java +++ b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/TomcatUtil.java @@ -46,7 +46,9 @@ static URL getWebAppConfigFile(String contextPath, Path docBase) { } }; - return configUrlRef.get(); + final URL url = configUrlRef.get(); + assert url != null; + return url; } static String noDefaultWebXmlPath() { diff --git a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/UnmanagedTomcatService.java b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/UnmanagedTomcatService.java index c4941068b60..60f74b36578 100644 --- a/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/UnmanagedTomcatService.java +++ b/tomcat10/src/main/java/com/linecorp/armeria/server/tomcat/UnmanagedTomcatService.java @@ -54,6 +54,7 @@ public Connector connector() { return tomcat.getConnector(); } + @Nullable @Override public String hostName() { if (hostName != null) { diff --git a/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaEndpoint.java b/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaEndpoint.java index f4aa0cd2f48..e25a2d98420 100644 --- a/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaEndpoint.java +++ b/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaEndpoint.java @@ -26,6 +26,8 @@ import org.apache.tomcat.util.net.SocketProcessorBase; import org.apache.tomcat.util.net.SocketWrapperBase; +import com.linecorp.armeria.common.annotation.Nullable; + /** * A fake {@link AbstractEndpoint}. */ @@ -43,6 +45,7 @@ protected void createSSLContext(SSLHostConfig sslHostConfig) throws Exception {} @Override protected void setDefaultSslHostConfig(SSLHostConfig sslHostConfig) {} + @Nullable @Override protected InetSocketAddress getLocalAddress() throws IOException { // Doesn't seem to be used. @@ -59,6 +62,7 @@ protected boolean getDeferAccept() { return false; } + @Nullable @Override protected SocketProcessorBase createSocketProcessor(SocketWrapperBase socketWrapper, SocketEvent event) { return null; @@ -84,6 +88,7 @@ protected Log getLog() { @Override protected void doCloseServerSocket() throws IOException {} + @Nullable @Override protected Object serverSocketAccept() throws Exception { return null; diff --git a/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java b/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java index eaa273bdf73..53ebd129599 100644 --- a/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java +++ b/tomcat8/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java @@ -26,6 +26,8 @@ import org.apache.tomcat.util.net.AbstractEndpoint; import org.apache.tomcat.util.net.SocketWrapperBase; +import com.linecorp.armeria.common.annotation.Nullable; + /** * Provides a fake Processor to provide {@link ActionHook} to request/response. */ @@ -89,6 +91,7 @@ protected AbstractEndpoint.Handler.SocketState dispatchEndRequest() throws IOExc throw new UnsupportedOperationException(); } + @Nullable @Override protected AbstractEndpoint.Handler.SocketState service(SocketWrapperBase socketWrapper) throws IOException { diff --git a/tomcat9/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java b/tomcat9/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java index 9c53581df68..7a3029eb2d2 100644 --- a/tomcat9/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java +++ b/tomcat9/src/main/java/com/linecorp/armeria/server/tomcat/ArmeriaProcessor.java @@ -26,6 +26,8 @@ import org.apache.tomcat.util.net.AbstractEndpoint; import org.apache.tomcat.util.net.SocketWrapperBase; +import com.linecorp.armeria.common.annotation.Nullable; + /** * Provides a fake Processor to provide {@code ActionHook} to request/response. */ @@ -94,6 +96,7 @@ protected AbstractEndpoint.Handler.SocketState dispatchEndRequest() throws IOExc throw new UnsupportedOperationException(); } + @Nullable @Override protected AbstractEndpoint.Handler.SocketState service(SocketWrapperBase socketWrapper) throws IOException { diff --git a/xds/src/main/java/com/linecorp/armeria/xds/AbstractResourceNode.java b/xds/src/main/java/com/linecorp/armeria/xds/AbstractResourceNode.java index 0b55c0c6ce6..a1200b99cd5 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/AbstractResourceNode.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/AbstractResourceNode.java @@ -54,6 +54,7 @@ XdsBootstrapImpl xdsBootstrap() { return xdsBootstrap; } + @Nullable @Override public ConfigSource configSource() { return configSource; @@ -63,6 +64,7 @@ private void setCurrent(@Nullable T current) { this.current = current; } + @Nullable @Override public T currentResource() { return current; diff --git a/xds/src/main/java/com/linecorp/armeria/xds/AbstractRoot.java b/xds/src/main/java/com/linecorp/armeria/xds/AbstractRoot.java index 29db1042a28..d5daeccba44 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/AbstractRoot.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/AbstractRoot.java @@ -107,7 +107,7 @@ public void snapshotUpdated(T newSnapshot) { return; } snapshot = newSnapshot; - notifyWatchers("snapshotUpdated", watcher -> watcher.snapshotUpdated(snapshot)); + notifyWatchers("snapshotUpdated", watcher -> watcher.snapshotUpdated(newSnapshot)); } @Override diff --git a/xds/src/main/java/com/linecorp/armeria/xds/ClusterXdsResource.java b/xds/src/main/java/com/linecorp/armeria/xds/ClusterXdsResource.java index 18dfef4d719..0b2a96f4f28 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/ClusterXdsResource.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/ClusterXdsResource.java @@ -54,6 +54,7 @@ ClusterXdsResource withPrimer(@Nullable XdsResource primer) { return new ClusterXdsResource(cluster, primer); } + @Nullable @Override XdsResource primer() { return primer; diff --git a/xds/src/main/java/com/linecorp/armeria/xds/CompositeXdsStream.java b/xds/src/main/java/com/linecorp/armeria/xds/CompositeXdsStream.java index d9ba15918d4..720fbf9c58b 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/CompositeXdsStream.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/CompositeXdsStream.java @@ -49,6 +49,8 @@ public void close() { @Override public void resourcesUpdated(XdsType type) { - streamMap.get(type).resourcesUpdated(type); + final XdsStream stream = streamMap.get(type); + assert stream != null; + stream.resourcesUpdated(type); } } diff --git a/xds/src/main/java/com/linecorp/armeria/xds/SotwXdsStream.java b/xds/src/main/java/com/linecorp/armeria/xds/SotwXdsStream.java index c0c3e77a48d..6ef26f321f7 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/SotwXdsStream.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/SotwXdsStream.java @@ -166,7 +166,10 @@ void sendDiscoveryRequest(XdsType type, @Nullable String version, Collection requestObserver.onNext(request), + eventLoop.schedule(() -> { + assert requestObserver != null; + requestObserver.onNext(request); + }, backoff.nextDelayMillis(ackBackoffAttempts), TimeUnit.MILLISECONDS); } else { ackBackoffAttempts = 0; diff --git a/xds/src/main/java/com/linecorp/armeria/xds/XdsResourceParserUtil.java b/xds/src/main/java/com/linecorp/armeria/xds/XdsResourceParserUtil.java index c799ad1d947..5da380d02d0 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/XdsResourceParserUtil.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/XdsResourceParserUtil.java @@ -45,7 +45,9 @@ final class XdsResourceParserUtil { } static ResourceParser fromType(XdsType xdsType) { - return typeToResourceType.get(xdsType); + final ResourceParser parser = typeToResourceType.get(xdsType); + assert parser != null; + return parser; } private XdsResourceParserUtil() {} diff --git a/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLbStateFactory.java b/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLbStateFactory.java index a7eb723996c..cf6cae2dde7 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLbStateFactory.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLbStateFactory.java @@ -78,6 +78,7 @@ private static PerPriorityLoad calculatePerPriorityLoad(PrioritySet prioritySet) private static HealthAndDegraded recalculatePerPriorityState( int priority, PrioritySet prioritySet) { final HostSet hostSet = prioritySet.hostSets().get(priority); + assert hostSet != null; final int hostCount = hostSet.hosts().size(); if (hostCount <= 0) { @@ -187,6 +188,7 @@ private static PerPriorityPanic recalculatePerPriorityPanic(PrioritySet priority final ImmutableMap.Builder perPriorityPanicBuilder = ImmutableMap.builder(); for (Integer priority : prioritySet.priorities()) { final HostSet hostSet = prioritySet.hostSets().get(priority); + assert hostSet != null; final boolean isPanic = normalizedTotalAvailability == 100 ? false : isHostSetInPanic(hostSet, panicThreshold); perPriorityPanicBuilder.put(priority, isPanic); @@ -211,6 +213,7 @@ private static PerPriorityLoad recalculateLoadInTotalPanic(PrioritySet priorityS new Int2IntOpenHashMap(prioritySet.priorities().size()); for (Integer priority: prioritySet.priorities()) { final HostSet hostSet = prioritySet.hostSets().get(priority); + assert hostSet != null; final int hostsSize = hostSet.hosts().size(); if (firstNoEmpty == -1 && hostsSize > 0) { firstNoEmpty = priority; diff --git a/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLoadBalancer.java b/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLoadBalancer.java index 0176817bdcf..77d2fafa25d 100644 --- a/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLoadBalancer.java +++ b/xds/src/main/java/com/linecorp/armeria/xds/client/endpoint/DefaultLoadBalancer.java @@ -95,6 +95,7 @@ HostsSource hostSourceToUse(DefaultLbState lbState, int hash) { final PrioritySet prioritySet = lbState.prioritySet(); final int priority = priorityAndAvailability.priority; final HostSet hostSet = prioritySet.hostSets().get(priority); + assert hostSet != null; final HostAvailability hostAvailability = priorityAndAvailability.hostAvailability; if (lbState.perPriorityPanic().get(priority)) { if (prioritySet.failTrafficOnPanic()) { diff --git a/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/LegacyZooKeeperDiscoverySpec.java b/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/LegacyZooKeeperDiscoverySpec.java index 59d89268801..9446e9bcf7e 100644 --- a/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/LegacyZooKeeperDiscoverySpec.java +++ b/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/LegacyZooKeeperDiscoverySpec.java @@ -18,11 +18,13 @@ import javax.annotation.Nonnull; import com.linecorp.armeria.client.Endpoint; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.internal.common.zookeeper.LegacyNodeValueCodec; enum LegacyZooKeeperDiscoverySpec implements ZooKeeperDiscoverySpec { INSTANCE; + @Nullable @Override public String path() { return null; diff --git a/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/ServerSetsDiscoverySpec.java b/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/ServerSetsDiscoverySpec.java index 43d001a04be..3ba695f44e1 100644 --- a/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/ServerSetsDiscoverySpec.java +++ b/zookeeper3/src/main/java/com/linecorp/armeria/client/zookeeper/ServerSetsDiscoverySpec.java @@ -21,6 +21,7 @@ import org.slf4j.LoggerFactory; import com.linecorp.armeria.client.Endpoint; +import com.linecorp.armeria.common.annotation.Nullable; import com.linecorp.armeria.common.zookeeper.ServerSetsInstance; import com.linecorp.armeria.internal.common.zookeeper.ServerSetsNodeValueCodec; @@ -34,11 +35,13 @@ final class ServerSetsDiscoverySpec implements ZooKeeperDiscoverySpec { this.converter = converter; } + @Nullable @Override public String path() { return null; } + @Nullable @Override public Endpoint decode(byte[] data) { final ServerSetsInstance decodedInstance = ServerSetsNodeValueCodec.INSTANCE.decode(data); diff --git a/zookeeper3/src/main/java/com/linecorp/armeria/common/zookeeper/AbstractCuratorFrameworkBuilder.java b/zookeeper3/src/main/java/com/linecorp/armeria/common/zookeeper/AbstractCuratorFrameworkBuilder.java index e85d508df5f..4721f5ee760 100644 --- a/zookeeper3/src/main/java/com/linecorp/armeria/common/zookeeper/AbstractCuratorFrameworkBuilder.java +++ b/zookeeper3/src/main/java/com/linecorp/armeria/common/zookeeper/AbstractCuratorFrameworkBuilder.java @@ -50,7 +50,8 @@ public class AbstractCuratorFrameworkBuilder> customizers; @@ -174,6 +175,7 @@ public SELF sessionTimeoutMillis(long sessionTimeoutMillis) { public SELF customizer( Consumer customizer) { ensureInternalClient(); + assert customizers != null; customizers.add(requireNonNull(customizer, "customizer")); return self(); } @@ -202,6 +204,8 @@ protected final CuratorFramework buildCuratorFramework() { if (client != null) { return client; } + assert customizers != null; + assert clientBuilder != null; customizers.build().forEach(c -> c.accept(clientBuilder)); return clientBuilder.build(); }