前言:
这几天大神开始教我弄安全方面的东西了,主要是数据防篡改的。今天就遇到一个很怪异的事,页面的数据流传过来,我接收到之后首个字符缺失了。123拿到却是23。记录一下今天的收获,算是收获很多的一天。
找原因:
- 很快就能定位到是接收流的时候出问题了,因为在ajax拦截器中,我打印了参数的值,F12查看请求也是没问题的。
- 百度,面向百度编程~。还真找到了博客,上面说的是BufferReader.read()方法会”吞“调一个字符,即循环取数据的时候:
int a = 0;
while((a = bufferReader.read()) != -1)
这样就会吃调掉最前面的一个字符。
- 博客上说用readLine()就能解决,经过多次修改测试,失败!
- 我就找来大神一起商量,大神也觉得很奇怪,开始怀疑是不是JDK1.6的缺陷(超级老项目~~)
- 忙活一阵之后,我发现我的代码是先判断数据是不是以流的方式传进来的,然后再用上面的代码取值,于是我是这样判定的:
if(inputStream.read() != -1){
}
如果能读到,说明是流;
看到这句代码,我恍然大悟:应该是这句出了问题
6.找到问题点,就开始修改测试,果然是它的问题
结论:
没了的原因其实是,read方法没指定一次读多少就是一个一个字符读的,我们如果不把while或者if中的read读的值取出来,加到字符串上去,就会造成少一个字符,如果是readLine就会少一行。因为read方法返回的是int没法加到字符串上去,所以使用readLine它返回一行数据(字符串),只要处理在while中或if中的那一次读取,就能保证数据不会缺。所以使用read的时候应该指定一次读多少字节(byte数组),并将这个byte数组加到字符串上去:
byte b[] = new byte[512];
String content = null;
//read
if((len = bufferReader.read(b))!=-1){
stringBuilder.append(b,0,len) //StringBuilder的append方法不知道的可以去了解下,或者评论私信问我
//readLine
if((content = bufferReader.readLine())!=-1){
stringBuilder.append(content)
}
这样就能保证数据不会丢失了
别像我那样,不然第一个字符就没了
下面是我做的一个实验:输入字符12345
package com.xp.test;
import java.io.*;
public class Read {
public static void main(String[] args) {
//初始化输入流
InputStream inputStream = null;
//初始化缓冲区
BufferedReader bufferedReader = null;
//使用StringBuilder来拼接原数据
StringBuilder builder = new StringBuilder();
//每次读取的内容
String content = null;
try {
//将字符串12345转为输入流
inputStream=new ByteArrayInputStream("12345".getBytes());
//指定输入流到缓冲区
bufferedReader = new BufferedReader(new InputStreamReader(inputStream));
if((inputStream.read())!=-1){
//行读取数据
while((content = bufferedReader.readLine())!=null){
builder.append(content);
}
//输出结果
System.out.println(builder.toString());
}
} catch (IOException e) {
e.printStackTrace();
}finally {
try {
if(bufferedReader==null){
bufferedReader.close();
}
inputStream.close();
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
结果:
额外收获:会有用的,收好
请求的contentType:
- application/json : 这是json数据,使用request payload(而且这玩意也是用流传的)的方式也是采用的这种
- application/x-www-form-urlencoded : 这是表单(form data)的默认格式
- multipart/form-data : 传文件(是流)的方式
如有错误或不足,欢迎指正,一起交流学习!