diff --git a/security/DataSecurity/README.md b/security/DataSecurity/README.md
new file mode 100644
index 0000000000000000000000000000000000000000..79a6513cf2da9a2e321fba0012c28c38799aa161
--- /dev/null
+++ b/security/DataSecurity/README.md
@@ -0,0 +1,3 @@
+# Data Security
+
+- You can call encryption and decryption APIs to protect the security of your applications.
\ No newline at end of file
diff --git a/security/DataSecurity/README_zh.md b/security/DataSecurity/README_zh.md
new file mode 100644
index 0000000000000000000000000000000000000000..feea55eda3c9398900960f3e25fef6e2594beb9b
--- /dev/null
+++ b/security/DataSecurity/README_zh.md
@@ -0,0 +1,3 @@
+# 数据安全
+
+- 支持开发者调用安全加解密接口来达到安全防护作用。
\ No newline at end of file
diff --git a/security/DataSecurity/build.gradle b/security/DataSecurity/build.gradle
new file mode 100644
index 0000000000000000000000000000000000000000..e76a14f743baa5377849b43abf29dd0fe29b6478
--- /dev/null
+++ b/security/DataSecurity/build.gradle
@@ -0,0 +1,34 @@
+// Top-level build file where you can add configuration options common to all sub-projects/modules.
+apply plugin: 'com.huawei.ohos.app'
+
+ohos {
+ compileSdkVersion 5
+ defaultConfig {
+ compatibleSdkVersion 4
+ }
+}
+buildscript {
+ repositories {
+ maven {
+ url 'https://repo.huaweicloud.com/repository/maven/'
+ }
+ maven {
+ url 'https://developer.huawei.com/repo/'
+ }
+ jcenter()
+ }
+ dependencies {
+ classpath 'com.huawei.ohos:hap:2.4.4.2'
+ }
+}
+allprojects {
+ repositories {
+ maven {
+ url 'https://repo.huaweicloud.com/repository/maven/'
+ }
+ maven {
+ url 'https://developer.huawei.com/repo/'
+ }
+ jcenter()
+ }
+}
\ No newline at end of file
diff --git a/security/DataSecurity/entry/build.gradle b/security/DataSecurity/entry/build.gradle
new file mode 100644
index 0000000000000000000000000000000000000000..1324a93eda46cb945cc94de68b1cb0d1bcca10d1
--- /dev/null
+++ b/security/DataSecurity/entry/build.gradle
@@ -0,0 +1,18 @@
+apply plugin: 'com.huawei.ohos.hap'
+ohos {
+ compileSdkVersion 5
+ defaultConfig {
+ compatibleSdkVersion 4
+ }
+ buildTypes {
+ release {
+ proguardOpt {
+ proguardEnabled false
+ rulesFiles 'proguard-rules.pro'
+ }
+ }
+ }
+}
+dependencies {
+ implementation fileTree(dir: 'libs', include: ['*.jar'])
+}
diff --git a/security/DataSecurity/entry/src/main/config.json b/security/DataSecurity/entry/src/main/config.json
new file mode 100644
index 0000000000000000000000000000000000000000..e5f1bf7961cfd58bfd326458704b96bcbf9365ef
--- /dev/null
+++ b/security/DataSecurity/entry/src/main/config.json
@@ -0,0 +1,48 @@
+{
+ "app": {
+ "bundleName": "ohos.samples.datasecurity",
+ "version": {
+ "code": 1000000,
+ "name": "1.0"
+ }
+ },
+ "deviceConfig": {},
+ "module": {
+ "package": "ohos.samples.datasecurity",
+ "name": ".MainAbility",
+ "reqCapabilities": [
+ "video_support"
+ ],
+ "deviceType": [
+ "default"
+ ],
+ "distro": {
+ "deliveryWithInstall": true,
+ "moduleName": "entry",
+ "moduleType": "entry",
+ "installationFree":false
+ },
+ "abilities": [
+ {
+ "skills": [
+ {
+ "entities": [
+ "entity.system.home"
+ ],
+ "actions": [
+ "action.system.home"
+ ]
+ }
+ ],
+ "orientation": "unspecified",
+ "formsEnabled": false,
+ "name": ".MainAbility",
+ "icon": "$media:icon",
+ "description": "$string:mainability_description",
+ "label": "$string:app_name",
+ "type": "page",
+ "launchType": "standard"
+ }
+ ]
+ }
+}
\ No newline at end of file
diff --git a/security/DataSecurity/entry/src/main/java/ohos/samples/datasecurity/MainAbility.java b/security/DataSecurity/entry/src/main/java/ohos/samples/datasecurity/MainAbility.java
new file mode 100644
index 0000000000000000000000000000000000000000..7d407bfa3d75cd5f940cf75c3a76c990d18c2492
--- /dev/null
+++ b/security/DataSecurity/entry/src/main/java/ohos/samples/datasecurity/MainAbility.java
@@ -0,0 +1,32 @@
+/*
+ * Copyright (c) 2021 Huawei Device Co., Ltd.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package ohos.samples.datasecurity;
+
+import ohos.samples.datasecurity.slice.MainAbilitySlice;
+
+import ohos.aafwk.ability.Ability;
+import ohos.aafwk.content.Intent;
+
+/**
+ * Data Security MainAbility
+ */
+public class MainAbility extends Ability {
+ @Override
+ public void onStart(Intent intent) {
+ super.onStart(intent);
+ super.setMainRoute(MainAbilitySlice.class.getName());
+ }
+}
diff --git a/security/DataSecurity/entry/src/main/java/ohos/samples/datasecurity/slice/MainAbilitySlice.java b/security/DataSecurity/entry/src/main/java/ohos/samples/datasecurity/slice/MainAbilitySlice.java
new file mode 100644
index 0000000000000000000000000000000000000000..10d7084db161127d8e85b796d53555666a591055
--- /dev/null
+++ b/security/DataSecurity/entry/src/main/java/ohos/samples/datasecurity/slice/MainAbilitySlice.java
@@ -0,0 +1,160 @@
+/*
+ * Copyright (c) 2021 Huawei Device Co., Ltd.
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package ohos.samples.datasecurity.slice;
+
+import ohos.samples.datasecurity.MainAbility;
+import ohos.samples.datasecurity.ResourceTable;
+
+import ohos.aafwk.ability.AbilitySlice;
+import ohos.aafwk.content.Intent;
+import ohos.agp.components.Component;
+import ohos.agp.components.Text;
+import ohos.hiviewdfx.HiLog;
+import ohos.hiviewdfx.HiLogLabel;
+import ohos.security.keystore.KeyGenAlgorithmParaSpec;
+import ohos.security.keystore.KeyStoreConstants;
+
+import java.io.IOException;
+import java.nio.charset.StandardCharsets;
+import java.security.InvalidAlgorithmParameterException;
+import java.security.InvalidKeyException;
+import java.security.Key;
+import java.security.KeyPair;
+import java.security.KeyPairGenerator;
+import java.security.KeyStore;
+import java.security.KeyStoreException;
+import java.security.NoSuchAlgorithmException;
+import java.security.NoSuchProviderException;
+import java.security.PrivateKey;
+import java.security.UnrecoverableKeyException;
+import java.security.cert.CertificateException;
+import java.util.Base64;
+import java.util.Objects;
+import java.util.Optional;
+
+import javax.crypto.BadPaddingException;
+import javax.crypto.Cipher;
+import javax.crypto.IllegalBlockSizeException;
+import javax.crypto.NoSuchPaddingException;
+
+/**
+ * MainAbilitySlice
+ */
+public class MainAbilitySlice extends AbilitySlice {
+ private static final String TAG = MainAbility.class.getSimpleName();
+
+ private static final HiLogLabel LABEL_LOG = new HiLogLabel(3, 0xD000F00, TAG);
+
+ private static final String PLAIN_TEXT = "Hello World!";
+
+ private static final String KEY_STORE = "HarmonyKeyStore";
+
+ private static final String KEY_PAIR_ALIAS = "HarmonyKeyPair";
+
+ private static final String ENCRYPT_ALGORITHM = "RSA/ECB/OAEPWithSHA-256AndMGF1Padding";
+
+ private static final String PROVIDER = "HarmonyKeyStoreBCWorkaround";
+
+ private static final String SIGNATURE_PADDING = "PSS";
+
+ private Text resultText;
+
+ private String result;
+
+ @Override
+ public void onStart(Intent intent) {
+ super.onStart(intent);
+ super.setUIContent(ResourceTable.Layout_main_ability_slice);
+ initComponents();
+ }
+
+ private void initComponents() {
+ resultText = (Text) findComponentById(ResourceTable.Id_result_text);
+ Component encryptButton = findComponentById(ResourceTable.Id_encrypt_button);
+ Component decryptButton = findComponentById(ResourceTable.Id_decrypt_button);
+ encryptButton.setClickedListener(component -> encrypt());
+ decryptButton.setClickedListener(component -> decrypt());
+ }
+
+ private Optional getSecKey() {
+ try {
+ KeyPairGenerator keyPairGenerator = KeyPairGenerator.getInstance(KeyStoreConstants.SEC_KEY_ALGORITHM_RSA,
+ KEY_STORE);
+ KeyGenAlgorithmParaSpec.Builder builder = new KeyGenAlgorithmParaSpec.Builder(
+ KEY_PAIR_ALIAS).setSecKeyUsagePurposes(
+ KeyStoreConstants.PURPOSE_CAN_ENCRYPT | KeyStoreConstants.PURPOSE_CAN_DECRYPT
+ | KeyStoreConstants.PURPOSE_CAN_SIGN | KeyStoreConstants.PURPOSE_CAN_VERIFY)
+ .addSecKeyCryptoAttr(KeyStoreConstants.CRYPTO_PARAMETER_BLOCK_MODE,
+ KeyStoreConstants.SEC_BLOCK_MODE_ECB)
+ .addSecKeyCryptoAttr(KeyStoreConstants.CRYPTO_PARAMETER_ENCRYPT_PADDING,
+ KeyStoreConstants.OPTIMAL_ASYMMETRIC_ENCRYPTION_PADDING)
+ .addSecKeyCryptoAttr(KeyStoreConstants.CRYPTO_PARAMETER_DIGEST,
+ KeyStoreConstants.DIGEST_ALGORITHM_SHA256)
+ .addSecKeyCryptoAttr(KeyStoreConstants.CRYPTO_PARAMETER_SIGNATURE_PADDING, SIGNATURE_PADDING);
+ KeyGenAlgorithmParaSpec keyGenAlgorithmParaSpec = builder.createKeyGenAlgorithmParaSpec();
+ keyPairGenerator.initialize(keyGenAlgorithmParaSpec);
+ return Optional.of(keyPairGenerator.generateKeyPair());
+ } catch (NoSuchProviderException | NoSuchAlgorithmException | InvalidAlgorithmParameterException e) {
+ HiLog.error(LABEL_LOG, "%{public}s", "getSecKey exception.");
+ return Optional.empty();
+ }
+ }
+
+ private void encrypt() {
+ try {
+ Optional keyPairOptional = getSecKey();
+ KeyPair keyPair = keyPairOptional.get();
+ Cipher cipher = Cipher.getInstance(ENCRYPT_ALGORITHM, PROVIDER);
+ cipher.init(Cipher.ENCRYPT_MODE, keyPair.getPublic());
+ byte[] bytes = cipher.doFinal(PLAIN_TEXT.getBytes(StandardCharsets.UTF_8));
+ result = Base64.getEncoder().encodeToString(bytes);
+ resultText.setText(result);
+ } catch (NoSuchAlgorithmException | NoSuchPaddingException | NoSuchProviderException
+ | InvalidKeyException | BadPaddingException | IllegalBlockSizeException e) {
+ HiLog.error(LABEL_LOG, "%{public}s", "encrypt exception.");
+ }
+ }
+
+ private void decrypt() {
+ if (Objects.isNull(result) || PLAIN_TEXT.equals(result)) {
+ HiLog.error(LABEL_LOG, "%{public}s", "result is null or " + PLAIN_TEXT.equals(result));
+ return;
+ } else {
+ try {
+ KeyStore keyStore = KeyStore.getInstance(KEY_STORE);
+ keyStore.load(null);
+ Key key = keyStore.getKey(KEY_PAIR_ALIAS, null);
+ PrivateKey privateKey = null;
+ if (key instanceof PrivateKey) {
+ privateKey = (PrivateKey) key;
+ } else {
+ HiLog.error(LABEL_LOG, "key is not instance of PrivateKey.");
+ return;
+ }
+ byte[] bytes = Base64.getDecoder().decode(result);
+ Cipher cipher = Cipher.getInstance(ENCRYPT_ALGORITHM, PROVIDER);
+ cipher.init(Cipher.DECRYPT_MODE, privateKey);
+ result = new String(cipher.doFinal(bytes)).trim();
+ resultText.setText(result);
+ } catch (KeyStoreException | CertificateException | IOException | NoSuchAlgorithmException
+ | UnrecoverableKeyException | NoSuchPaddingException | NoSuchProviderException
+ | InvalidKeyException | BadPaddingException | IllegalBlockSizeException e) {
+ HiLog.error(LABEL_LOG, "%{public}s", "decrypt exception.");
+ }
+ }
+ }
+}
+
diff --git a/security/DataSecurity/entry/src/main/resources/base/element/string.json b/security/DataSecurity/entry/src/main/resources/base/element/string.json
new file mode 100644
index 0000000000000000000000000000000000000000..af0198f6c2c5a821e4952404ada8cced67ceb58d
--- /dev/null
+++ b/security/DataSecurity/entry/src/main/resources/base/element/string.json
@@ -0,0 +1,12 @@
+{
+ "string": [
+ {
+ "name": "app_name",
+ "value": "DataSecurity"
+ },
+ {
+ "name": "mainability_description",
+ "value": "hap sample empty page"
+ }
+ ]
+}
\ No newline at end of file
diff --git a/security/DataSecurity/entry/src/main/resources/base/graphic/button_background.xml b/security/DataSecurity/entry/src/main/resources/base/graphic/button_background.xml
new file mode 100644
index 0000000000000000000000000000000000000000..6501645111d9237119d38999c7d9889d11905434
--- /dev/null
+++ b/security/DataSecurity/entry/src/main/resources/base/graphic/button_background.xml
@@ -0,0 +1,23 @@
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/security/DataSecurity/entry/src/main/resources/base/layout/main_ability_slice.xml b/security/DataSecurity/entry/src/main/resources/base/layout/main_ability_slice.xml
new file mode 100644
index 0000000000000000000000000000000000000000..73157ddcd4fea75b4c464c74f1d5c4b35c56a610
--- /dev/null
+++ b/security/DataSecurity/entry/src/main/resources/base/layout/main_ability_slice.xml
@@ -0,0 +1,98 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/security/DataSecurity/entry/src/main/resources/base/media/icon.png b/security/DataSecurity/entry/src/main/resources/base/media/icon.png
new file mode 100644
index 0000000000000000000000000000000000000000..ce307a8827bd75456441ceb57d530e4c8d45d36c
Binary files /dev/null and b/security/DataSecurity/entry/src/main/resources/base/media/icon.png differ
diff --git a/security/DataSecurity/screenshots/phone/decrypt.png b/security/DataSecurity/screenshots/phone/decrypt.png
new file mode 100644
index 0000000000000000000000000000000000000000..865e554e13162f11fcdd6fa7cd96d9a9a1158614
Binary files /dev/null and b/security/DataSecurity/screenshots/phone/decrypt.png differ
diff --git a/security/DataSecurity/screenshots/phone/encrypt.png b/security/DataSecurity/screenshots/phone/encrypt.png
new file mode 100644
index 0000000000000000000000000000000000000000..fa29d639623446993da354e515db0fe63160c768
Binary files /dev/null and b/security/DataSecurity/screenshots/phone/encrypt.png differ
diff --git a/security/DataSecurity/screenshots/phone/main.png b/security/DataSecurity/screenshots/phone/main.png
new file mode 100644
index 0000000000000000000000000000000000000000..e579f14e08ef2d4d54252370f74b791d5b101319
Binary files /dev/null and b/security/DataSecurity/screenshots/phone/main.png differ
diff --git a/security/DataSecurity/settings.gradle b/security/DataSecurity/settings.gradle
new file mode 100644
index 0000000000000000000000000000000000000000..4773db73233a570c2d0c01a22e75321acfbf7a07
--- /dev/null
+++ b/security/DataSecurity/settings.gradle
@@ -0,0 +1 @@
+include ':entry'