이 함수는 AES(Advanced Encryption Standard) 알고리즘으로 데이터를 암호화하고 복호화합니다.
키 길이는 암호화 모드에 따라 달라집니다. -128-, -196-, -256- 모드의 키 길이는 각각 16, 24, 32바이트입니다.
초기화 벡터 길이는 항상 16바이트입니다(16바이트를 초과하는 바이트는 무시됩니다).
HMAC
도입 버전: v25.12.0
지정된 해시 알고리즘과 비밀 키를 사용해 주어진 메시지에 대한 HMAC(Hash-based Message Authentication Code)를 계산합니다.
지원되는 해시 알고리즘:
- blake2b512
- blake2s256
- md4
- md5
- md5-sha1
- mdc2
- ripemd (별칭: RIPEMD160, ripemd)
- ripemd160
- rmd160 (별칭: RIPEMD160, rmd160)
- sha1
- sha224
- sha256
- sha3-224
- sha3-256
- sha3-384
- sha3-512
- sha384
- sha512
- sha512-224
- sha512-256
- shake128
- shake256
- sm3
- ssl3-md5 (별칭: MD5, ssl3-md5)
- ssl3-sha1 (별칭: SHA1, ssl3-sha1)
- whirlpool
구문
HMAC(mode, message, key)인수
mode— 해시 알고리즘 이름입니다(대소문자 구분 없음). 지원되는 값: md5, sha1, sha224, sha256, sha384, sha512.Stringmessage— 인증할 메시지입니다.Stringkey— HMAC에 사용할 시크릿 키입니다.String
반환 값
HMAC 다이제스트가 포함된 바이너리 문자열을 반환합니다. String
예시
기본 HMAC-SHA256
SELECT hex(HMAC('sha256', 'The quick brown fox jumps over the lazy dog', 'secret_key'));┌─hex(HMAC('sha256', 'The quick brown fox jumps over the lazy dog', [HIDDEN id: 1]))─┐
│ 31FD15FA0F61FD40DC09D919D4AA5B4141A0B27C1D51E74A6789A890AAAA187C │
└────────────────────────────────────────────────────────────────────────────────────┘다양한 해시 알고리즘
SELECT
hex(HMAC('md5', 'message', 'key')) AS hmac_md5,
hex(HMAC('sha1', 'message', 'key')) AS hmac_sha1,
hex(HMAC('sha256', 'message', 'key')) AS hmac_sha256;┌─hmac_md5─────────────────────────┬─hmac_sha1────────────────────────────────┬─hmac_sha256──────────────────────────────────────────────────────┐
│ 4E4748E62B463521F6775FBF921234B5 │ 2088DF74D5F2146B48146CAF4965377E9D0BE3A4 │ 6E9EF29B75FFFC5B7ABAE527D58FDADB2FE42E7219011976917343065F58ED4A │
└──────────────────────────────────┴──────────────────────────────────────────┴──────────────────────────────────────────────────────────────────┘대소문자를 구분하지 않는 모드
SELECT
hmac('SHA256', 'message', 'key') = HMAC('sha256', 'message', 'key') AS same_result,
HMAC('SHA256', 'message', 'key') = Hmac('Sha256', 'message', 'key') AS also_same;┌─same_result─┬─also_same─┐
│ 1 │ 1 │
└─────────────┴───────────┘aes_decrypt_mysql
도입 버전: v20.12.0
MySQL의 AES_ENCRYPT 함수로 암호화된 데이터를 복호화합니다.
동일한 입력에 대해서는 decrypt와 같은 평문을 생성합니다.
key 또는 iv가 일반적으로 필요한 길이보다 길면, aes_decrypt_mysql은 MySQL의 aes_decrypt와 동일하게 동작하여 key를 "fold"하고 IV의 초과 비트는 무시합니다.
다음 복호화 모드를 지원합니다.
- aes-128-ecb, aes-192-ecb, aes-256-ecb
- aes-128-cbc, aes-192-cbc, aes-256-cbc
- aes-128-cfb128
- aes-128-ofb, aes-192-ofb, aes-256-ofb
구문
aes_decrypt_mysql(mode, ciphertext, key[, iv])인수
반환 값
복호화된 String을 반환합니다. String
예시
MySQL 데이터 복호화
-- Let's decrypt data we've previously encrypted with MySQL:
-- mysql> SET block_encryption_mode='aes-256-ofb';
-- Query OK, 0 rows affected (0.00 sec)
--
-- mysql> SELECT aes_encrypt('Secret', '123456789101213141516171819202122', 'iviviviviviviviv123456') as ciphertext;
-- +------------------------+
-- | ciphertext |
-- +------------------------+
-- | 0x24E9E4966469 |
-- +------------------------+
-- 1 row in set (0.00 sec)
SELECT aes_decrypt_mysql('aes-256-ofb', unhex('24E9E4966469'), '123456789101213141516171819202122', 'iviviviviviviviv123456') AS plaintext┌─plaintext─┐
│ Secret │
└───────────┘aes_encrypt_mysql
도입 버전: v20.12.0
MySQL의 AES_ENCRYPT 함수와 동일한 방식으로 텍스트를 암호화합니다.
생성된 암호문은 MySQL의 AES_DECRYPT 함수로 복호화할 수 있습니다.
동일한 입력에 대해서는 encrypt 함수와 같은 암호문을 생성합니다.
key 또는 iv가 일반적으로 필요한 길이보다 길면, aes_encrypt_mysql은 MySQL의 aes_encrypt와 동일하게 동작하며 key는 'fold' 처리하고 iv의 초과 비트는 무시합니다.
지원되는 암호화 모드는 다음과 같습니다.
- aes-128-ecb, aes-192-ecb, aes-256-ecb
- aes-128-cbc, aes-192-cbc, aes-256-cbc
- aes-128-ofb, aes-192-ofb, aes-256-ofb
구문
aes_encrypt_mysql(mode, plaintext, key[, iv])인수
mode— 암호화 모드입니다.Stringplaintext— 암호화할 텍스트입니다.Stringkey— 암호화 키입니다. 키 길이가mode에 필요한 길이보다 길면 MySQL 전용 키 폴딩이 수행됩니다.Stringiv— 선택 사항입니다. 초기화 벡터입니다. 처음 16바이트만 사용됩니다.String
반환 값
암호문인 바이너리 문자열입니다. String
예시
동일한 입력 비교
-- 동일한 입력값이 주어지면 encrypt와 aes_encrypt_mysql은 동일한 암호문(ciphertext)을 생성합니다:
SELECT encrypt('aes-256-ofb', 'Secret', '12345678910121314151617181920212', 'iviviviviviviviv') = aes_encrypt_mysql('aes-256-ofb', 'Secret', '12345678910121314151617181920212', 'iviviviviviviviv') AS ciphertexts_equal;┌─ciphertexts_equal─┐
│ 1 │
└───────────────────┘키가 길면 암호화에 실패함
-- 하지만 key 또는 iv가 예상보다 길면 encrypt가 실패합니다:
SELECT encrypt('aes-256-ofb', 'Secret', '123456789101213141516171819202122', 'iviviviviviviviv123');Received exception from server (version 22.6.1):
Code: 36. DB::Exception: Received from localhost:9000. DB::Exception: Invalid key size: 33 expected 32: While processing encrypt('aes-256-ofb', 'Secret', '123456789101213141516171819202122', 'iviviviviviviviv123').MySQL 호환성
-- aes_encrypt_mysql는 MySQL 호환 출력을 생성합니다:
SELECT hex(aes_encrypt_mysql('aes-256-ofb', 'Secret', '123456789101213141516171819202122', 'iviviviviviviviv123')) AS ciphertext;┌─ciphertext───┐
│ 24E9E4966469 │
└──────────────┘더 긴 IV도 동일한 결과를 냅니다
-- 더 긴 IV를 제공해도 동일한 결과가 생성되는 것을 확인하세요
SELECT hex(aes_encrypt_mysql('aes-256-ofb', 'Secret', '123456789101213141516171819202122', 'iviviviviviviviv123456')) AS ciphertext┌─ciphertext───┐
│ 24E9E4966469 │
└──────────────┘decrypt
도입 버전: v20.12.0
이 함수는 다음 모드에서 AES로 암호화된 바이너리 문자열을 복호화합니다.
- aes-128-ecb, aes-192-ecb, aes-256-ecb
- aes-128-cbc, aes-192-cbc, aes-256-cbc
- aes-128-ofb, aes-192-ofb, aes-256-ofb
- aes-128-gcm, aes-192-gcm, aes-256-gcm
- aes-128-ctr, aes-192-ctr, aes-256-ctr
- aes-128-cfb, aes-128-cfb1, aes-128-cfb8
구문
decrypt(mode, ciphertext, key[, iv, aad])인수
mode— 복호화 모드입니다.Stringciphertext— 복호화할 암호문입니다.Stringkey— 복호화 키입니다.Stringiv— 초기화 벡터입니다.-gcm모드에서는 필수이고, 그 외 모드에서는 선택 사항입니다.Stringaad— 추가 인증 데이터입니다. 이 값이 올바르지 않으면 복호화할 수 없습니다.-gcm모드에서만 동작하며, 그 외 모드에서는 예외가 발생합니다.String
반환 값
복호화된 평문을 반환합니다. String
예시
암호화된 데이터를 올바르게 복호화하기
CREATE TABLE encryption_test
(
`comment` String,
`secret` String
)
ENGINE = MergeTree
ORDER BY tuple();
INSERT INTO encryption_test VALUES
('aes-256-ofb no IV', encrypt('aes-256-ofb', 'Secret', '12345678910121314151617181920212')),
('aes-256-ofb no IV, different key', encrypt('aes-256-ofb', 'Secret', 'keykeykeykeykeykeykeykeykeykeyke')),
('aes-256-ofb with IV', encrypt('aes-256-ofb', 'Secret', '12345678910121314151617181920212', 'iviviviviviviviv')),
('aes-256-cbc no IV', encrypt('aes-256-cbc', 'Secret', '12345678910121314151617181920212'));
SELECT comment, hex(secret) FROM encryption_test;┌─comment──────────────────────────┬─hex(secret)──────────────────────┐
│ aes-256-ofb no IV │ B4972BDC4459 │
│ aes-256-ofb no IV, different key │ 2FF57C092DC9 │
│ aes-256-ofb with IV │ 5E6CB398F653 │
│ aes-256-cbc no IV │ 1BC0629A92450D9E73A00E7D02CF4142 │
└──────────────────────────────────┴──────────────────────────────────┘암호화된 데이터를 잘못 복호화하는 경우
SELECT comment, hex(decrypt('aes-256-cfb8', secret, '12345678910121314151617181920212')) AS plaintext FROM encryption_testaes-256-ofb no IV 53A69A28E815
aes-256-ofb no IV, different key C86BD2404D8A
aes-256-ofb with IV B9658159142A
aes-256-cbc no IV FC552E5096F1455997B2732FB31DCFEBencrypt
도입 버전: v20.12.0
다음 AES 모드 중 하나를 사용해 평문을 암호문으로 암호화합니다:
- aes-128-ecb, aes-192-ecb, aes-256-ecb
- aes-128-cbc, aes-192-cbc, aes-256-cbc
- aes-128-ofb, aes-192-ofb, aes-256-ofb
- aes-128-gcm, aes-192-gcm, aes-256-gcm
- aes-128-ctr, aes-192-ctr, aes-256-ctr
- aes-128-cfb, aes-128-cfb1, aes-128-cfb8
구문
encrypt(mode, plaintext, key[, iv, aad])인수
mode— 암호화 모드입니다.Stringplaintext— 암호화할 텍스트입니다.Stringkey— 암호화 키입니다.Stringiv— 초기화 벡터입니다.-gcm모드에서는 필수이며, 다른 모드에서는 선택 사항입니다.Stringaad— 추가 인증 데이터입니다. 이 값은 암호화되지는 않지만 복호화에 영향을 줍니다.-gcm모드에서만 작동하며, 다른 모드에서는 예외가 발생합니다.String
반환 값
바이너리 문자열인 암호문을 반환합니다. String
예시
암호화 예시
CREATE TABLE encryption_test
(
`comment` String,
`secret` String
)
ENGINE = MergeTree;
INSERT INTO encryption_test VALUES
('aes-256-ofb no IV', encrypt('aes-256-ofb', 'Secret', '12345678910121314151617181920212')),
('aes-256-ofb no IV, different key', encrypt('aes-256-ofb', 'Secret', 'keykeykeykeykeykeykeykeykeykeyke')),
('aes-256-ofb with IV', encrypt('aes-256-ofb', 'Secret', '12345678910121314151617181920212', 'iviviviviviviviv')),
('aes-256-cbc no IV', encrypt('aes-256-cbc', 'Secret', '12345678910121314151617181920212'));
SELECT comment, hex(secret) FROM encryption_test;┌─comment──────────────────────────┬─hex(secret)──────────────────────┐
│ aes-256-ofb no IV │ B4972BDC4459 │
│ aes-256-ofb no IV, different key │ 2FF57C092DC9 │
│ aes-256-ofb with IV │ 5E6CB398F653 │
│ aes-256-cbc no IV │ 1BC0629A92450D9E73A00E7D02CF4142 │
└──────────────────────────────────┴──────────────────────────────────┘GCM 모드 사용 예시
INSERT INTO encryption_test VALUES
('aes-256-gcm', encrypt('aes-256-gcm', 'Secret', '12345678910121314151617181920212', 'iviviviviviviviv')),
('aes-256-gcm with AAD', encrypt('aes-256-gcm', 'Secret', '12345678910121314151617181920212', 'iviviviviviviviv', 'aad'));
SELECT comment, hex(secret) FROM encryption_test WHERE comment LIKE '%gcm%';┌─comment──────────────┬─hex(secret)──────────────────────────────────┐
│ aes-256-gcm │ A8A3CCBC6426CFEEB60E4EAE03D3E94204C1B09E0254 │
│ aes-256-gcm with AAD │ A8A3CCBC6426D9A1017A0A932322F1852260A4AD6837 │
└──────────────────────┴──────────────────────────────────────────────┘tryDecrypt
도입 버전: v22.10.0
decrypt 함수와 유사하지만, 잘못된 키를 사용해 복호화에 실패한 경우 NULL을 반환합니다.
구문
tryDecrypt(mode, ciphertext, key[, iv, aad])인수
mode— 복호화 모드입니다.Stringciphertext— 복호화할 암호문입니다.Stringkey— 복호화 키입니다.Stringiv— 선택 사항입니다. 초기화 벡터입니다.-gcm모드에서는 필수이고, 다른 모드에서는 선택 사항입니다.Stringaad— 선택 사항입니다. 추가 인증 데이터입니다. 이 값이 올바르지 않으면 복호화할 수 없습니다.-gcm모드에서만 작동하며, 다른 모드에서는 예외가 발생합니다.String
반환 값
복호화된 String을 반환합니다. 복호화에 실패하면 NULL을 반환합니다. Nullable(String)
예시
테이블 생성 및 데이터 삽입
-- user_id는 고유한 사용자 ID, encrypted는 암호화된 문자열 필드, iv는 복호화/암호화를 위한 초기 벡터입니다.
-- 사용자가 자신의 ID와 encrypted 필드를 복호화하기 위한 키를 알고 있다고 가정합니다:
CREATE TABLE decrypt_null
(
dt DateTime,
user_id UInt32,
encrypted String,
iv String
)
ENGINE = MergeTree;
-- 데이터를 삽입합니다:
INSERT INTO decrypt_null VALUES
('2022-08-02 00:00:00', 1, encrypt('aes-256-gcm', 'value1', 'keykeykeykeykeykeykeykeykeykey01', 'iv1'), 'iv1'),
('2022-09-02 00:00:00', 2, encrypt('aes-256-gcm', 'value2', 'keykeykeykeykeykeykeykeykeykey02', 'iv2'), 'iv2'),
('2022-09-02 00:00:01', 3, encrypt('aes-256-gcm', 'value3', 'keykeykeykeykeykeykeykeykeykey03', 'iv3'), 'iv3');
-- 하나의 키로 복호화를 시도합니다
SELECT
dt,
user_id,
tryDecrypt('aes-256-gcm', encrypted, 'keykeykeykeykeykeykeykeykeykey02', iv) AS value
FROM decrypt_null
ORDER BY user_id ASC┌──────────────────dt─┬─user_id─┬─value──┐
│ 2022-08-02 00:00:00 │ 1 │ ᴺᵁᴸᴸ │
│ 2022-09-02 00:00:00 │ 2 │ value2 │
│ 2022-09-02 00:00:01 │ 3 │ ᴺᵁᴸᴸ │
└─────────────────────┴─────────┴────────┘