Java Web中涉及的编解码

本文详细介绍了HTTP请求和响应过程中的编码与解码问题,包括URL、HTTPHeader、POST表单及HTTPBody等内容的编解码处理,探讨了不同场景下的编码差异及解决方案。

用户从浏览器发起一个HTTP请求,存在编码的地方是URL、Cookie、Paramiter。服务器端接收到HTTP请求后要解析HTTP协议,其中URL、Cookie和POST表单参数要解码,服务器端可能还需要读取硬盘数据(数据库、文件),这些数据都可能存在编码问题。当Servlet处理完所有请求的数据后,需要将这些数据再编码通过Socket发送到用户请求的浏览器里,再经过浏览器解码成为文本。这些过程用图表示如下:

image

1.URL的编解码

image

为了验证浏览器是怎么编码URL的,我们选择FireFox浏览器并通过HTTPFox插件观察请求的URL的实际内容:

image

从结果上看,PathInfo是UTF-8编码,而QueryString是GBK编码。至于为什么有%,是由URL的编码规范FRC3986规定:浏览器编码URL将非ASCII字符按照某种编码格式编码成16进制数字后将每个16进制表示的字节前加上“%”。

从上面的测试结果可知,浏览器对PathInfo和QueryString的编码是不一样的,不同的浏览器对PathInfo的编码也可能不一样。如Chrome会对请求“http://localhost:8080/中国?中国”转变为“http://localhost:8080/%E4%B8%AD%E5%9B%BD?%E4%B8%AD%E5%9B%BD”,这里PathInfo和QueryString的编码是一样的,都是UTF-8编码。

2.HTTP Header的编解码

当客户端发起一个HTTP请求时,除了上面的URL外还可能会在Header中传递其他的参数,如Cookie、redirectPath等,这些用户设置的值很可能也会存在编码问题。

在Tomcat中,对Header中的项进行解码是在调用request.getHeader时进行的,如果请求的Header项没有解码则调用MessageBytes的toString方法,这个方法将从byte从char的转化使用的默认编码是ISO-8859-1,而我们也不能设置Header的其他解码格式,所以如果你设置的Header中非ASCII字符解码肯定会有乱码。

我们在添加Header时也是同样的道理,不要在Header中传递非ASCII字符,如果一定要传递可以先将字符用org.apache.catalina.util.URLEncoder编码,然后再添加到Header中,这样在浏览器到服务器的传递中就不会丢失信息了,我们在访问这些项时再按照相应的字符集解码就好了。

3.POST表单的编解码

POST表单参数传递方式与QueryString不同,它是通过HTTP的BODY传递到服务端的。当我们在页面上点击提交按钮时浏览器首先将根据页面的ContentType的Charset编码格式对表单填的参数进行编码,然后提交到服务器端。在服务器端同样也是用ContentType中的字符集进行解码。所以通过POST表单提交的参数一般不会出现问题,而且这个字符集编码是我们自己设置的。

另外,针对multipart/form-data类型的参数,也就是上传的文件编码,同样也使用ContentType定义的字符集编码。值得注意的地方是,上传文件是用字节流的方式传输到服务器的本地临时目录,这个过程并没有涉及字符编码,而真正编码是在将文件内容添加到parameters中时,如果用这个不能编码将会用默认编码ISO-8859-1来编码。

4.HTTP BODY的编解码

当用户请求的资源服务端已经成功获取后,这些内容将通过Response返回给客户端浏览器,这个过程先要经过编码再到浏览器进行解码,浏览器根据HTML的<meta HTTP-equiv=“Content-Type” content=”text/html; charset=GBK”>中的charset来解码。如果没有定义,那么浏览器将会使用默认的编码来解码。

访问数据库都是通过客户端JDBC驱动来完成的,用JDBC来存取数据要和数据的内置编码保持一致,可以通过设置JDBC URL来指定。

5.JS中的编解码

html文件本身中的js的编码和当前页面中的Content-Type保持一致。

对于采用<script src=”script.js”/>类型引入的js文件,浏览器就会以当前这个页面的默认字符集解析这个JS文件,如果外部的JS文件的编码格式与当前页面的编码格式一致,那么可以不设置这个charset。但是如果script.js文件的编码格式与当前页面的不一致,就必须要指定对应的字符集,要不然对于非ASCII字符就会出现乱码。

6.其他需要编码的地方

除了URL和参数编码问题外,在服务端还有很多地方可能存在编码,如可能需要读取XML、Velocity模板引擎、JSP或者从数据库读取数据等。

image

 

参考资料:《深入分析Java Web技术》

转载于:https://www.cnblogs.com/sunzhenchao/p/3904886.html

能转换下面这些音频和视频,压缩包有包和源码,还有文档api. 整理资料不易,不喜欢可以自己百度 Audio decoders adpcm_4xm adpcm_adx adpcm_ct adpcm_ea adpcm_ea_r1 adpcm_ea_r2 adpcm_ea_r3 adpcm_ea_xas adpcm_ima_amv adpcm_ima_dk3 adpcm_ima_dk4 adpcm_ima_ea_eacs adpcm_ima_ea_sead adpcm_ima_qt adpcm_ima_smjpeg adpcm_ima_wav adpcm_ima_ws adpcm_ms adpcm_sbpro_2 adpcm_sbpro_3 adpcm_sbpro_4 adpcm_swf adpcm_thp adpcm_xa adpcm_yamaha alac ape atrac 3 cook dca dsicinaudio flac g726 imc interplay_dpcm liba52 libamr_nb libamr_wb libfaad libgsm libgsm_ms mace3 mace6 mp2 mp3 mp3adu mp3on4 mpc sv7 mpc sv8 mpeg4aac nellymoser pcm_alaw pcm_mulaw pcm_s16be pcm_s16le pcm_s16le_planar pcm_s24be pcm_s24daud pcm_s24le pcm_s32be pcm_s32le pcm_s8 pcm_u16be pcm_u16le pcm_u24be pcm_u24le pcm_u32be pcm_u32le pcm_u8 pcm_zork qdm2 real_144 real_288 roq_dpcm shorten smackaud sol_dpcm sonic truespeech tta vmdaudio vorbis wavpack wmav1 wmav2 ws_snd1 xan_dpcm Audio encoders ac3 adpcm_adx adpcm_ima_wav adpcm_ms adpcm_swf adpcm_yamaha flac g726 libamr_nb libamr_wb libfaac libgsm libgsm_ms libmp3lame libvorbis mp2 pcm_alaw pcm_mulaw pcm_s16be pcm_s16le pcm_s24be pcm_s24daud pcm_s24le pcm_s32be pcm_s32le pcm_s8 pcm_u16be pcm_u16le pcm_u24be pcm_u24le pcm_u32be pcm_u32le pcm_u8 pcm_zork roq_dpcm sonic sonicls vorbis wmav1 wmav2 Video decoders 4xm 8bps VMware video aasc amv asv1 asv2 avs bethsoftvid bmp c93 camstudio camtasia cavs cinepak cljr cyuv dnxhd dsicinvideo dvvideo dxa ffv1 ffvhuff flashsv flic flv fraps gif h261 h263 h263i h264 huffyuv idcinvideo indeo2 indeo3 interplayvideo jpegls kmvc loco mdec mjpeg mjpegb mmvideo mpeg1video mpeg2video mpeg4 mpegvideo msmpeg4 msmpeg4v1 msmpeg4v2 msrle msvideo1 mszh nuv pam pbm pgm pgmyuv png ppm ptx qdraw qpeg qtrle rawvideo roqvideo rpza rv10 rv20 sgi smackvid smc snow sp5x svq1 svq3 targa theora thp tiertexseqvideo tiff truemotion1 truemotion2 txd ultimotion vb vc1 vcr1 vmdvideo vp3 vp5 vp6 vp6a vp6f vqavideo wmv1 wmv2 wmv3 wnv1 xan_wc3 xl zlib zmbv Video encoders asv1 asv2 bmp dnxhd dvvideo ffv1 ffvhuff flashsv flv gif h261 h263 h263p huffyuv jpegls libtheora libx264 libxvid ljpeg mjpeg mpeg1video mpeg2video mpeg4 msmpeg4 msmpeg4v1 msmpeg4v2 pam pbm pgm pgmyuv png ppm qtrle rawvideo roqvideo rv10 rv20 sgi snow svq1 targa tiff wmv1 wmv2 zlib zmbv
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值