在 Java 中通过 http 请求发送 base64 图像丢失了一些字符
Sending base64 image via http request in Java miss up some chars
我一直在尝试使用 java
将 base64 图像发送到 NodeJS
API,在工作和搜索了几个小时之后,我不知道是什么原因导致了以下问题,问题如下:
After logging the base64 image in nodejs I see all +
chars replaced by space
这里是Java
中原始base64的一部分
f8A0NH2qH+/+hooouAfaof7/wCho+1Q/
这里是 NodeJS
中接收到的图像的一部分
f8A0NH2qH / hooouAfaof7/wCho 1Q/
我已经尝试通过 POSTMAN
发送图像,完全没问题。
所有步骤如下:
1- 我正在使用以下代码片段将图像转换为 base64
public static String imgToBase64String(final RenderedImage img, final String formatName) {
final ByteArrayOutputStream os = new ByteArrayOutputStream();
try {
ImageIO.write(img, formatName, Base64.getEncoder().wrap(os));
return os.toString(StandardCharsets.ISO_8859_1.name());
} catch (final IOException ioe) {
throw new UncheckedIOException(ioe);
}
}
public static BufferedImage base64StringToImg(final String base64String) {
try {
return ImageIO.read(new ByteArrayInputStream(Base64.getDecoder().decode(base64String)));
} catch (final IOException ioe) {
throw new UncheckedIOException(ioe);
}
}
并截图
final Robot robot = new Robot();
final Rectangle r = new Rectangle(Toolkit.getDefaultToolkit().getScreenSize());
final BufferedImage bi = robot.createScreenCapture(r);
final String base64String = Base64Converter.imgToBase64String(bi, "jpg");
2- 我正在使用 Gson
库对对象进行字符串化
3- 我在 NodeJS
中使用 bodyParser
4- 发送 HTTP
请求为:
public static void sendPOST(String image) throws Exception {
String POST_PARAMS = "screenShotData";
URL obj = new URL(POST_URL);
HttpURLConnection con = (HttpURLConnection) obj.openConnection();
con.setRequestMethod("POST");
con.setConnectTimeout(5000); // 5 seconds
con.setReadTimeout(5000); // 5 seconds
Gson gson = new Gson();
Http.ScreenShot screenShot = new ScreenShot(); // This is just a class with a string property
screenShot.setImage(image);
POST_PARAMS += gson.toJsonTree(screenShot).getAsJsonObject();
con.setDoOutput(true);
OutputStream os = con.getOutputStream();
byte[] outputBytesArray = POST_PARAMS.getBytes();
os.write(outputBytesArray);
os.flush();
os.close();
int responseCode = con.getResponseCode();
System.out.println("POST Response Code :: " + responseCode);
if (responseCode == HttpURLConnection.HTTP_OK) { //success
BufferedReader in = new BufferedReader(new InputStreamReader(
con.getInputStream()));
String inputLine;
StringBuffer response = new StringBuffer();
while ((inputLine = in.readLine()) != null) {
response.append(inputLine);
}
in.close();
Object responseObject = gson.fromJson(response.toString(), Object.class);
System.out.println("Res: " + responseObject);
} else {
System.out.println(con.getResponseMessage());
}
}
在 URL 编码文本中,+
字符表示 space 字符。例如,
https://example.com/?s=nodejs+bodyparser
发送值为
的s
参数
nodejs bodyparser
(注意 space)。
当你做一个普通的表单 post(浏览器做的那种)时,你使用 application/x-www-form-urlencoded
数据类型,这意味着你的 POST 操作的有效负载看起来像一个查询字符串。我认为您将 JSON object 作为文本字符串传递而没有 url-encoding 它。
您可能想改用 application/json
数据类型。 nodejs 的 body 解析器从您的 Content-type header 检测到它是 JSON 并正确解析它。
试试这个。 (没有调试,抱歉。)
string payload = gson.toJsonTree(screenShot).getAsJsonObject();
byte[] outputBytesArray = payload.getBytes();
con.setRequestProperty("Content-Type", "application/json");
con.setDoOutput(true);
OutputStream os = con.getOutputStream();
os.write(outputBytesArray);
os.flush();
os.close();
您忘记关闭包装的 Base64 编码器流。只有关闭才可以写入base64编码数据的末尾:
public static String imgToBase64String(final RenderedImage img, final String formatName) {
final ByteArrayOutputStream os = new ByteArrayOutputStream();
try {
try (OutputStream wrapped = Base64.getEncoder().wrap(os)) {
ImageIO.write(img, formatName, wrapped);
}
return os.toString(StandardCharsets.ISO_8859_1.name());
} catch (final IOException ioe) {
throw new UncheckedIOException(ioe);
}
}
我遇到过这个问题,但我无权更改 class 或其他内容。
我只是简单地将 space 替换为 +,在大多数情况下它都有效。
我一直在尝试使用 java
将 base64 图像发送到 NodeJS
API,在工作和搜索了几个小时之后,我不知道是什么原因导致了以下问题,问题如下:
After logging the base64 image in nodejs I see all
+
chars replaced byspace
这里是Java
f8A0NH2qH+/+hooouAfaof7/wCho+1Q/
这里是 NodeJS
f8A0NH2qH / hooouAfaof7/wCho 1Q/
我已经尝试通过 POSTMAN
发送图像,完全没问题。
所有步骤如下:
1- 我正在使用以下代码片段将图像转换为 base64
public static String imgToBase64String(final RenderedImage img, final String formatName) {
final ByteArrayOutputStream os = new ByteArrayOutputStream();
try {
ImageIO.write(img, formatName, Base64.getEncoder().wrap(os));
return os.toString(StandardCharsets.ISO_8859_1.name());
} catch (final IOException ioe) {
throw new UncheckedIOException(ioe);
}
}
public static BufferedImage base64StringToImg(final String base64String) {
try {
return ImageIO.read(new ByteArrayInputStream(Base64.getDecoder().decode(base64String)));
} catch (final IOException ioe) {
throw new UncheckedIOException(ioe);
}
}
并截图
final Robot robot = new Robot();
final Rectangle r = new Rectangle(Toolkit.getDefaultToolkit().getScreenSize());
final BufferedImage bi = robot.createScreenCapture(r);
final String base64String = Base64Converter.imgToBase64String(bi, "jpg");
2- 我正在使用 Gson
库对对象进行字符串化
3- 我在 NodeJS
bodyParser
4- 发送 HTTP
请求为:
public static void sendPOST(String image) throws Exception {
String POST_PARAMS = "screenShotData";
URL obj = new URL(POST_URL);
HttpURLConnection con = (HttpURLConnection) obj.openConnection();
con.setRequestMethod("POST");
con.setConnectTimeout(5000); // 5 seconds
con.setReadTimeout(5000); // 5 seconds
Gson gson = new Gson();
Http.ScreenShot screenShot = new ScreenShot(); // This is just a class with a string property
screenShot.setImage(image);
POST_PARAMS += gson.toJsonTree(screenShot).getAsJsonObject();
con.setDoOutput(true);
OutputStream os = con.getOutputStream();
byte[] outputBytesArray = POST_PARAMS.getBytes();
os.write(outputBytesArray);
os.flush();
os.close();
int responseCode = con.getResponseCode();
System.out.println("POST Response Code :: " + responseCode);
if (responseCode == HttpURLConnection.HTTP_OK) { //success
BufferedReader in = new BufferedReader(new InputStreamReader(
con.getInputStream()));
String inputLine;
StringBuffer response = new StringBuffer();
while ((inputLine = in.readLine()) != null) {
response.append(inputLine);
}
in.close();
Object responseObject = gson.fromJson(response.toString(), Object.class);
System.out.println("Res: " + responseObject);
} else {
System.out.println(con.getResponseMessage());
}
}
在 URL 编码文本中,+
字符表示 space 字符。例如,
https://example.com/?s=nodejs+bodyparser
发送值为
的s
参数
nodejs bodyparser
(注意 space)。
当你做一个普通的表单 post(浏览器做的那种)时,你使用 application/x-www-form-urlencoded
数据类型,这意味着你的 POST 操作的有效负载看起来像一个查询字符串。我认为您将 JSON object 作为文本字符串传递而没有 url-encoding 它。
您可能想改用 application/json
数据类型。 nodejs 的 body 解析器从您的 Content-type header 检测到它是 JSON 并正确解析它。
试试这个。 (没有调试,抱歉。)
string payload = gson.toJsonTree(screenShot).getAsJsonObject();
byte[] outputBytesArray = payload.getBytes();
con.setRequestProperty("Content-Type", "application/json");
con.setDoOutput(true);
OutputStream os = con.getOutputStream();
os.write(outputBytesArray);
os.flush();
os.close();
您忘记关闭包装的 Base64 编码器流。只有关闭才可以写入base64编码数据的末尾:
public static String imgToBase64String(final RenderedImage img, final String formatName) {
final ByteArrayOutputStream os = new ByteArrayOutputStream();
try {
try (OutputStream wrapped = Base64.getEncoder().wrap(os)) {
ImageIO.write(img, formatName, wrapped);
}
return os.toString(StandardCharsets.ISO_8859_1.name());
} catch (final IOException ioe) {
throw new UncheckedIOException(ioe);
}
}
我遇到过这个问题,但我无权更改 class 或其他内容。 我只是简单地将 space 替换为 +,在大多数情况下它都有效。