[掌眼]iOS / Android / java / node.js 通用的 AES256 加解密算法

example.m

NSString *text = @"text";
NSString *key32 = @"xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx";

NSData *data = [text dataUsingEncoding:NSUTF8StringEncoding];
NSString *encryptedData = [[data AES256EncryptWithKey:key32] base64EncodedStringWithOptions:0];

NSLog(@"%@",encryptedData); # => QfpLKBn20BZI1NIhigOo6g==

NSData+AES256.m

- (NSData *)AES256EncryptWithKey:(NSString *)key {
    // ‘key‘ should be 32 bytes for AES256, will be null-padded otherwise
    char keyPtr[kCCKeySizeAES256+1]; // room for terminator (unused)
    bzero(keyPtr, sizeof(keyPtr)); // fill with zeroes (for padding)

    // fetch key data
    [key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];

    NSUInteger dataLength = [self length];

    //See the doc: For block ciphers, the output size will always be less than or
    //equal to the input size plus the size of one block.
    //That‘s why we need to add the size of one block here
    size_t bufferSize = dataLength + kCCBlockSizeAES128;
    void *buffer = malloc(bufferSize);

    size_t numBytesEncrypted = 0;
    CCCryptorStatus cryptStatus = CCCrypt(kCCEncrypt, kCCAlgorithmAES128, kCCOptionPKCS7Padding,
                                          keyPtr, kCCKeySizeAES256,
                                          NULL /* initialization vector (optional) */,
                                          [self bytes], dataLength, /* input */
                                          buffer, bufferSize, /* output */
                                          &numBytesEncrypted);
    if (cryptStatus == kCCSuccess) {
        //the returned NSData takes ownership of the buffer and will free it on deallocation
        return [NSData dataWithBytesNoCopy:buffer length:numBytesEncrypted];
    }

    free(buffer); //free the buffer;
    return nil;
}

- (NSData *)AES256DecryptWithKey:(NSString *)key {
    // ‘key‘ should be 32 bytes for AES256, will be null-padded otherwise
    char keyPtr[kCCKeySizeAES256+1]; // room for terminator (unused)
    bzero(keyPtr, sizeof(keyPtr)); // fill with zeroes (for padding)

    // fetch key data
    [key getCString:keyPtr maxLength:sizeof(keyPtr) encoding:NSUTF8StringEncoding];

    NSUInteger dataLength = [self length];

    //See the doc: For block ciphers, the output size will always be less than or
    //equal to the input size plus the size of one block.
    //That‘s why we need to add the size of one block here
    size_t bufferSize = dataLength + kCCBlockSizeAES128;
    void *buffer = malloc(bufferSize);

    size_t numBytesDecrypted = 0;
    CCCryptorStatus cryptStatus = CCCrypt(kCCDecrypt, kCCAlgorithmAES128, kCCOptionPKCS7Padding,
                                          keyPtr, kCCKeySizeAES256,
                                          NULL /* initialization vector (optional) */,
                                          [self bytes], dataLength, /* input */
                                          buffer, bufferSize, /* output */
                                          &numBytesDecrypted);

    if (cryptStatus == kCCSuccess) {
        //the returned NSData takes ownership of the buffer and will free it on deallocation
        return [NSData dataWithBytesNoCopy:buffer length:numBytesDecrypted];
    }

    free(buffer); //free the buffer;
    return nil;
}

AES256.java

/**
 * Encodes a String in AES-256 with a given key
 *
 * @param context
 * @param password
 * @param text
 * @return String Base64 and AES encoded String
 */
public static String encode(String keyString, String stringToEncode) throws NullPointerException {
    if (keyString.length() == 0 || keyString == null) {
        throw new NullPointerException("Please give Password");
    }

    if (stringToEncode.length() == 0 || stringToEncode == null) {
        throw new NullPointerException("Please give text");
    }

    try {
        SecretKeySpec skeySpec = getKey(keyString);
        byte[] clearText = stringToEncode.getBytes("UTF8");

        // IMPORTANT TO GET SAME RESULTS ON iOS and ANDROID
        final byte[] iv = new byte[16];
        Arrays.fill(iv, (byte) 0x00);
        IvParameterSpec ivParameterSpec = new IvParameterSpec(iv);

        // Cipher is not thread safe
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding");
        cipher.init(Cipher.ENCRYPT_MODE, skeySpec, ivParameterSpec);

        String encrypedValue = Base64.encodeToString(cipher.doFinal(clearText), Base64.DEFAULT);
        Log.d("jacek", "Encrypted: " + stringToEncode + " -> " + encrypedValue);
        return encrypedValue;

    } catch (InvalidKeyException e) {
        e.printStackTrace();
    } catch (UnsupportedEncodingException e) {
        e.printStackTrace();
    } catch (NoSuchAlgorithmException e) {
        e.printStackTrace();
    } catch (BadPaddingException e) {
        e.printStackTrace();
    } catch (NoSuchPaddingException e) {
        e.printStackTrace();
    } catch (IllegalBlockSizeException e) {
        e.printStackTrace();
    } catch (InvalidAlgorithmParameterException e) {
        e.printStackTrace();
    }
    return "";
}

/**
 * Decodes a String using AES-256 and Base64
 *
 * @param context
 * @param password
 * @param text
 * @return desoded String
 */
public String decode(String password, String text) throws NullPointerException {

    if (password.length() == 0 || password == null) {
        throw new NullPointerException("Please give Password");
    }

    if (text.length() == 0 || text == null) {
        throw new NullPointerException("Please give text");
    }

    try {
        SecretKey key = getKey(password);

        // IMPORTANT TO GET SAME RESULTS ON iOS and ANDROID
        final byte[] iv = new byte[16];
        Arrays.fill(iv, (byte) 0x00);
        IvParameterSpec ivParameterSpec = new IvParameterSpec(iv);

        byte[] encrypedPwdBytes = Base64.decode(text, Base64.DEFAULT);
        // cipher is not thread safe
        Cipher cipher = Cipher.getInstance("AES/CBC/PKCS7Padding");
        cipher.init(Cipher.DECRYPT_MODE, key, ivParameterSpec);
        byte[] decrypedValueBytes = (cipher.doFinal(encrypedPwdBytes));

        String decrypedValue = new String(decrypedValueBytes);
        Log.d(LOG_TAG, "Decrypted: " + text + " -> " + decrypedValue);
        return decrypedValue;

    } catch (InvalidKeyException e) {
        e.printStackTrace();
    } catch (UnsupportedEncodingException e) {
        e.printStackTrace();
    } catch (NoSuchAlgorithmException e) {
        e.printStackTrace();
    } catch (BadPaddingException e) {
        e.printStackTrace();
    } catch (NoSuchPaddingException e) {
        e.printStackTrace();
    } catch (IllegalBlockSizeException e) {
        e.printStackTrace();
    } catch (InvalidAlgorithmParameterException e) {
        e.printStackTrace();
    }
    return "";
}

/**
 * Generates a SecretKeySpec for given password
 *
 * @param password
 * @return SecretKeySpec
 * @throws UnsupportedEncodingException
 */
private static SecretKeySpec getKey(String password) throws UnsupportedEncodingException {

    // You can change it to 128 if you wish
    int keyLength = 256;
    byte[] keyBytes = new byte[keyLength / 8];
    // explicitly fill with zeros
    Arrays.fill(keyBytes, (byte) 0x0);

    // if password is shorter then key length, it will be zero-padded
    // to key length
    byte[] passwordBytes = password.getBytes("UTF-8");
    int length = passwordBytes.length < keyBytes.length ? passwordBytes.length : keyBytes.length;
    System.arraycopy(passwordBytes, 0, keyBytes, 0, length);
    SecretKeySpec key = new SecretKeySpec(keyBytes, "AES");
    return key;
}

node.js

crypto = require(‘crypto‘)
key = ‘xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx‘
iv = new Buffer(16)
iv.fill(0)

text = ‘text‘

cipher = crypto.createCipheriv(‘aes-256-cbc‘, key, iv)
output = cipher.update(‘text‘, ‘utf8‘, ‘base64‘)
output += cipher.final(‘base64‘)

console.log output # => QfpLKBn20BZI1NIhigOo6g==

[掌眼]iOS / Android / java / node.js 通用的 AES256 加解密算法,布布扣,bubuko.com

时间: 2024-10-13 20:56:51

[掌眼]iOS / Android / java / node.js 通用的 AES256 加解密算法的相关文章

实现与JS相同的Des加解密算法【转】

Java代码 import java.util.ArrayList; import java.util.List; /** * DES加密/解密 * * @Copyright Copyright (c) 2015 * @author liuyazhuang * @see DESCore */ public class Des { public Des() { } public static void main(String[] args) { Des desObj = new Des(); St

[掌眼]IOS UIWebView Long press save image 长按图片保存到手机

具体效果可下载"掌眼"古玩江湖进行测试:http://bbs.guwanch.com ViewController.h @interface ViewController : CDVViewController<UIActionSheetDelegate>{ NSTimer *_timer; // 用于UIWebView保存图片 int _gesState; // 用于UIWebView保存图片 NSString *_imgURL; // 用于UIWebView保存图片 }

java 使用pem密钥进行RSA加解密

1.使用openssl生成私钥和公钥 openssl下载地址:http://www.openssl.org/source openssl生成私钥命令:  genrsa -out rsa_private_key.pem 1024 openssl生成公钥命令:  rsa -in rsa_private_key.pem -pubout -out rsa_public_key.pem 2.此时在openssl安装目录下的bin文件夹可以看到 rsa_private_key.pem 和 rsa_publi

编写浏览器和Node.js通用的JavaScript模块

长期以来JavaScript语言本身不提供模块化的支持, ES6中终于给出了 from, import等关键字来进行模块化的代码组织. 但CommonJS.AMD等规范已经被广为使用,如果希望你的JavaScript同时支持浏览器和Node.js, 现在只有这几种方式: 通过 browserify等工具进行转换. 提供浏览器端CommonJS框架,比如这个简易的 CommonJS 实现. 通过小心的编码来支持多种环境. browserify几乎可以保证Node.js下测试通过的代码在浏览器中仍然

多语言(Java&amp;C#&amp;Ruby&amp;C++&amp;Objective-C&amp;Android)互通的TripleDES加解密算法实现

直入主题:前段时间根据公司对开发API的安全性要求,采用了小数据加密验证的方式,根据需求采用了三重DES加密算法.在实施的过程中发现各个语言之间加密由于加密补位的方式有所不同,导致不同语言之间加密之后无法相互解析.在强大的会联网技术和公司其他同事的支持下,最终整合了集Java,C#,Ruby,C++,Objective-C,Android多语言的可以互通的TripleDES加密算法,虽然在AES加密推崇的今天DES有些乏力,但小可大胆贴上代码,希望能给大家提供一些思路. Java DES加密(J

前端JS后端nodeJs 实现加解密; 个人理解

//说明: // 1.如果加密解密涉及到前端和后端,则这里的key要保持和后端的key一致 // 2.AES的算法模式有好几种(ECB,CBC,CFB,OFB),所以也要和后端保持一致 // 3.AES的补码方式有两种(PKS5,PKS7),所以也要和后端保持一致 // 4.AES的密钥长度有三种(128,192,256,默认是128),所以也要和后端保持一致 // 5.AES的加密结果编码方式有两种(base64和十六进制),具体怎么选择由自己定,但是加密和解密的编码方式要统////一 //

Android数据库安全解决方案,使用SQLCipher进行加解密

转载请注明出处:http://blog.csdn.net/guolin_blog/article/details/11952409 我们都知道,Android系统内置了SQLite数据库,并且提供了一整套的API用于对数据库进行增删改查操作.数据库存储是我们经常会使用到的一种存储方式,相信大多数朋友对它的使用方法都已经比较熟悉了吧.在Android中,我们既可以使用原生的SQL语句来对数据进行操作,也可以使用Android API提供的CRUD方法来对数据库进行操作,两种方式各有特点,选择使用哪

Java实现RSA密钥对并在加解密、加签验签中应用的实例

一.项目结构 二.代码具体实现 1.密钥对生成的两种方式:一种生成公钥私文件,一种生成公钥私串 KeyPairGenUtil.java package com.wangjinxiang.genkey.util; import java.io.FileOutputStream; import java.io.ObjectOutputStream; import java.security.Key; import java.security.KeyPair; import java.security

Node.js——优先从缓存加载

main中执行require操作,目的是获取接口对象,所以多次引用b,并不会重复执行模块内部的输入输出,因为缓存中已经存在 原文地址:https://www.cnblogs.com/wuqiuxue/p/9180586.html