C# 與 php 7.1 資料傳輸以DES加解密

原本在 php 7.0 及之前可以直接用 mcrypt,但是在 7.1 之後就被拿掉了,除非用 PCEL 去裝,或者使用其他的 library,要不然應該就只能使用 openssl 的加解密。

原本應該是很容易的事情,但是因為 C# 跟 php 兩邊的寫法實在差很大,其中 php 用 openssl 做加解密真的方便很多,麻煩的主要是在 C# 這邊...

php 使用 openssl 完成 DES 加解密

$password = '12345678'; //DES 8 digit password
var_dump($password);

$method = "des-cbc";
var_dump($method);

$plain = "this is a book";
$iv = $password;

$cipher = openssl_encrypt($plain, $method, $password, 0, $iv);
var_dump($cipher);

var_dump(openssl_decrypt($cipher, $method, $password, 0, $iv));

C#實作DES加解密

using System;
using System.Collections.Generic;
using System.IO;
using System.Security.Cryptography;
using System.Text;

namespace MySecure
{
    public static class MyEncryption
    {

        /// 
        /// DES Encryption
        /// 
        /// Plain text for encryption.
        /// keyfor encryption, length = 8
        /// Return encrypted string. If fail, return null.
        public static string EncryptDES(string encryptString, string encryptKey = "12345678")
        {
            try
            {
                DESCryptoServiceProvider des = new DESCryptoServiceProvider();
                byte[] key = Encoding.ASCII.GetBytes(encryptKey);
                byte[] iv = Encoding.ASCII.GetBytes(encryptKey);
                byte[] dataByteArray = Encoding.UTF8.GetBytes(encryptString);

                des.Key = key;
                des.IV = iv;
                string encrypt = "";
                using (MemoryStream ms = new MemoryStream())
                using (CryptoStream cs = new CryptoStream(ms, des.CreateEncryptor(), CryptoStreamMode.Write))
                {
                    cs.Write(dataByteArray, 0, dataByteArray.Length);
                    cs.FlushFinalBlock();
                    encrypt = Convert.ToBase64String(ms.ToArray());
                }
                return encrypt;
            }
            catch
            {
                return null;
            }
        }

        /// 
        /// DES Decryption
        /// 
        /// Cipher text for decryption.
        /// key for decrypt, length = 8
        /// Return decripted string. If fail, return null.
        public static string DecryptDES(string cipher, string decryptKey = "12345678")
        {
            try
            {
                DESCryptoServiceProvider des = new DESCryptoServiceProvider();
                byte[] key = Encoding.ASCII.GetBytes(decryptKey);
                byte[] iv = Encoding.ASCII.GetBytes(decryptKey);
                des.Key = key;
                des.IV = iv;

                byte[] dataByteArray = Convert.FromBase64String(cipher);
                using (MemoryStream ms = new MemoryStream())
                {
                    using (CryptoStream cs = new CryptoStream(ms, des.CreateDecryptor(), CryptoStreamMode.Write))
                    {
                        cs.Write(dataByteArray, 0, dataByteArray.Length);
                        cs.FlushFinalBlock();
                        return Encoding.UTF8.GetString(ms.ToArray());
                    }
                }
            }
            catch
            {
                return null;
            }
        }
    }
}

呼叫使用

using System;
using System.Collections.Generic;
using System.Threading.Tasks;
using MySecure;

namespace TestConsoleApplication1
{
    class Program
    {
        static void Main(string[] args)
        {
            string plain = "this is a book";
            Console.WriteLine(plain);
            string cipher = MyEncryption.EncryptDES(plain, "12345678");
            Console.WriteLine(cipher);
            Console.WriteLine(MyEncryption.DecryptDES(cipher, "12345678"));
            Console.ReadLine();
        }
    }
}