diff --git a/src/main/java/org/redkale/mq/HttpMessageLocalClient.java b/src/main/java/org/redkale/mq/HttpMessageLocalClient.java index 0f3a7965d..c011eb50f 100644 --- a/src/main/java/org/redkale/mq/HttpMessageLocalClient.java +++ b/src/main/java/org/redkale/mq/HttpMessageLocalClient.java @@ -202,7 +202,7 @@ public class HttpMessageLocalClient extends HttpMessageClient { } @Override - public void finishJson(final JsonConvert convert, final Object obj) { + public void finishJson(final Convert convert, final Object obj) { finish(convert, (Type) null, obj); } @@ -212,7 +212,7 @@ public class HttpMessageLocalClient extends HttpMessageClient { } @Override - public void finishJson(final JsonConvert convert, final Type type, final Object obj) { + public void finishJson(final Convert convert, final Type type, final Object obj) { if (future == null) { return; } diff --git a/src/main/java/org/redkale/mq/HttpMessageResponse.java b/src/main/java/org/redkale/mq/HttpMessageResponse.java index 9737706a0..33bdf7669 100644 --- a/src/main/java/org/redkale/mq/HttpMessageResponse.java +++ b/src/main/java/org/redkale/mq/HttpMessageResponse.java @@ -125,7 +125,7 @@ public class HttpMessageResponse extends HttpResponse { } @Override - public void finishJson(final JsonConvert convert, final Object obj) { + public void finishJson(final Convert convert, final Object obj) { if (message.isEmptyRespTopic()) { if (callback != null) { callback.run(); @@ -148,7 +148,7 @@ public class HttpMessageResponse extends HttpResponse { } @Override - public void finishJson(final JsonConvert convert, final Type type, final Object obj) { + public void finishJson(final Convert convert, final Type type, final Object obj) { if (message.isEmptyRespTopic()) { if (callback != null) { callback.run(); @@ -166,7 +166,7 @@ public class HttpMessageResponse extends HttpResponse { } return; } - finishHttpResult(type, new HttpResult(ret)); + finish(type, new HttpResult(ret)); } diff --git a/src/main/java/org/redkale/net/http/HttpResponse.java b/src/main/java/org/redkale/net/http/HttpResponse.java index aee800fe3..364df313b 100644 --- a/src/main/java/org/redkale/net/http/HttpResponse.java +++ b/src/main/java/org/redkale/net/http/HttpResponse.java @@ -181,7 +181,7 @@ public class HttpResponse extends Response { protected final ConvertBytesHandler convertHandler = new ConvertBytesHandler() { @Override public void completed(byte[] bs, int offset, int length, Consumer callback, A attachment) { - finish(bs, offset, length, callback, attachment); + HttpResponse.this.finish(bs, offset, length, callback, attachment); } }; @@ -356,7 +356,7 @@ public class HttpResponse extends Response { * @param convert 指定的JsonConvert * @param obj 输出对象 */ - public void finishJson(final JsonConvert convert, final Object obj) { + public void finishJson(final Convert convert, final Object obj) { this.contentType = this.jsonContentType; if (this.recycleListener != null) { this.output = obj; @@ -394,11 +394,11 @@ public class HttpResponse extends Response { /** * 将对象以JSON格式输出 * - * @param convert 指定的JsonConvert + * @param convert 指定的Convert * @param type 指定的类型 * @param obj 输出对象 */ - public void finishJson(final JsonConvert convert, final Type type, final Object obj) { + public void finishJson(final Convert convert, final Type type, final Object obj) { this.contentType = this.jsonContentType; if (this.recycleListener != null) { this.output = obj; @@ -445,7 +445,7 @@ public class HttpResponse extends Response { // if (convert == jsonRootConvert) { // JsonBytesWriter writer = jsonWriter; // convert.convertTo(writer.clear(), type, ret); -// finish(false, (String) null, writer.content(), writer.offset(), writer.length(), null, null); +// finishFuture(false, (String) null, writer.content(), writer.offset(), writer.length(), null, null); // } else { // convert.convertToBytes(type, ret, convertHandler); // } @@ -453,12 +453,12 @@ public class HttpResponse extends Response { /** * 将RetResult对象以JSON格式输出 * - * @param convert 指定的JsonConvert + * @param convert 指定的Convert * @param type 指定的RetResult泛型类型 * @param ret RetResult输出对象 */ // @Deprecated //@since 2.5.0 -// public void finishJson(final JsonConvert convert, Type type, org.redkale.service.RetResult ret) { +// public void finishJson(final Convert convert, Type type, org.redkale.service.RetResult ret) { // this.contentType = this.jsonContentType; // if (this.retResultHandler != null) { // ret = this.retResultHandler.apply(this.request, ret); @@ -471,7 +471,7 @@ public class HttpResponse extends Response { // if (convert == jsonRootConvert) { // JsonBytesWriter writer = jsonWriter; // convert.convertTo(writer.clear(), type, ret); -// finish(false, (String) null, writer.content(), writer.offset(), writer.length(), null, null); +// finishFuture(false, (String) null, writer.content(), writer.offset(), writer.length(), null, null); // } else { // convert.convertToBytes(type, ret, convertHandler); // } @@ -479,14 +479,14 @@ public class HttpResponse extends Response { /** * 将CompletableFuture的结果对象以JSON格式输出 * - * @param convert 指定的JsonConvert + * @param convert 指定的Convert * @param valueType 指定CompletableFuture.value的泛型类型 * @param future 输出对象的句柄 */ // @Deprecated //@since 2.5.0 // @SuppressWarnings("unchecked") -// public void finishJson(final JsonConvert convert, final Type valueType, final CompletableFuture future) { -// finish(convert, valueType, future); +// public void finishJson(final Convert convert, final Type valueType, final CompletableFuture future) { +// finishFuture(convert, valueType, future); // } /** * 将RetResult对象输出 @@ -606,8 +606,8 @@ public class HttpResponse extends Response { * @param valueType CompletionFuture.value的泛型类型 * @param future CompletionStage输出对象 */ - public void finish(Type valueType, CompletionStage future) { - finish(request.getRespConvert(), valueType, future); + public void finishFuture(Type valueType, CompletionStage future) { + finishFuture(request.getRespConvert(), valueType, future); } /** @@ -617,7 +617,7 @@ public class HttpResponse extends Response { * @param valueType CompletionFuture.value的泛型类型 * @param future CompletionStage输出对象 */ - public void finish(final Convert convert, Type valueType, CompletionStage future) { + public void finishFuture(final Convert convert, Type valueType, CompletionStage future) { future.whenComplete((v, e) -> { if (e != null) { context.getLogger().log(Level.WARNING, "Servlet occur, force to close channel. request = " + request + ", result is CompletionStage", (Throwable) e); @@ -632,6 +632,38 @@ public class HttpResponse extends Response { }); } + /** + * 将CompletionStage对象输出 + * + * @param valueType CompletionFuture.value的泛型类型 + * @param future CompletionStage输出对象 + */ + public void finishJsonFuture(Type valueType, CompletionStage future) { + finishJsonFuture(request.getRespConvert(), valueType, future); + } + + /** + * 将CompletionStage对象输出 + * + * @param convert 指定的Convert + * @param valueType CompletionFuture.value的泛型类型 + * @param future CompletionStage输出对象 + */ + public void finishJsonFuture(final Convert convert, Type valueType, CompletionStage future) { + future.whenComplete((v, e) -> { + if (e != null) { + context.getLogger().log(Level.WARNING, "Servlet occur, force to close channel. request = " + request + ", result is CompletionStage", (Throwable) e); + if (e instanceof TimeoutException) { + finish504(); + } else { + finish500(); + } + return; + } + finishJson(convert, valueType, v); + }); + } + /** * 将Flow.Publisher对象输出 * @@ -652,7 +684,7 @@ public class HttpResponse extends Response { * @param publisher Publisher输出对象 */ public void finishPublisher(final Convert convert, Type valueType, Flow.Publisher publisher) { - finish(convert, valueType, (CompletionStage) Flows.createMonoFuture(publisher)); + finishFuture(convert, valueType, (CompletionStage) Flows.createMonoFuture(publisher)); } /** @@ -673,7 +705,7 @@ public class HttpResponse extends Response { * @param publisher Publisher输出对象 */ public void finishPublisher(final Convert convert, Type valueType, Object publisher) { - finish(convert, valueType, (CompletionStage) Flows.maybePublisherToFuture(publisher)); + finishFuture(convert, valueType, (CompletionStage) Flows.maybePublisherToFuture(publisher)); } /** @@ -681,8 +713,8 @@ public class HttpResponse extends Response { * * @param future HttpScope输出异步对象 */ - public void finishScope(CompletionStage future) { - finish(request.getRespConvert(), future); + public void finishScopeFuture(CompletionStage future) { + finishScopeFuture(request.getRespConvert(), future); } /** @@ -691,7 +723,7 @@ public class HttpResponse extends Response { * @param convert 指定的Convert * @param future HttpScope输出异步对象 */ - public void finishScope(final Convert convert, CompletionStage future) { + public void finishScopeFuture(final Convert convert, CompletionStage future) { future.whenComplete((v, e) -> { if (e != null) { context.getLogger().log(Level.WARNING, "Servlet occur, force to close channel. request = " + request + ", result is CompletionStage", (Throwable) e); @@ -795,7 +827,7 @@ public class HttpResponse extends Response { } finish("null"); } else if (val instanceof CompletionStage) { - finish(convert, val == obj ? type : null, (CompletionStage) val); + finishFuture(convert, val == obj ? type : null, (CompletionStage) val); } else if (val instanceof CharSequence) { finish((String) val.toString()); } else if (val instanceof byte[]) { @@ -945,7 +977,7 @@ public class HttpResponse extends Response { if (cacheHandler != null) { cacheHandler.accept(this, data.getBytes()); } - //不能用finish(boolean kill, final ByteTuple array) 否则会调this.finish + //不能用finish(boolean kill, final ByteTuple array) 否则会调this.finishFuture super.finish(false, data.content(), 0, data.length()); } @@ -1193,13 +1225,13 @@ public class HttpResponse extends Response { /** * 将文件按指定文件名输出 * - * @param filename 输出文件名 + * @param fileName 输出文件名 * @param file 输出文件 * * @throws IOException IO异常 */ - public void finish(final String filename, File file) throws IOException { - finishFile(filename, file, null); + public void finish(final String fileName, File file) throws IOException { + finishFile(fileName, file, null); } /** @@ -1610,7 +1642,7 @@ public class HttpResponse extends Response { // // @Override // public void failed(Throwable exc, Void attachment) { -// finish(true); +// finishFuture(true); // try { // filechannel.close(); // } catch (IOException e) { diff --git a/src/main/java/org/redkale/net/http/Rest.java b/src/main/java/org/redkale/net/http/Rest.java index e6f1868a9..9d1d06223 100644 --- a/src/main/java/org/redkale/net/http/Rest.java +++ b/src/main/java/org/redkale/net/http/Rest.java @@ -3061,10 +3061,32 @@ public final class Rest { mv.visitVarInsn(ALOAD, 0); mv.visitFieldInsn(GETFIELD, newDynName, REST_CONVERT_FIELD_PREFIX + restConverts.size(), convertDesc); mv.visitVarInsn(ALOAD, maxLocals); - mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishScope", "(" + convertDesc + stageDesc + ")V", false); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishScopeFuture", "(" + convertDesc + stageDesc + ")V", false); } else { mv.visitVarInsn(ALOAD, maxLocals); - mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishScope", "(" + stageDesc + ")V", false); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishScopeFuture", "(" + stageDesc + ")V", false); + } + } else if (returnGenericNoFutureType != byte[].class + && returnGenericNoFutureType != RetResult.class + && returnGenericNoFutureType != HttpResult.class + && returnGenericNoFutureType != File.class + && !((returnGenericNoFutureType instanceof Class) && (((Class) returnGenericNoFutureType).isPrimitive() || CharSequence.class.isAssignableFrom((Class) returnGenericNoFutureType)))) { + if (rcs != null && rcs.length > 0) { + mv.visitVarInsn(ALOAD, 0); + mv.visitFieldInsn(GETFIELD, newDynName, REST_CONVERT_FIELD_PREFIX + restConverts.size(), convertDesc); + mv.visitVarInsn(ALOAD, 0); + mv.visitFieldInsn(GETFIELD, newDynName, REST_RETURNTYPES_FIELD_NAME, "[Ljava/lang/reflect/Type;"); + MethodDebugVisitor.pushInt(mv, entry.methodidx);//方法下标 + mv.visitInsn(AALOAD); + mv.visitVarInsn(ALOAD, maxLocals); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishJsonFuture", "(" + convertDesc + typeDesc + stageDesc + ")V", false); + } else { + mv.visitVarInsn(ALOAD, 0); + mv.visitFieldInsn(GETFIELD, newDynName, REST_RETURNTYPES_FIELD_NAME, "[Ljava/lang/reflect/Type;"); + MethodDebugVisitor.pushInt(mv, entry.methodidx);//方法下标 + mv.visitInsn(AALOAD); + mv.visitVarInsn(ALOAD, maxLocals); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishJsonFuture", "(" + typeDesc + stageDesc + ")V", false); } } else { if (rcs != null && rcs.length > 0) { @@ -3075,14 +3097,14 @@ public final class Rest { MethodDebugVisitor.pushInt(mv, entry.methodidx);//方法下标 mv.visitInsn(AALOAD); mv.visitVarInsn(ALOAD, maxLocals); - mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finish", "(" + convertDesc + typeDesc + stageDesc + ")V", false); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishFuture", "(" + convertDesc + typeDesc + stageDesc + ")V", false); } else { mv.visitVarInsn(ALOAD, 0); mv.visitFieldInsn(GETFIELD, newDynName, REST_RETURNTYPES_FIELD_NAME, "[Ljava/lang/reflect/Type;"); MethodDebugVisitor.pushInt(mv, entry.methodidx);//方法下标 mv.visitInsn(AALOAD); mv.visitVarInsn(ALOAD, maxLocals); - mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finish", "(" + typeDesc + stageDesc + ")V", false); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishFuture", "(" + typeDesc + stageDesc + ")V", false); } } mv.visitInsn(RETURN); @@ -3120,7 +3142,7 @@ public final class Rest { MethodDebugVisitor.pushInt(mv, entry.methodidx);//方法下标 mv.visitInsn(AALOAD); mv.visitVarInsn(ALOAD, maxLocals); - mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishJson", "(" + Type.getDescriptor(JsonConvert.class) + typeDesc + "Ljava/lang/Object;)V", false); + mv.visitMethodInsn(INVOKEVIRTUAL, respInternalName, "finishJson", "(" + convertDesc + typeDesc + "Ljava/lang/Object;)V", false); } else { mv.visitVarInsn(ALOAD, 0); mv.visitFieldInsn(GETFIELD, newDynName, REST_RETURNTYPES_FIELD_NAME, "[Ljava/lang/reflect/Type;"); diff --git a/src/test/java/org/redkale/test/http/UploadTestServlet.java b/src/test/java/org/redkale/test/http/UploadTestServlet.java index 12c7a850c..9d5fbc2c8 100644 --- a/src/test/java/org/redkale/test/http/UploadTestServlet.java +++ b/src/test/java/org/redkale/test/http/UploadTestServlet.java @@ -5,11 +5,8 @@ */ package org.redkale.test.http; -import org.redkale.net.http.HttpServlet; -import org.redkale.net.http.MultiPart; -import org.redkale.net.http.HttpRequest; -import org.redkale.net.http.HttpResponse; -import java.io.*; +import java.io.IOException; +import org.redkale.net.http.*; /** *