zoukankan      html  css  js  c++  java
  • url参数的编码解码Demo

    为了保证在页面传递数据的安全性,我们通常会对Url传递的参数进行编码解码操作。我们写一个Demo剖析URL编码解码过程。

    完整Demo下载地址

    1. Url参数如何在服务端进行编码和解码。

    1.1 Url参数编码

    思路:

    1. 对Url的参数进行Base64编码
    2. 再进行Url编码。
    3. 将多个参数封装到键值对,调用工具类同一进行编码。
      代码:
                 // 传递数据到详细页
                Product p = new Product() { Id = 1, Name = "泡椒凤爪", Price = 4.5m, Category = "零食" };
                // 封装到Dictionary中
                Dictionary dic = new Dictionary()
                {
                    {"Id",p.Id.ToString()},
                    {"Name",p.Name},
                    {"Price",p.Price.ToString()},
                    {"Category",p.Category}
                };
                // 进行Base64编码  返回数据 {"key":"value",...}
                string data = Helper.UrlCode.UrlEncode(dic);
                // 进行Url编码
                data = HttpUtility.UrlEncode(data, Encoding.UTF8);
                Response.Redirect("details.aspx?data=" + data);
    

    工具类编码方法:

            public static string UrlEncode(Dictionary dic)
            {
                string res = "{";
                foreach (string key in dic.Keys)
                {
                    byte[] buffer = Encoding.UTF8.GetBytes(dic[key]);
                    string value = Convert.ToBase64String(buffer, 0, buffer.Length);
                    res += key + ":" + value + ",";
                }
                res = res.Remove(res.Length - 1);
                res += "}";
                return res;
            }
    

    编码后的地址:

    http://localhost:50664/details.aspx?data={Id%3AMQ%3D%3D%2CName%3A5rOh5qSS5Yek54iq%2CPrice%3ANC41%2CCategory%3A6Zu26aOf}

    1.2 Url参数解码

    解码就更简单了,只需要取到Request中的数据,调用工具类解码。我们的数据就在返回的键值对中了。
    代码:

                    // 解码Url参数
                    string data = Request["data"];
                    Dictionary dicRes = Helper.UrlCode.UrlDecode(data);
                    Pro = new Product();
                    Pro.Id = int.Parse(dicRes["Id"]);
                    Pro.Price = decimal.Parse(dicRes["Price"]);
                    Pro.Name = dicRes["Name"];
                    Pro.Category = dicRes["Category"];
    

    工具类解码方法:

          public static Dictionary UrlDecode(string data)
            {
                Dictionary dic = new Dictionary();
                Dictionary dicRes = new Dictionary();
                data = data.Trim(new char[] { '{', '}' });
                string[] arrRes = data.Split(new char[] { ',' }, StringSplitOptions.RemoveEmptyEntries);
                //"key":"value"
                for (int i = 0; i < arrRes.Length; i++)
                {
                    string[] keyvalueArr = arrRes[i].Split(new char[] { ':' }, StringSplitOptions.RemoveEmptyEntries);
                    dic[keyvalueArr[0]] = keyvalueArr[1];
                }
                foreach (var kvp in dic)
                {
                    byte[] buffer = Convert.FromBase64String(kvp.Value);
                    dicRes[kvp.Key] = Encoding.UTF8.GetString(buffer, 0, buffer.Length);
                }
                return dicRes;
            }
    

    总结

    我们依次对参数进行Base64编码和ulr编码。并且对多个参数进行统一的封装。而在解码时我们并没有调用Url解码是因为返回的数据已经进行了Url解码了。
    可能有人会问进行Base64编码就可以满足需求了,为什么还要多此一举进行Url编码呢?
    主要基于以下几个原因:

    1. url编码后,Base64编码中生成的’=‘ 等字符不容易引起混淆。
    2. Base64编码有可能产生'+' 这个字符,ASP.NET帮我们接受参数时会默认把'+' 替换为空格,所以此时数据就不对了。Url编码可以避免这种情况的发生。
    3. url编码后参数更加隐秘。

    2.在客户端用js实现url参数编码。

    js实现和服务端一样,只不过base64编码需要我们自己实现。

    代码:

                // url参数编码
                var b = new Base64();
                // base64编码
                var data = "{Id:" + b.encode("1") + ",Name:" + b.encode('凤爪') +",Price:" + b.encode('4.5')+",Category:" + b.encode('零食')+ "}";
                data = encodeURIComponent(data); // URL编码
                location.href = '/details.aspx?data=' + data;
    

    编码后的地址:

    http://localhost:50664/details.aspx?data={Id%3AMQ%3D%3D%2CName%3A5rOh5qSS5Yek54iq%2CPrice%3ANC41%2CCategory%3A6Zu26aOf}


    Base64对象:

           //  Base64 加密和解密
     
            function Base64() {
     
                // private property 
                _keyStr = "ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+/=";
     
                // public method for encoding 
                this.encode = function (input) {
                    input += ''; // 转为string
                    var output = "";
                    var chr1, chr2, chr3, enc1, enc2, enc3, enc4;
                    var i = 0;
                    input = _utf8_encode(input);
                    while (i < input.length) {
                        chr1 = input.charCodeAt(i++);
                        chr2 = input.charCodeAt(i++);
                        chr3 = input.charCodeAt(i++);
                        enc1 = chr1 >> 2;
                        enc2 = ((chr1 & 3) << 4) | (chr2 >> 4);
                        enc3 = ((chr2 & 15) << 2) | (chr3 >> 6);
                        enc4 = chr3 & 63;
                        if (isNaN(chr2)) {
                            enc3 = enc4 = 64;
                        } else if (isNaN(chr3)) {
                            enc4 = 64;
                        }
                        output = output +
                        _keyStr.charAt(enc1) + _keyStr.charAt(enc2) +
                        _keyStr.charAt(enc3) + _keyStr.charAt(enc4);
                    }
                    return output;
                }
     
                // public method for decoding 
                this.decode = function (input) {
                    var output = "";
                    var chr1, chr2, chr3;
                    var enc1, enc2, enc3, enc4;
                    var i = 0;
                    input = input.replace(/[^A-Za-z0-9+/=]/g, "");
                    while (i < input.length) {
                        enc1 = _keyStr.indexOf(input.charAt(i++));
                        enc2 = _keyStr.indexOf(input.charAt(i++));
                        enc3 = _keyStr.indexOf(input.charAt(i++));
                        enc4 = _keyStr.indexOf(input.charAt(i++));
                        chr1 = (enc1 << 2) | (enc2 >> 4);
                        chr2 = ((enc2 & 15) << 4) | (enc3 >> 2);
                        chr3 = ((enc3 & 3) << 6) | enc4;
                        output = output + String.fromCharCode(chr1);
                        if (enc3 != 64) {
                            output = output + String.fromCharCode(chr2);
                        }
                        if (enc4 != 64) {
                            output = output + String.fromCharCode(chr3);
                        }
                    }
                    output = _utf8_decode(output);
                    return output;
                }
     
                // private method for UTF-8 encoding 
                _utf8_encode = function (string) {
                    string = string.replace(/
    /g, "
    ");
                    var utftext = "";
                    for (var n = 0; n < string.length; n++) {
                        var c = string.charCodeAt(n);
                        if (c < 128) {
                            utftext += String.fromCharCode(c);
                        } else if ((c > 127) && (c < 2048)) {
                            utftext += String.fromCharCode((c >> 6) | 192);
                            utftext += String.fromCharCode((c & 63) | 128);
                        } else {
                            utftext += String.fromCharCode((c >> 12) | 224);
                            utftext += String.fromCharCode(((c >> 6) & 63) | 128);
                            utftext += String.fromCharCode((c & 63) | 128);
                        }
     
                    }
                    return utftext;
                }
     
                // private method for UTF-8 decoding 
                _utf8_decode = function (utftext) {
                    var string = "";
                    var i = 0;
                    var c = c1 = c2 = 0;
                    while (i < utftext.length) {
                        c = utftext.charCodeAt(i);
                        if (c < 128) {
                            string += String.fromCharCode(c);
                            i++;
                        } else if ((c > 191) && (c < 224)) {
                            c2 = utftext.charCodeAt(i + 1);
                            string += String.fromCharCode(((c & 31) << 6) | (c2 & 63));
                            i += 2;
                        } else {
                            c2 = utftext.charCodeAt(i + 1);
                            c3 = utftext.charCodeAt(i + 2);
                            string += String.fromCharCode(((c & 15) << 12) | ((c2 & 63) << 6) | (c3 & 63));
                            i += 3;
                        }
                    }
                    return string;
                }
            }
    
    
  • 相关阅读:
    Populating Next Right Pointers in Each Node II
    Populating Next Right Pointers in Each Node
    Construct Binary Tree from Preorder and Inorder Traversal
    Construct Binary Tree from Inorder and Postorder Traversal
    Path Sum
    Symmetric Tree
    Solve Tree Problems Recursively
    632. Smallest Range(priority_queue)
    609. Find Duplicate File in System
    poj3159最短路spfa+邻接表
  • 原文地址:https://www.cnblogs.com/simple-blog/p/4368272.html
Copyright © 2011-2022 走看看