【问题标题】:How to properly read POST request body in a Handler?如何正确读取 Handler 中的 POST 请求正文?
【发布时间】:2014-11-29 23:25:23
【问题描述】:

我现在使用的代码:

    Pooled<ByteBuffer> pooledByteBuffer = exchange.getConnection().getBufferPool().allocate();
    ByteBuffer byteBuffer = pooledByteBuffer.getResource();

    int limit = byteBuffer.limit();

    byteBuffer.clear();

    exchange.getRequestChannel().read(byteBuffer);
    int pos = byteBuffer.position();
    byteBuffer.rewind();
    byte[] bytes = new byte[pos];
    byteBuffer.get(bytes);

    String requestBody = new String(bytes, Charset.forName("UTF-8") );

    byteBuffer.clear();
    pooledByteBuffer.free();

它似乎工作正常,但我不确定在将其返回到池之前是否需要 clear() ByteBuffer。我什至不确定使用exchange.getConnection().getBufferPool().allocate();。文档中没有太多关于它的内容。

【问题讨论】:

  • 查看此函数 Exchange.getRequestReceiver().receiveFullBytes(cb, ecb) 以异步读取正文。

标签: java undertow


【解决方案1】:

读取请求正文的更简单方法是分派到工作线程,这使得HttpExchange#getInputStream() 可用。

有两种方法可以做到这一点:使用BlockingHandlerdocumentation 中显示的调度模式。下面是一个使用BlockingHandler的例子:

new BlockingHandler(myHandler)

BlockingHandler 基本上是为你做调度。

【讨论】:

    【解决方案2】:

    要以非阻塞方式进行,请参阅io.undertow.io.Receiver 接口。 处理程序的示例可以是:

    pathHandler.put("/test", new HttpHandler() {
        @Override
        public void handleRequest(HttpServerExchange exchange) throws Exception {
            exchange.getRequestReceiver().receiveFullBytes(new FullBytesCallback() {
                @Override
                public void handle(HttpServerExchange exchange, byte[] message) {
                    System.out.println(new String(message));
                }                    
            });
    
            exchange.getResponseSender().send("Hello World");
        }
    });
    

    对于 Java 8:

    pathHandler.put("/test", (ex) -> {
        ex.getRequestReceiver().receiveFullBytes((e, m) -> {
            System.out.println(new String(m));
        });
        ex.getResponseSender().send("Hello World");
    });
    

    【讨论】:

      【解决方案3】:

      @atok,我使用你的方法有一段时间了,但有时当流在 read 调用之前关闭时,我会得到一个空的 body。这就像魅力:

      BufferedReader reader = null;
      StringBuilder builder = new StringBuilder( );
      
      try {
          exchange.startBlocking( );
          reader = new BufferedReader( new InputStreamReader( exchange.getInputStream( ) ) );
      
          String line;
          while( ( line = reader.readLine( ) ) != null ) {
              builder.append( line );
          }
      } catch( IOException e ) {
          e.printStackTrace( );
      } finally {
          if( reader != null ) {
              try {
                  reader.close( );
              } catch( IOException e ) {
                  e.printStackTrace( );
              }
          }
      }
      
      String body = builder.toString( );
      

      【讨论】:

        【解决方案4】:
        import io.undertow.Handlers;
        import io.undertow.Undertow;
        import io.undertow.server.HttpHandler;
        import io.undertow.server.HttpServerExchange;
        import io.undertow.server.handlers.BlockingHandler;
        
        
        public static void main(String[] args) {
        
            Undertow server = Undertow.builder()
                    .addHttpListener(8087, "xx.xx.xx.xx")
                    .setHandler(Handlers.pathTemplate().add("/webhook", new BlockingHandler(new ItemHandler())))
                    .build();
            server.start();
        }
        
        static class ItemHandler implements HttpHandler {
        
        
            @Override
            public void handleRequest(HttpServerExchange exchange) throws Exception {
               exchange.getInputStream());
            }
        }
        

        【讨论】:

          猜你喜欢
          • 2023-04-07
          • 1970-01-01
          • 2018-07-06
          • 2019-11-30
          • 2020-05-16
          • 1970-01-01
          • 1970-01-01
          • 2018-10-30
          • 2017-10-14
          相关资源
          最近更新 更多