zoukankan      html  css  js  c++  java
  • Compress before Encrypt

    Reference

    [1] https://stackoverflow.com/questions/3538021/why-do-we-use-base64

    [2] https://dzone.com/articles/base64-encoding-java-8

    It is better to compress before encrypting.

    Any proven block cipher will reduce the data to a pseudo-random sequence of bytes that will typically yield little to no compression gain at all. Additionally, encrypting compressed data can potentially also carry the added benefit of making statistical analysis harder (though this of course does depend on the compression algorithm and whether it inserts any predictable metadata), although this isn't particularly relevant with a block cipher and a sensible operation mode (i.e. not ECB)

    So Gzip a String first and then encode it via Base64.


    public static final String compressAndEncode(String data) throws IOException {
    return base64Encode(gzipCompress(data));
    }

    public static final String decodeAndDecompress(String compressedString) throws IOException {
    return gzipDecompress(base64Decode(compressedString));
    }

    public static final byte[] gzipCompress(String data) throws IOException {
    ByteArrayOutputStream bos = new ByteArrayOutputStream(data.length());
    GZIPOutputStream gzip = new GZIPOutputStream(bos);
    gzip.write(data.getBytes(charSet));
    gzip.close();
    byte[] compressed = bos.toByteArray();
    bos.close();
    return compressed;
    }

    public static final String gzipDecompress(byte[] compressed) throws IOException {
    ByteArrayInputStream bis = new ByteArrayInputStream(compressed);
    GZIPInputStream gis = new GZIPInputStream(bis);
    byte[] bytes = IOUtils.toByteArray(gis);
    return new String(bytes, charSet);
    }

    public static final String base64Encode(byte[] data) {
    return Base64.getEncoder().encodeToString(data);
    }

    public static final byte[] base64Decode(String data) {
    return Base64.getDecoder().decode(data);
    }

    Base64

    1. Base64 encoding schemes are commonly used when there is a need to encode binary data that needs be stored and transferred over media that are designed to deal with textual data. This is to ensure that the data remains intact without modification during transport. This allows you to encode aribtrary bytes to bytes which are known to be safe to send without getting corrupted (ASCII alphanumeric characters and a couple of symbols). The disadvantage is that encoding the message using Base64 increases its length - every 3 bytes of data is encoded to 4 ASCII characters.

    2. Base 64 encoding will make it easier to debug, comparing with a byte stream.

    3. Base64 encodes each set of three bytes into four bytes. In addition the output is padded to always be a multiple of four.

    This means that the size of the base-64 representation of a string of size n is:

    ceil(n / 3) * 4
    

    So, for a 16kB array, the base-64 representation will be ceil(16*1024/3)*4 = 21848 bytes long ~= 21.8kB.

    rough approximation would be that the size of the data is increased to 4/3 of the original. 

    URL Encoding

    Most of us are used to get annoyed when we have to encode something to be later included in a URL or as a filename - the problem is that the Base64 Alphabet contains meaningful characters in both URIs and filesystems (most specifically the forward slash (/)). The second type of encoder uses the alternative "URL and Filename safe" Alphabet which includes -_ (minus and underline) instead of +/. See the following example:

    String basicEncoded = Base64.getEncoder().encodeToString("subjects?abcd".getBytes("utf-8"));
    System.out.println("Using Basic Alphabet: " + basicEncoded);
    
    String urlEncoded = Base64.getUrlEncoder().encodeToString("subjects?abcd".getBytes("utf-8"));
    System.out.println("Using URL Alphabet: " + urlEncoded);
    The output will be:
    Using Basic Alphabet: c3ViamVjdHM/YWJjZA==
    Using URL Alphabet: c3ViamVjdHM_YWJjZA==

    MIME Encoding

    The MIME encoder generates a Base64 encoded output using the Basic Alphabet but in a MIME friendly format: each line of the output is no longer than 76 characters and ends with a carriage return followed by a linefeed ( ). The following example generates a block of text (this is needed just to make sure we have enough 'body' to encode into more than 76 characters) and encodes it using the MIME encoder:

    StringBuilder sb = new StringBuilder();
    for (int t = 0; t < 10; ++t) {
     sb.append(UUID.randomUUID().toString());
    }
    
    byte[] toEncode = sb.toString().getBytes("utf-8");
    String mimeEncoded = Base64.getMimeEncoder().encodeToString(toEncode);
    System.out.println(mimeEncoded);
    The output:
    NDU5ZTFkNDEtMDVlNy00MDFiLTk3YjgtMWRlMmRkMWEzMzc5YTJkZmEzY2YtM2Y2My00Y2Q4LTk5
    ZmYtMTU1NzY0MWM5Zjk4ODA5ZjVjOGUtOGMxNi00ZmVjLTgyZjctNmVjYTU5MTAxZWUyNjQ1MjJj
    NDMtYzA0MC00MjExLTk0NWMtYmFiZGRlNDk5OTZhMDMxZGE5ZTYtZWVhYS00OGFmLTlhMjgtMDM1
    ZjAyY2QxNDUyOWZiMjI3NDctNmI3OC00YjgyLThiZGQtM2MyY2E3ZGNjYmIxOTQ1MDVkOGQtMzIz
    Yi00MDg0LWE0ZmItYzkwMGEzNDUxZTIwOTllZTJiYjctMWI3MS00YmQzLTgyYjUtZGRmYmYxNDA4
    Mjg3YTMxZjMxZmMtYTdmYy00YzMyLTkyNzktZTc2ZDc5ZWU4N2M5ZDU1NmQ4NWYtMDkwOC00YjIy
    LWIwYWItMzJiYmZmM2M0OTBm
  • 相关阅读:
    2003远程桌面不能粘贴文本的解决办法
    23号
    自定义鼠标外形
    自定义鼠标外形2.0
    hadoop与spark的处理技巧(四)推荐引擎处理技巧
    关于idea的一次踩坑记录Auto build completed with errors
    spark aggregate函数
    Spark aggregateByKey函数
    B/S与C/S的区别
    jmeter之_MD5函数与请求参数化
  • 原文地址:https://www.cnblogs.com/codingforum/p/9069287.html
Copyright © 2011-2022 走看看