Web Socket 上传文件并在同一端点发送 json
Web Socket upload file and send json on the same endpoint
我正在使用 Jetty 为聊天应用程序实施 JSR-356 Web 套接字。
对于托管对话和发送不同的消息类型,我使用的是使用 Jackson 和 TextDecoder
序列化 from/to json 的 DTO 对象
public class JsonDtoCodec implements Decoder.Text<Dto>,Encoder.Text<Dto>{
ObjectMapper om = ... //some object mapper
@Override
public Dto decode(String json) throws DecodeException {
Dto dto = null;
try {
dto = om.readValue(json,Dto.class);
} catch (IOException e) {
//ToDo add Log
}
return dto;
}
@Override
public String encode(Dto dto) throws EncodeException {
try {
return om.writeValueAsString(dto);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}
现在,在我的端点中,我使用直接 Dto 对象:
@ServerEndpoint(value = "/{version}/{userType}/{token}",
decoders =JsonDtoCodec.class,
encoders = JsonDtoCodec.class)
public class ChatServerEndPoint {
@OnMessage
public void onMessage(final @PathParam("userType") String userType,
final @PathParam("token") String token,
final @PathParam("version") String version,
final Session session,
Dto dto)
throws IOException {
//handling all DTO related object and sending response
Dto response = .... // create some DTO
session.getAsyncRemote().sendObject(dto);
}
}
不幸的是,我需要处理通过网络套接字上传最大 100Kb 大小的图像文件。
我可以使用同一个端点来处理 DTO 和二进制数据吗?
如果不是,我应该添加新的 EndPoint 并且我应该处理两个单独的连接,一个用于二进制文件,一个用于 Json 内容?
你当然可以。
您将有 2 个 @OnMessage
注释方法。 (一个处理文本,另一个处理二进制)
假设您的 JsonToDtoCodec
扩展了 Decoder.Text<Dto>
,那么您的其他方法将被声明为 ...
@OnMessage(maxMessageSize=100000)
public void onFileUpload(final Session session, final ByteBuffer buf)
{
}
既然你说文件最大为100kb,那么将方法传入完整ByteBuffer
就足够了。如果它更大,您可以改用 InputStream 方法。至于限制该缓冲区的大小,您的 maxMessageSize
注释将保持理智。
注意:如果客户端尝试发送超过 100kb 的二进制文件,则连接将关闭并使用关闭代码 1009: Too Big。
我正在使用 Jetty 为聊天应用程序实施 JSR-356 Web 套接字。 对于托管对话和发送不同的消息类型,我使用的是使用 Jackson 和 TextDecoder
序列化 from/to json 的 DTO 对象public class JsonDtoCodec implements Decoder.Text<Dto>,Encoder.Text<Dto>{
ObjectMapper om = ... //some object mapper
@Override
public Dto decode(String json) throws DecodeException {
Dto dto = null;
try {
dto = om.readValue(json,Dto.class);
} catch (IOException e) {
//ToDo add Log
}
return dto;
}
@Override
public String encode(Dto dto) throws EncodeException {
try {
return om.writeValueAsString(dto);
} catch (IOException e) {
throw new RuntimeException(e);
}
}
}
现在,在我的端点中,我使用直接 Dto 对象:
@ServerEndpoint(value = "/{version}/{userType}/{token}",
decoders =JsonDtoCodec.class,
encoders = JsonDtoCodec.class)
public class ChatServerEndPoint {
@OnMessage
public void onMessage(final @PathParam("userType") String userType,
final @PathParam("token") String token,
final @PathParam("version") String version,
final Session session,
Dto dto)
throws IOException {
//handling all DTO related object and sending response
Dto response = .... // create some DTO
session.getAsyncRemote().sendObject(dto);
}
}
不幸的是,我需要处理通过网络套接字上传最大 100Kb 大小的图像文件。
我可以使用同一个端点来处理 DTO 和二进制数据吗? 如果不是,我应该添加新的 EndPoint 并且我应该处理两个单独的连接,一个用于二进制文件,一个用于 Json 内容?
你当然可以。
您将有 2 个 @OnMessage
注释方法。 (一个处理文本,另一个处理二进制)
假设您的 JsonToDtoCodec
扩展了 Decoder.Text<Dto>
,那么您的其他方法将被声明为 ...
@OnMessage(maxMessageSize=100000)
public void onFileUpload(final Session session, final ByteBuffer buf)
{
}
既然你说文件最大为100kb,那么将方法传入完整ByteBuffer
就足够了。如果它更大,您可以改用 InputStream 方法。至于限制该缓冲区的大小,您的 maxMessageSize
注释将保持理智。
注意:如果客户端尝试发送超过 100kb 的二进制文件,则连接将关闭并使用关闭代码 1009: Too Big。