react-native-security-suite 0.1.2 → 0.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (55) hide show
  1. package/README.md +40 -3
  2. package/android/.gradle/7.4/checksums/checksums.lock +0 -0
  3. package/android/.gradle/7.4/checksums/md5-checksums.bin +0 -0
  4. package/android/.gradle/7.4/checksums/sha1-checksums.bin +0 -0
  5. package/android/.gradle/7.4/dependencies-accessors/dependencies-accessors.lock +0 -0
  6. package/android/.gradle/7.4/dependencies-accessors/gc.properties +0 -0
  7. package/android/.gradle/7.4/executionHistory/executionHistory.bin +0 -0
  8. package/android/.gradle/7.4/executionHistory/executionHistory.lock +0 -0
  9. package/android/.gradle/7.4/fileChanges/last-build.bin +0 -0
  10. package/android/.gradle/7.4/fileHashes/fileHashes.bin +0 -0
  11. package/android/.gradle/7.4/fileHashes/fileHashes.lock +0 -0
  12. package/android/.gradle/7.4/fileHashes/resourceHashesCache.bin +0 -0
  13. package/android/.gradle/7.4/gc.properties +0 -0
  14. package/android/.gradle/buildOutputCleanup/buildOutputCleanup.lock +0 -0
  15. package/android/.gradle/buildOutputCleanup/cache.properties +2 -0
  16. package/android/.gradle/buildOutputCleanup/outputFiles.bin +0 -0
  17. package/android/.gradle/file-system.probe +0 -0
  18. package/android/.gradle/vcs-1/gc.properties +0 -0
  19. package/android/.idea/compiler.xml +6 -0
  20. package/android/.idea/gradle.xml +17 -0
  21. package/android/.idea/jarRepositories.xml +40 -0
  22. package/android/.idea/misc.xml +10 -0
  23. package/android/.idea/vcs.xml +6 -0
  24. package/android/gradle/wrapper/gradle-wrapper.jar +0 -0
  25. package/android/gradle/wrapper/gradle-wrapper.properties +5 -0
  26. package/android/gradlew +234 -0
  27. package/android/gradlew.bat +89 -0
  28. package/android/local.properties +8 -0
  29. package/android/src/main/java/com/reactnativesecuritysuite/SecuritySuiteModule.java +182 -18
  30. package/android/src/main/java/com/reactnativesecuritysuite/SecuritySuitePackage.java +12 -12
  31. package/android/src/main/java/com/reactnativesecuritysuite/StorageEncryption.java +53 -0
  32. package/ios/DataHashingMethods.swift +196 -0
  33. package/ios/SecuritySuite-Bridging-Header.h +1 -0
  34. package/ios/SecuritySuite.m +14 -0
  35. package/ios/SecuritySuite.swift +129 -0
  36. package/ios/SecuritySuite.xcodeproj/project.pbxproj +9 -15
  37. package/ios/SecuritySuite.xcodeproj/project.xcworkspace/contents.xcworkspacedata +7 -0
  38. package/ios/SecuritySuite.xcodeproj/project.xcworkspace/xcshareddata/IDEWorkspaceChecks.plist +8 -0
  39. package/ios/SecuritySuite.xcodeproj/project.xcworkspace/xcuserdata/Navabi.xcuserdatad/UserInterfaceState.xcuserstate +0 -0
  40. package/ios/SecuritySuite.xcodeproj/xcuserdata/Navabi.xcuserdatad/xcschemes/xcschememanagement.plist +14 -0
  41. package/ios/StorageEncryption.swift +81 -0
  42. package/lib/commonjs/helpers.js +19 -0
  43. package/lib/commonjs/helpers.js.map +1 -0
  44. package/lib/commonjs/index.js +173 -1
  45. package/lib/commonjs/index.js.map +1 -1
  46. package/lib/module/helpers.js +10 -0
  47. package/lib/module/helpers.js.map +1 -0
  48. package/lib/module/index.js +143 -0
  49. package/lib/module/index.js.map +1 -1
  50. package/lib/typescript/helpers.d.ts +1 -0
  51. package/lib/typescript/index.d.ts +19 -0
  52. package/package.json +12 -1
  53. package/react-native-security-suite.podspec +1 -1
  54. package/src/helpers.ts +8 -0
  55. package/src/index.tsx +195 -3
@@ -1,3 +1,22 @@
1
1
  declare const SecuritySuite: any;
2
+ export declare const getPublicKey: () => Promise<string>;
3
+ export declare const getSharedKey: (serverPublicKey: string) => Promise<string>;
4
+ export declare const encryptBySharedKey: (input: string) => Promise<string>;
5
+ export declare const decryptBySharedKey: (input: string) => any;
6
+ export declare const getDeviceId: () => Promise<string>;
7
+ export declare const encrypt: (input: string, hardEncryption?: boolean, secretKey?: null) => Promise<string>;
8
+ export declare const decrypt: (input: string, hardEncryption?: boolean, secretKey?: null) => Promise<string>;
9
+ export declare const SecureStorage: {
10
+ setItem: (key: string, value: string) => Promise<unknown>;
11
+ getItem: (key: string) => Promise<unknown>;
12
+ mergeItem: (key: string, value: string) => Promise<unknown>;
13
+ removeItem: (key: string) => Promise<unknown>;
14
+ getAllKeys: () => Promise<unknown>;
15
+ multiSet: (keyValuePairs: Array<Array<string>>) => Promise<unknown>;
16
+ multiGet: (keys: Array<string>) => Promise<unknown>;
17
+ multiMerge: (keyValuePairs: Array<Array<string>>) => Promise<unknown>;
18
+ multiRemove: (keys: Array<string>) => Promise<unknown>;
19
+ clear: () => Promise<unknown>;
20
+ };
2
21
  export declare function deviceHasSecurityRisk(): Promise<boolean>;
3
22
  export default SecuritySuite;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "react-native-security-suite",
3
- "version": "0.1.2",
3
+ "version": "0.2.0",
4
4
  "description": "Security suite for React Native",
5
5
  "main": "lib/commonjs/index",
6
6
  "module": "lib/module/index",
@@ -54,6 +54,7 @@
54
54
  "@react-native-community/eslint-config": "^2.0.0",
55
55
  "@release-it/conventional-changelog": "^2.0.0",
56
56
  "@types/jest": "^26.0.0",
57
+ "@types/lodash": "^4.14.195",
57
58
  "@types/react": "^16.9.19",
58
59
  "@types/react-native": "0.62.13",
59
60
  "commitlint": "^11.0.0",
@@ -71,9 +72,16 @@
71
72
  "typescript": "^4.1.3"
72
73
  },
73
74
  "peerDependencies": {
75
+ "@react-native-async-storage/async-storage": "*",
76
+ "lodash": "*",
74
77
  "react": "*",
75
78
  "react-native": "*"
76
79
  },
80
+ "peerDependenciesMeta": {
81
+ "@react-native-async-storage/async-storage": {
82
+ "optional": false
83
+ }
84
+ },
77
85
  "jest": {
78
86
  "preset": "react-native",
79
87
  "modulePathIgnorePatterns": [
@@ -149,5 +157,8 @@
149
157
  },
150
158
  "directories": {
151
159
  "example": "example"
160
+ },
161
+ "dependencies": {
162
+ "@react-native-async-storage/async-storage": "^1.19.0"
152
163
  }
153
164
  }
@@ -10,7 +10,7 @@ Pod::Spec.new do |s|
10
10
  s.license = package["license"]
11
11
  s.authors = package["author"]
12
12
 
13
- s.platforms = { :ios => "10.0" }
13
+ s.platforms = { :ios => "13.0" }
14
14
  s.source = { :git => "https://github.com/mohamadnavabi/react-native-security-suite.git", :tag => "#{s.version}" }
15
15
 
16
16
  s.source_files = "ios/**/*.{h,m,mm,swift}"
package/src/helpers.ts ADDED
@@ -0,0 +1,8 @@
1
+ export const isJsonString = (value: string): boolean => {
2
+ try {
3
+ JSON.parse(value);
4
+ } catch (e) {
5
+ return false;
6
+ }
7
+ return true;
8
+ };
package/src/index.tsx CHANGED
@@ -1,4 +1,7 @@
1
1
  import { NativeModules, Platform } from 'react-native';
2
+ import AsyncStorage from '@react-native-async-storage/async-storage';
3
+ import _ from 'lodash';
4
+ import { isJsonString } from './helpers';
2
5
 
3
6
  const LINKING_ERROR =
4
7
  `The package 'react-native-security-suite' doesn't seem to be linked. Make sure: \n\n` +
@@ -15,10 +18,199 @@ const SecuritySuite = NativeModules.SecuritySuite
15
18
  throw new Error(LINKING_ERROR);
16
19
  },
17
20
  }
18
- );
19
-
21
+ );
22
+
23
+ export const getPublicKey = (): Promise<string> => SecuritySuite.getPublicKey();
24
+
25
+ export const getSharedKey = (serverPublicKey: string): Promise<string> =>
26
+ SecuritySuite.getSharedKey(serverPublicKey);
27
+
28
+ export const encryptBySharedKey = (input: string): Promise<string> =>
29
+ input && typeof input === 'string' ? SecuritySuite.encrypt(input) : '';
30
+
31
+ export const decryptBySharedKey = (input: string) =>
32
+ input && typeof input === 'string' ? SecuritySuite.decrypt(input) : '';
33
+
34
+ export const getDeviceId = (): Promise<string> =>
35
+ new Promise((resolve: any, reject: any) => {
36
+ SecuritySuite.getDeviceId((result: string | null, error: string | null) => {
37
+ if (error !== null) reject(error);
38
+ else resolve(result);
39
+ });
40
+ });
41
+
42
+ export const encrypt = (
43
+ input: string,
44
+ hardEncryption = true,
45
+ secretKey = null
46
+ ): Promise<string> =>
47
+ new Promise((resolve: any, reject: any) => {
48
+ if (!input) resolve(input);
49
+
50
+ SecuritySuite.storageEncrypt(
51
+ input,
52
+ secretKey,
53
+ hardEncryption,
54
+ (result: string | null, error: string | null) => {
55
+ if (error !== null) reject(error);
56
+ else resolve(result);
57
+ }
58
+ );
59
+ });
60
+
61
+ export const decrypt = (
62
+ input: string,
63
+ hardEncryption = true,
64
+ secretKey = null
65
+ ): Promise<string> =>
66
+ new Promise((resolve: any, reject: any) => {
67
+ if (!input) resolve(input);
68
+
69
+ SecuritySuite.storageDecrypt(
70
+ input,
71
+ secretKey,
72
+ hardEncryption,
73
+ (result: string | null, error: string | null) => {
74
+ if (error !== null) reject(error);
75
+ else resolve(result);
76
+ }
77
+ );
78
+ });
79
+
80
+ export const SecureStorage = {
81
+ setItem: async (key: string, value: string) => {
82
+ try {
83
+ const encryptedKey = await encrypt(key, false);
84
+ const encryptedValue = await encrypt(value);
85
+ return AsyncStorage.setItem(encryptedKey, encryptedValue);
86
+ } catch (e) {
87
+ return e;
88
+ }
89
+ },
90
+ getItem: async (key: string) => {
91
+ try {
92
+ const encryptedKey = await encrypt(key, false);
93
+ const encryptedData = await AsyncStorage.getItem(encryptedKey);
94
+ return decrypt(encryptedData ?? '');
95
+ } catch (e) {
96
+ return e;
97
+ }
98
+ },
99
+ mergeItem: async (key: string, value: string) => {
100
+ try {
101
+ const encryptedKey = await encrypt(key, false);
102
+ const encryptedData = await AsyncStorage.getItem(encryptedKey);
103
+ const data = await decrypt(encryptedData ?? '');
104
+ if (!isJsonString(data) || !isJsonString(value)) return null;
105
+ const mergedData = await JSON.stringify(
106
+ _.merge(JSON.parse(data), JSON.parse(value))
107
+ );
108
+ const encryptedValue = await encrypt(mergedData);
109
+ return AsyncStorage.setItem(encryptedKey, encryptedValue);
110
+ } catch (e) {
111
+ return e;
112
+ }
113
+ },
114
+ removeItem: async (key: string) => {
115
+ try {
116
+ const encryptedKey = await encrypt(key, false);
117
+ return AsyncStorage.removeItem(encryptedKey);
118
+ } catch (e) {
119
+ return e;
120
+ }
121
+ },
122
+ getAllKeys: async () => {
123
+ try {
124
+ const encryptedKeys = await AsyncStorage.getAllKeys();
125
+ return await Promise.all(
126
+ encryptedKeys.map(async (item: string): Promise<string> => {
127
+ const decryptedKey = await decrypt(item, false);
128
+ return decryptedKey ? decryptedKey : item;
129
+ })
130
+ );
131
+ } catch (e) {
132
+ return e;
133
+ }
134
+ },
135
+ multiSet: async (keyValuePairs: Array<Array<string>>) => {
136
+ try {
137
+ const encryptedKeyValuePairs: any = await Promise.all(
138
+ keyValuePairs.map(async (item: Array<string>) => {
139
+ if (item.length !== 2) return [];
140
+ const encryptedKey = await encrypt(item[0], false);
141
+ const encryptedValue = await encrypt(item[1]);
142
+ return [encryptedKey, encryptedValue];
143
+ })
144
+ );
145
+ AsyncStorage.multiSet(encryptedKeyValuePairs);
146
+ } catch (e) {
147
+ return e;
148
+ }
149
+ },
150
+ multiGet: async (keys: Array<string>) => {
151
+ try {
152
+ if (!Array.isArray(keys)) return null;
153
+ const encryptedKeys = await Promise.all(
154
+ keys.map(
155
+ async (item: string): Promise<string> => await encrypt(item, false)
156
+ )
157
+ );
158
+ const encryptedItems = await AsyncStorage.multiGet(encryptedKeys);
159
+ return await Promise.all(
160
+ encryptedItems && encryptedItems.length
161
+ ? encryptedItems.map(async (item: any): Promise<string[]> => {
162
+ const decryptedKey = await decrypt(item[0], false);
163
+ const decryptedalue = await decrypt(item[1]);
164
+ return [decryptedKey, decryptedalue];
165
+ })
166
+ : []
167
+ );
168
+ } catch (e) {
169
+ return e;
170
+ }
171
+ },
172
+ multiMerge: async (keyValuePairs: Array<Array<string>>) => {
173
+ try {
174
+ return keyValuePairs.map(async (item: Array<string>) => {
175
+ if (item.length !== 2) return;
176
+ const encryptedKey = await encrypt(item[0], false);
177
+ const encryptedData = await AsyncStorage.getItem(item[0]);
178
+ const data = await decrypt(encryptedData ?? '');
179
+ if (!isJsonString(data) || !isJsonString(item[1])) return null;
180
+ const mergedData = await JSON.stringify(
181
+ _.merge(JSON.parse(data), JSON.parse(item[1]))
182
+ );
183
+ const encryptedValue = await encrypt(mergedData, false);
184
+ return AsyncStorage.setItem(encryptedKey, encryptedValue);
185
+ });
186
+ } catch (e) {
187
+ return e;
188
+ }
189
+ },
190
+ multiRemove: async (keys: Array<string>) => {
191
+ try {
192
+ if (!Array.isArray(keys)) return keys;
193
+ const encryptedKeys = await Promise.all(
194
+ keys.map(
195
+ async (item: string): Promise<string> => await encrypt(item, false)
196
+ )
197
+ );
198
+ return AsyncStorage.multiRemove(encryptedKeys);
199
+ } catch (e) {
200
+ return e;
201
+ }
202
+ },
203
+ clear: async () => {
204
+ try {
205
+ return AsyncStorage.clear();
206
+ } catch (e) {
207
+ return e;
208
+ }
209
+ },
210
+ };
211
+
20
212
  export function deviceHasSecurityRisk(): Promise<boolean> {
21
213
  return SecuritySuite.deviceHasSecurityRisk();
22
214
  }
23
215
 
24
- export default SecuritySuite;
216
+ export default SecuritySuite;