@capawesome/capacitor-app-integrity 0.0.1
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.
- package/CapawesomeCapacitorAppIntegrity.podspec +17 -0
- package/LICENSE +21 -0
- package/Package.swift +28 -0
- package/README.md +385 -0
- package/android/build.gradle +60 -0
- package/android/src/main/AndroidManifest.xml +2 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/AppIntegrity.java +208 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/AppIntegrityPlugin.java +137 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/classes/CustomException.java +20 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/classes/CustomExceptions.java +11 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/classes/options/PrepareIntegrityTokenOptions.java +26 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/classes/options/RequestIntegrityTokenOptions.java +51 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/classes/results/IsAvailableResult.java +22 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/classes/results/RequestIntegrityTokenResult.java +23 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/interfaces/Callback.java +5 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/interfaces/EmptyCallback.java +5 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/interfaces/NonEmptyResultCallback.java +7 -0
- package/android/src/main/java/io/capawesome/capacitorjs/plugins/appintegrity/interfaces/Result.java +7 -0
- package/android/src/main/res/.gitkeep +0 -0
- package/dist/docs.json +472 -0
- package/dist/esm/definitions.d.ts +384 -0
- package/dist/esm/definitions.js +152 -0
- package/dist/esm/definitions.js.map +1 -0
- package/dist/esm/index.d.ts +4 -0
- package/dist/esm/index.js +7 -0
- package/dist/esm/index.js.map +1 -0
- package/dist/esm/web.d.ts +10 -0
- package/dist/esm/web.js +22 -0
- package/dist/esm/web.js.map +1 -0
- package/dist/plugin.cjs.js +188 -0
- package/dist/plugin.cjs.js.map +1 -0
- package/dist/plugin.js +191 -0
- package/dist/plugin.js.map +1 -0
- package/ios/Plugin/AppIntegrity.swift +78 -0
- package/ios/Plugin/AppIntegrityPlugin.swift +116 -0
- package/ios/Plugin/Classes/Options/AttestKeyOptions.swift +29 -0
- package/ios/Plugin/Classes/Options/GenerateAssertionOptions.swift +29 -0
- package/ios/Plugin/Classes/Results/AttestKeyResult.swift +16 -0
- package/ios/Plugin/Classes/Results/GenerateAssertionResult.swift +16 -0
- package/ios/Plugin/Classes/Results/GenerateKeyResult.swift +16 -0
- package/ios/Plugin/Classes/Results/IsAvailableResult.swift +16 -0
- package/ios/Plugin/Enums/CustomError.swift +59 -0
- package/ios/Plugin/Info.plist +24 -0
- package/ios/Plugin/Protocols/Result.swift +5 -0
- package/package.json +91 -0
|
@@ -0,0 +1,188 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var core = require('@capacitor/core');
|
|
4
|
+
|
|
5
|
+
/**
|
|
6
|
+
* @since 0.1.0
|
|
7
|
+
*/
|
|
8
|
+
exports.ErrorCode = void 0;
|
|
9
|
+
(function (ErrorCode) {
|
|
10
|
+
/**
|
|
11
|
+
* The Play Integrity API is not available on this device.
|
|
12
|
+
*
|
|
13
|
+
* Only available on Android.
|
|
14
|
+
*
|
|
15
|
+
* @since 0.1.0
|
|
16
|
+
*/
|
|
17
|
+
ErrorCode["ApiNotAvailable"] = "API_NOT_AVAILABLE";
|
|
18
|
+
/**
|
|
19
|
+
* The calling app is not installed.
|
|
20
|
+
*
|
|
21
|
+
* Only available on Android.
|
|
22
|
+
*
|
|
23
|
+
* @since 0.1.0
|
|
24
|
+
*/
|
|
25
|
+
ErrorCode["AppNotInstalled"] = "APP_NOT_INSTALLED";
|
|
26
|
+
/**
|
|
27
|
+
* The calling app UID does not match the one from the package manager.
|
|
28
|
+
*
|
|
29
|
+
* Only available on Android.
|
|
30
|
+
*
|
|
31
|
+
* @since 0.1.0
|
|
32
|
+
*/
|
|
33
|
+
ErrorCode["AppUidMismatch"] = "APP_UID_MISMATCH";
|
|
34
|
+
/**
|
|
35
|
+
* The assertion could not be generated.
|
|
36
|
+
*
|
|
37
|
+
* Only available on iOS.
|
|
38
|
+
*
|
|
39
|
+
* @since 0.1.0
|
|
40
|
+
*/
|
|
41
|
+
ErrorCode["AssertionFailed"] = "ASSERTION_FAILED";
|
|
42
|
+
/**
|
|
43
|
+
* The attestation could not be generated.
|
|
44
|
+
*
|
|
45
|
+
* Only available on iOS.
|
|
46
|
+
*
|
|
47
|
+
* @since 0.1.0
|
|
48
|
+
*/
|
|
49
|
+
ErrorCode["AttestationFailed"] = "ATTESTATION_FAILED";
|
|
50
|
+
/**
|
|
51
|
+
* The app could not bind to the integrity service in the Play Store.
|
|
52
|
+
*
|
|
53
|
+
* Only available on Android.
|
|
54
|
+
*
|
|
55
|
+
* @since 0.1.0
|
|
56
|
+
*/
|
|
57
|
+
ErrorCode["CannotBindToService"] = "CANNOT_BIND_TO_SERVICE";
|
|
58
|
+
/**
|
|
59
|
+
* A transient error occurred on the device. Retry with an exponential backoff.
|
|
60
|
+
*
|
|
61
|
+
* Only available on Android.
|
|
62
|
+
*
|
|
63
|
+
* @since 0.1.0
|
|
64
|
+
*/
|
|
65
|
+
ErrorCode["ClientTransientError"] = "CLIENT_TRANSIENT_ERROR";
|
|
66
|
+
/**
|
|
67
|
+
* The Google server is currently unavailable. Retry with an exponential backoff.
|
|
68
|
+
*
|
|
69
|
+
* Only available on Android.
|
|
70
|
+
*
|
|
71
|
+
* @since 0.1.0
|
|
72
|
+
*/
|
|
73
|
+
ErrorCode["GoogleServerUnavailable"] = "GOOGLE_SERVER_UNAVAILABLE";
|
|
74
|
+
/**
|
|
75
|
+
* The integrity token provider is invalid. Call `prepareIntegrityToken(...)` again.
|
|
76
|
+
*
|
|
77
|
+
* Only available on Android.
|
|
78
|
+
*
|
|
79
|
+
* @since 0.1.0
|
|
80
|
+
*/
|
|
81
|
+
ErrorCode["IntegrityTokenProviderInvalid"] = "INTEGRITY_TOKEN_PROVIDER_INVALID";
|
|
82
|
+
/**
|
|
83
|
+
* An internal error occurred. Retry with an exponential backoff.
|
|
84
|
+
*
|
|
85
|
+
* Only available on Android.
|
|
86
|
+
*
|
|
87
|
+
* @since 0.1.0
|
|
88
|
+
*/
|
|
89
|
+
ErrorCode["InternalError"] = "INTERNAL_ERROR";
|
|
90
|
+
/**
|
|
91
|
+
* The key is invalid or was not recognized by the App Attest service.
|
|
92
|
+
* Generate and attest a new key.
|
|
93
|
+
*
|
|
94
|
+
* Only available on iOS.
|
|
95
|
+
*
|
|
96
|
+
* @since 0.1.0
|
|
97
|
+
*/
|
|
98
|
+
ErrorCode["InvalidKey"] = "INVALID_KEY";
|
|
99
|
+
/**
|
|
100
|
+
* No network connection is available. Retry when the device is online.
|
|
101
|
+
*
|
|
102
|
+
* Only available on Android.
|
|
103
|
+
*
|
|
104
|
+
* @since 0.1.0
|
|
105
|
+
*/
|
|
106
|
+
ErrorCode["NetworkError"] = "NETWORK_ERROR";
|
|
107
|
+
/**
|
|
108
|
+
* Google Play Services is not available on this device.
|
|
109
|
+
*
|
|
110
|
+
* Only available on Android.
|
|
111
|
+
*
|
|
112
|
+
* @since 0.1.0
|
|
113
|
+
*/
|
|
114
|
+
ErrorCode["PlayServicesNotFound"] = "PLAY_SERVICES_NOT_FOUND";
|
|
115
|
+
/**
|
|
116
|
+
* Google Play Services needs to be updated.
|
|
117
|
+
*
|
|
118
|
+
* Only available on Android.
|
|
119
|
+
*
|
|
120
|
+
* @since 0.1.0
|
|
121
|
+
*/
|
|
122
|
+
ErrorCode["PlayServicesVersionOutdated"] = "PLAY_SERVICES_VERSION_OUTDATED";
|
|
123
|
+
/**
|
|
124
|
+
* No official Play Store app was found on the device.
|
|
125
|
+
*
|
|
126
|
+
* Only available on Android.
|
|
127
|
+
*
|
|
128
|
+
* @since 0.1.0
|
|
129
|
+
*/
|
|
130
|
+
ErrorCode["PlayStoreNotFound"] = "PLAY_STORE_NOT_FOUND";
|
|
131
|
+
/**
|
|
132
|
+
* The Play Store app needs to be updated.
|
|
133
|
+
*
|
|
134
|
+
* Only available on Android.
|
|
135
|
+
*
|
|
136
|
+
* @since 0.1.0
|
|
137
|
+
*/
|
|
138
|
+
ErrorCode["PlayStoreVersionOutdated"] = "PLAY_STORE_VERSION_OUTDATED";
|
|
139
|
+
/**
|
|
140
|
+
* The App Attest service is currently unavailable. Retry later.
|
|
141
|
+
*
|
|
142
|
+
* Only available on iOS.
|
|
143
|
+
*
|
|
144
|
+
* @since 0.1.0
|
|
145
|
+
*/
|
|
146
|
+
ErrorCode["ServerUnavailable"] = "SERVER_UNAVAILABLE";
|
|
147
|
+
/**
|
|
148
|
+
* The calling app is making too many requests and has been throttled.
|
|
149
|
+
*
|
|
150
|
+
* Only available on Android.
|
|
151
|
+
*
|
|
152
|
+
* @since 0.1.0
|
|
153
|
+
*/
|
|
154
|
+
ErrorCode["TooManyRequests"] = "TOO_MANY_REQUESTS";
|
|
155
|
+
})(exports.ErrorCode || (exports.ErrorCode = {}));
|
|
156
|
+
|
|
157
|
+
const AppIntegrity = core.registerPlugin('AppIntegrity', {
|
|
158
|
+
web: () => Promise.resolve().then(function () { return web; }).then(m => new m.AppIntegrityWeb()),
|
|
159
|
+
});
|
|
160
|
+
|
|
161
|
+
class AppIntegrityWeb extends core.WebPlugin {
|
|
162
|
+
async attestKey() {
|
|
163
|
+
throw this.unimplemented('Not implemented on web.');
|
|
164
|
+
}
|
|
165
|
+
async generateAssertion() {
|
|
166
|
+
throw this.unimplemented('Not implemented on web.');
|
|
167
|
+
}
|
|
168
|
+
async generateKey() {
|
|
169
|
+
throw this.unimplemented('Not implemented on web.');
|
|
170
|
+
}
|
|
171
|
+
async isAvailable() {
|
|
172
|
+
throw this.unimplemented('Not implemented on web.');
|
|
173
|
+
}
|
|
174
|
+
async prepareIntegrityToken() {
|
|
175
|
+
throw this.unimplemented('Not implemented on web.');
|
|
176
|
+
}
|
|
177
|
+
async requestIntegrityToken() {
|
|
178
|
+
throw this.unimplemented('Not implemented on web.');
|
|
179
|
+
}
|
|
180
|
+
}
|
|
181
|
+
|
|
182
|
+
var web = /*#__PURE__*/Object.freeze({
|
|
183
|
+
__proto__: null,
|
|
184
|
+
AppIntegrityWeb: AppIntegrityWeb
|
|
185
|
+
});
|
|
186
|
+
|
|
187
|
+
exports.AppIntegrity = AppIntegrity;
|
|
188
|
+
//# sourceMappingURL=plugin.cjs.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plugin.cjs.js","sources":["esm/definitions.js","esm/index.js","esm/web.js"],"sourcesContent":["/**\n * @since 0.1.0\n */\nexport var ErrorCode;\n(function (ErrorCode) {\n /**\n * The Play Integrity API is not available on this device.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"ApiNotAvailable\"] = \"API_NOT_AVAILABLE\";\n /**\n * The calling app is not installed.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AppNotInstalled\"] = \"APP_NOT_INSTALLED\";\n /**\n * The calling app UID does not match the one from the package manager.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AppUidMismatch\"] = \"APP_UID_MISMATCH\";\n /**\n * The assertion could not be generated.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AssertionFailed\"] = \"ASSERTION_FAILED\";\n /**\n * The attestation could not be generated.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AttestationFailed\"] = \"ATTESTATION_FAILED\";\n /**\n * The app could not bind to the integrity service in the Play Store.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"CannotBindToService\"] = \"CANNOT_BIND_TO_SERVICE\";\n /**\n * A transient error occurred on the device. Retry with an exponential backoff.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"ClientTransientError\"] = \"CLIENT_TRANSIENT_ERROR\";\n /**\n * The Google server is currently unavailable. Retry with an exponential backoff.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"GoogleServerUnavailable\"] = \"GOOGLE_SERVER_UNAVAILABLE\";\n /**\n * The integrity token provider is invalid. Call `prepareIntegrityToken(...)` again.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"IntegrityTokenProviderInvalid\"] = \"INTEGRITY_TOKEN_PROVIDER_INVALID\";\n /**\n * An internal error occurred. Retry with an exponential backoff.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"InternalError\"] = \"INTERNAL_ERROR\";\n /**\n * The key is invalid or was not recognized by the App Attest service.\n * Generate and attest a new key.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"InvalidKey\"] = \"INVALID_KEY\";\n /**\n * No network connection is available. Retry when the device is online.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"NetworkError\"] = \"NETWORK_ERROR\";\n /**\n * Google Play Services is not available on this device.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayServicesNotFound\"] = \"PLAY_SERVICES_NOT_FOUND\";\n /**\n * Google Play Services needs to be updated.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayServicesVersionOutdated\"] = \"PLAY_SERVICES_VERSION_OUTDATED\";\n /**\n * No official Play Store app was found on the device.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayStoreNotFound\"] = \"PLAY_STORE_NOT_FOUND\";\n /**\n * The Play Store app needs to be updated.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayStoreVersionOutdated\"] = \"PLAY_STORE_VERSION_OUTDATED\";\n /**\n * The App Attest service is currently unavailable. Retry later.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"ServerUnavailable\"] = \"SERVER_UNAVAILABLE\";\n /**\n * The calling app is making too many requests and has been throttled.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"TooManyRequests\"] = \"TOO_MANY_REQUESTS\";\n})(ErrorCode || (ErrorCode = {}));\n//# sourceMappingURL=definitions.js.map","import { registerPlugin } from '@capacitor/core';\nconst AppIntegrity = registerPlugin('AppIntegrity', {\n web: () => import('./web').then(m => new m.AppIntegrityWeb()),\n});\nexport * from './definitions';\nexport { AppIntegrity };\n//# sourceMappingURL=index.js.map","import { WebPlugin } from '@capacitor/core';\nexport class AppIntegrityWeb extends WebPlugin {\n async attestKey() {\n throw this.unimplemented('Not implemented on web.');\n }\n async generateAssertion() {\n throw this.unimplemented('Not implemented on web.');\n }\n async generateKey() {\n throw this.unimplemented('Not implemented on web.');\n }\n async isAvailable() {\n throw this.unimplemented('Not implemented on web.');\n }\n async prepareIntegrityToken() {\n throw this.unimplemented('Not implemented on web.');\n }\n async requestIntegrityToken() {\n throw this.unimplemented('Not implemented on web.');\n }\n}\n//# sourceMappingURL=web.js.map"],"names":["ErrorCode","registerPlugin","WebPlugin"],"mappings":";;;;AAAA;AACA;AACA;AACWA;AACX,CAAC,UAAU,SAAS,EAAE;AACtB;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,mBAAmB;AACtD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,mBAAmB;AACtD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,gBAAgB,CAAC,GAAG,kBAAkB;AACpD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,kBAAkB;AACrD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,mBAAmB,CAAC,GAAG,oBAAoB;AACzD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,qBAAqB,CAAC,GAAG,wBAAwB;AAC/D;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,sBAAsB,CAAC,GAAG,wBAAwB;AAChE;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,yBAAyB,CAAC,GAAG,2BAA2B;AACtE;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,+BAA+B,CAAC,GAAG,kCAAkC;AACnF;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,eAAe,CAAC,GAAG,gBAAgB;AACjD;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,YAAY,CAAC,GAAG,aAAa;AAC3C;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,cAAc,CAAC,GAAG,eAAe;AAC/C;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,sBAAsB,CAAC,GAAG,yBAAyB;AACjE;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,6BAA6B,CAAC,GAAG,gCAAgC;AAC/E;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,mBAAmB,CAAC,GAAG,sBAAsB;AAC3D;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,0BAA0B,CAAC,GAAG,6BAA6B;AACzE;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,mBAAmB,CAAC,GAAG,oBAAoB;AACzD;AACA;AACA;AACA;AACA;AACA;AACA;AACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,mBAAmB;AACtD,CAAC,EAAEA,iBAAS,KAAKA,iBAAS,GAAG,EAAE,CAAC,CAAC;;ACrJ5B,MAAC,YAAY,GAAGC,mBAAc,CAAC,cAAc,EAAE;AACpD,IAAI,GAAG,EAAE,MAAM,mDAAe,CAAC,IAAI,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,eAAe,EAAE,CAAC;AACjE,CAAC;;ACFM,MAAM,eAAe,SAASC,cAAS,CAAC;AAC/C,IAAI,MAAM,SAAS,GAAG;AACtB,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;AAC3D,IAAI;AACJ,IAAI,MAAM,iBAAiB,GAAG;AAC9B,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;AAC3D,IAAI;AACJ,IAAI,MAAM,WAAW,GAAG;AACxB,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;AAC3D,IAAI;AACJ,IAAI,MAAM,WAAW,GAAG;AACxB,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;AAC3D,IAAI;AACJ,IAAI,MAAM,qBAAqB,GAAG;AAClC,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;AAC3D,IAAI;AACJ,IAAI,MAAM,qBAAqB,GAAG;AAClC,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;AAC3D,IAAI;AACJ;;;;;;;;;"}
|
package/dist/plugin.js
ADDED
|
@@ -0,0 +1,191 @@
|
|
|
1
|
+
var capacitorAppIntegrity = (function (exports, core) {
|
|
2
|
+
'use strict';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* @since 0.1.0
|
|
6
|
+
*/
|
|
7
|
+
exports.ErrorCode = void 0;
|
|
8
|
+
(function (ErrorCode) {
|
|
9
|
+
/**
|
|
10
|
+
* The Play Integrity API is not available on this device.
|
|
11
|
+
*
|
|
12
|
+
* Only available on Android.
|
|
13
|
+
*
|
|
14
|
+
* @since 0.1.0
|
|
15
|
+
*/
|
|
16
|
+
ErrorCode["ApiNotAvailable"] = "API_NOT_AVAILABLE";
|
|
17
|
+
/**
|
|
18
|
+
* The calling app is not installed.
|
|
19
|
+
*
|
|
20
|
+
* Only available on Android.
|
|
21
|
+
*
|
|
22
|
+
* @since 0.1.0
|
|
23
|
+
*/
|
|
24
|
+
ErrorCode["AppNotInstalled"] = "APP_NOT_INSTALLED";
|
|
25
|
+
/**
|
|
26
|
+
* The calling app UID does not match the one from the package manager.
|
|
27
|
+
*
|
|
28
|
+
* Only available on Android.
|
|
29
|
+
*
|
|
30
|
+
* @since 0.1.0
|
|
31
|
+
*/
|
|
32
|
+
ErrorCode["AppUidMismatch"] = "APP_UID_MISMATCH";
|
|
33
|
+
/**
|
|
34
|
+
* The assertion could not be generated.
|
|
35
|
+
*
|
|
36
|
+
* Only available on iOS.
|
|
37
|
+
*
|
|
38
|
+
* @since 0.1.0
|
|
39
|
+
*/
|
|
40
|
+
ErrorCode["AssertionFailed"] = "ASSERTION_FAILED";
|
|
41
|
+
/**
|
|
42
|
+
* The attestation could not be generated.
|
|
43
|
+
*
|
|
44
|
+
* Only available on iOS.
|
|
45
|
+
*
|
|
46
|
+
* @since 0.1.0
|
|
47
|
+
*/
|
|
48
|
+
ErrorCode["AttestationFailed"] = "ATTESTATION_FAILED";
|
|
49
|
+
/**
|
|
50
|
+
* The app could not bind to the integrity service in the Play Store.
|
|
51
|
+
*
|
|
52
|
+
* Only available on Android.
|
|
53
|
+
*
|
|
54
|
+
* @since 0.1.0
|
|
55
|
+
*/
|
|
56
|
+
ErrorCode["CannotBindToService"] = "CANNOT_BIND_TO_SERVICE";
|
|
57
|
+
/**
|
|
58
|
+
* A transient error occurred on the device. Retry with an exponential backoff.
|
|
59
|
+
*
|
|
60
|
+
* Only available on Android.
|
|
61
|
+
*
|
|
62
|
+
* @since 0.1.0
|
|
63
|
+
*/
|
|
64
|
+
ErrorCode["ClientTransientError"] = "CLIENT_TRANSIENT_ERROR";
|
|
65
|
+
/**
|
|
66
|
+
* The Google server is currently unavailable. Retry with an exponential backoff.
|
|
67
|
+
*
|
|
68
|
+
* Only available on Android.
|
|
69
|
+
*
|
|
70
|
+
* @since 0.1.0
|
|
71
|
+
*/
|
|
72
|
+
ErrorCode["GoogleServerUnavailable"] = "GOOGLE_SERVER_UNAVAILABLE";
|
|
73
|
+
/**
|
|
74
|
+
* The integrity token provider is invalid. Call `prepareIntegrityToken(...)` again.
|
|
75
|
+
*
|
|
76
|
+
* Only available on Android.
|
|
77
|
+
*
|
|
78
|
+
* @since 0.1.0
|
|
79
|
+
*/
|
|
80
|
+
ErrorCode["IntegrityTokenProviderInvalid"] = "INTEGRITY_TOKEN_PROVIDER_INVALID";
|
|
81
|
+
/**
|
|
82
|
+
* An internal error occurred. Retry with an exponential backoff.
|
|
83
|
+
*
|
|
84
|
+
* Only available on Android.
|
|
85
|
+
*
|
|
86
|
+
* @since 0.1.0
|
|
87
|
+
*/
|
|
88
|
+
ErrorCode["InternalError"] = "INTERNAL_ERROR";
|
|
89
|
+
/**
|
|
90
|
+
* The key is invalid or was not recognized by the App Attest service.
|
|
91
|
+
* Generate and attest a new key.
|
|
92
|
+
*
|
|
93
|
+
* Only available on iOS.
|
|
94
|
+
*
|
|
95
|
+
* @since 0.1.0
|
|
96
|
+
*/
|
|
97
|
+
ErrorCode["InvalidKey"] = "INVALID_KEY";
|
|
98
|
+
/**
|
|
99
|
+
* No network connection is available. Retry when the device is online.
|
|
100
|
+
*
|
|
101
|
+
* Only available on Android.
|
|
102
|
+
*
|
|
103
|
+
* @since 0.1.0
|
|
104
|
+
*/
|
|
105
|
+
ErrorCode["NetworkError"] = "NETWORK_ERROR";
|
|
106
|
+
/**
|
|
107
|
+
* Google Play Services is not available on this device.
|
|
108
|
+
*
|
|
109
|
+
* Only available on Android.
|
|
110
|
+
*
|
|
111
|
+
* @since 0.1.0
|
|
112
|
+
*/
|
|
113
|
+
ErrorCode["PlayServicesNotFound"] = "PLAY_SERVICES_NOT_FOUND";
|
|
114
|
+
/**
|
|
115
|
+
* Google Play Services needs to be updated.
|
|
116
|
+
*
|
|
117
|
+
* Only available on Android.
|
|
118
|
+
*
|
|
119
|
+
* @since 0.1.0
|
|
120
|
+
*/
|
|
121
|
+
ErrorCode["PlayServicesVersionOutdated"] = "PLAY_SERVICES_VERSION_OUTDATED";
|
|
122
|
+
/**
|
|
123
|
+
* No official Play Store app was found on the device.
|
|
124
|
+
*
|
|
125
|
+
* Only available on Android.
|
|
126
|
+
*
|
|
127
|
+
* @since 0.1.0
|
|
128
|
+
*/
|
|
129
|
+
ErrorCode["PlayStoreNotFound"] = "PLAY_STORE_NOT_FOUND";
|
|
130
|
+
/**
|
|
131
|
+
* The Play Store app needs to be updated.
|
|
132
|
+
*
|
|
133
|
+
* Only available on Android.
|
|
134
|
+
*
|
|
135
|
+
* @since 0.1.0
|
|
136
|
+
*/
|
|
137
|
+
ErrorCode["PlayStoreVersionOutdated"] = "PLAY_STORE_VERSION_OUTDATED";
|
|
138
|
+
/**
|
|
139
|
+
* The App Attest service is currently unavailable. Retry later.
|
|
140
|
+
*
|
|
141
|
+
* Only available on iOS.
|
|
142
|
+
*
|
|
143
|
+
* @since 0.1.0
|
|
144
|
+
*/
|
|
145
|
+
ErrorCode["ServerUnavailable"] = "SERVER_UNAVAILABLE";
|
|
146
|
+
/**
|
|
147
|
+
* The calling app is making too many requests and has been throttled.
|
|
148
|
+
*
|
|
149
|
+
* Only available on Android.
|
|
150
|
+
*
|
|
151
|
+
* @since 0.1.0
|
|
152
|
+
*/
|
|
153
|
+
ErrorCode["TooManyRequests"] = "TOO_MANY_REQUESTS";
|
|
154
|
+
})(exports.ErrorCode || (exports.ErrorCode = {}));
|
|
155
|
+
|
|
156
|
+
const AppIntegrity = core.registerPlugin('AppIntegrity', {
|
|
157
|
+
web: () => Promise.resolve().then(function () { return web; }).then(m => new m.AppIntegrityWeb()),
|
|
158
|
+
});
|
|
159
|
+
|
|
160
|
+
class AppIntegrityWeb extends core.WebPlugin {
|
|
161
|
+
async attestKey() {
|
|
162
|
+
throw this.unimplemented('Not implemented on web.');
|
|
163
|
+
}
|
|
164
|
+
async generateAssertion() {
|
|
165
|
+
throw this.unimplemented('Not implemented on web.');
|
|
166
|
+
}
|
|
167
|
+
async generateKey() {
|
|
168
|
+
throw this.unimplemented('Not implemented on web.');
|
|
169
|
+
}
|
|
170
|
+
async isAvailable() {
|
|
171
|
+
throw this.unimplemented('Not implemented on web.');
|
|
172
|
+
}
|
|
173
|
+
async prepareIntegrityToken() {
|
|
174
|
+
throw this.unimplemented('Not implemented on web.');
|
|
175
|
+
}
|
|
176
|
+
async requestIntegrityToken() {
|
|
177
|
+
throw this.unimplemented('Not implemented on web.');
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
|
|
181
|
+
var web = /*#__PURE__*/Object.freeze({
|
|
182
|
+
__proto__: null,
|
|
183
|
+
AppIntegrityWeb: AppIntegrityWeb
|
|
184
|
+
});
|
|
185
|
+
|
|
186
|
+
exports.AppIntegrity = AppIntegrity;
|
|
187
|
+
|
|
188
|
+
return exports;
|
|
189
|
+
|
|
190
|
+
})({}, capacitorExports);
|
|
191
|
+
//# sourceMappingURL=plugin.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"plugin.js","sources":["esm/definitions.js","esm/index.js","esm/web.js"],"sourcesContent":["/**\n * @since 0.1.0\n */\nexport var ErrorCode;\n(function (ErrorCode) {\n /**\n * The Play Integrity API is not available on this device.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"ApiNotAvailable\"] = \"API_NOT_AVAILABLE\";\n /**\n * The calling app is not installed.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AppNotInstalled\"] = \"APP_NOT_INSTALLED\";\n /**\n * The calling app UID does not match the one from the package manager.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AppUidMismatch\"] = \"APP_UID_MISMATCH\";\n /**\n * The assertion could not be generated.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AssertionFailed\"] = \"ASSERTION_FAILED\";\n /**\n * The attestation could not be generated.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"AttestationFailed\"] = \"ATTESTATION_FAILED\";\n /**\n * The app could not bind to the integrity service in the Play Store.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"CannotBindToService\"] = \"CANNOT_BIND_TO_SERVICE\";\n /**\n * A transient error occurred on the device. Retry with an exponential backoff.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"ClientTransientError\"] = \"CLIENT_TRANSIENT_ERROR\";\n /**\n * The Google server is currently unavailable. Retry with an exponential backoff.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"GoogleServerUnavailable\"] = \"GOOGLE_SERVER_UNAVAILABLE\";\n /**\n * The integrity token provider is invalid. Call `prepareIntegrityToken(...)` again.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"IntegrityTokenProviderInvalid\"] = \"INTEGRITY_TOKEN_PROVIDER_INVALID\";\n /**\n * An internal error occurred. Retry with an exponential backoff.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"InternalError\"] = \"INTERNAL_ERROR\";\n /**\n * The key is invalid or was not recognized by the App Attest service.\n * Generate and attest a new key.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"InvalidKey\"] = \"INVALID_KEY\";\n /**\n * No network connection is available. Retry when the device is online.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"NetworkError\"] = \"NETWORK_ERROR\";\n /**\n * Google Play Services is not available on this device.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayServicesNotFound\"] = \"PLAY_SERVICES_NOT_FOUND\";\n /**\n * Google Play Services needs to be updated.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayServicesVersionOutdated\"] = \"PLAY_SERVICES_VERSION_OUTDATED\";\n /**\n * No official Play Store app was found on the device.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayStoreNotFound\"] = \"PLAY_STORE_NOT_FOUND\";\n /**\n * The Play Store app needs to be updated.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"PlayStoreVersionOutdated\"] = \"PLAY_STORE_VERSION_OUTDATED\";\n /**\n * The App Attest service is currently unavailable. Retry later.\n *\n * Only available on iOS.\n *\n * @since 0.1.0\n */\n ErrorCode[\"ServerUnavailable\"] = \"SERVER_UNAVAILABLE\";\n /**\n * The calling app is making too many requests and has been throttled.\n *\n * Only available on Android.\n *\n * @since 0.1.0\n */\n ErrorCode[\"TooManyRequests\"] = \"TOO_MANY_REQUESTS\";\n})(ErrorCode || (ErrorCode = {}));\n//# sourceMappingURL=definitions.js.map","import { registerPlugin } from '@capacitor/core';\nconst AppIntegrity = registerPlugin('AppIntegrity', {\n web: () => import('./web').then(m => new m.AppIntegrityWeb()),\n});\nexport * from './definitions';\nexport { AppIntegrity };\n//# sourceMappingURL=index.js.map","import { WebPlugin } from '@capacitor/core';\nexport class AppIntegrityWeb extends WebPlugin {\n async attestKey() {\n throw this.unimplemented('Not implemented on web.');\n }\n async generateAssertion() {\n throw this.unimplemented('Not implemented on web.');\n }\n async generateKey() {\n throw this.unimplemented('Not implemented on web.');\n }\n async isAvailable() {\n throw this.unimplemented('Not implemented on web.');\n }\n async prepareIntegrityToken() {\n throw this.unimplemented('Not implemented on web.');\n }\n async requestIntegrityToken() {\n throw this.unimplemented('Not implemented on web.');\n }\n}\n//# sourceMappingURL=web.js.map"],"names":["ErrorCode","registerPlugin","WebPlugin"],"mappings":";;;IAAA;IACA;IACA;AACWA;IACX,CAAC,UAAU,SAAS,EAAE;IACtB;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,mBAAmB;IACtD;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,mBAAmB;IACtD;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,gBAAgB,CAAC,GAAG,kBAAkB;IACpD;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,kBAAkB;IACrD;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,mBAAmB,CAAC,GAAG,oBAAoB;IACzD;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,qBAAqB,CAAC,GAAG,wBAAwB;IAC/D;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,sBAAsB,CAAC,GAAG,wBAAwB;IAChE;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,yBAAyB,CAAC,GAAG,2BAA2B;IACtE;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,+BAA+B,CAAC,GAAG,kCAAkC;IACnF;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,eAAe,CAAC,GAAG,gBAAgB;IACjD;IACA;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,YAAY,CAAC,GAAG,aAAa;IAC3C;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,cAAc,CAAC,GAAG,eAAe;IAC/C;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,sBAAsB,CAAC,GAAG,yBAAyB;IACjE;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,6BAA6B,CAAC,GAAG,gCAAgC;IAC/E;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,mBAAmB,CAAC,GAAG,sBAAsB;IAC3D;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,0BAA0B,CAAC,GAAG,6BAA6B;IACzE;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,mBAAmB,CAAC,GAAG,oBAAoB;IACzD;IACA;IACA;IACA;IACA;IACA;IACA;IACA,IAAI,SAAS,CAAC,iBAAiB,CAAC,GAAG,mBAAmB;IACtD,CAAC,EAAEA,iBAAS,KAAKA,iBAAS,GAAG,EAAE,CAAC,CAAC;;ACrJ5B,UAAC,YAAY,GAAGC,mBAAc,CAAC,cAAc,EAAE;IACpD,IAAI,GAAG,EAAE,MAAM,mDAAe,CAAC,IAAI,CAAC,CAAC,IAAI,IAAI,CAAC,CAAC,eAAe,EAAE,CAAC;IACjE,CAAC;;ICFM,MAAM,eAAe,SAASC,cAAS,CAAC;IAC/C,IAAI,MAAM,SAAS,GAAG;IACtB,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;IAC3D,IAAI;IACJ,IAAI,MAAM,iBAAiB,GAAG;IAC9B,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;IAC3D,IAAI;IACJ,IAAI,MAAM,WAAW,GAAG;IACxB,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;IAC3D,IAAI;IACJ,IAAI,MAAM,WAAW,GAAG;IACxB,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;IAC3D,IAAI;IACJ,IAAI,MAAM,qBAAqB,GAAG;IAClC,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;IAC3D,IAAI;IACJ,IAAI,MAAM,qBAAqB,GAAG;IAClC,QAAQ,MAAM,IAAI,CAAC,aAAa,CAAC,yBAAyB,CAAC;IAC3D,IAAI;IACJ;;;;;;;;;;;;;;;"}
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import CryptoKit
|
|
2
|
+
import DeviceCheck
|
|
3
|
+
import Foundation
|
|
4
|
+
|
|
5
|
+
@objc public class AppIntegrity: NSObject {
|
|
6
|
+
private let plugin: AppIntegrityPlugin
|
|
7
|
+
private let service = DCAppAttestService.shared
|
|
8
|
+
|
|
9
|
+
init(plugin: AppIntegrityPlugin) {
|
|
10
|
+
self.plugin = plugin
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
@objc public func attestKey(_ options: AttestKeyOptions, completion: @escaping (AttestKeyResult?, Error?) -> Void) {
|
|
14
|
+
let clientDataHash = Data(SHA256.hash(data: options.challenge))
|
|
15
|
+
service.attestKey(options.keyId, clientDataHash: clientDataHash) { attestation, error in
|
|
16
|
+
if let error = error {
|
|
17
|
+
completion(nil, self.mapError(error))
|
|
18
|
+
return
|
|
19
|
+
}
|
|
20
|
+
guard let attestation = attestation else {
|
|
21
|
+
completion(nil, CustomError.attestationFailed)
|
|
22
|
+
return
|
|
23
|
+
}
|
|
24
|
+
completion(AttestKeyResult(attestationObject: attestation), nil)
|
|
25
|
+
}
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
@objc public func generateAssertion(_ options: GenerateAssertionOptions, completion: @escaping (GenerateAssertionResult?, Error?) -> Void) {
|
|
29
|
+
let clientDataHash = Data(SHA256.hash(data: options.clientData))
|
|
30
|
+
service.generateAssertion(options.keyId, clientDataHash: clientDataHash) { assertion, error in
|
|
31
|
+
if let error = error {
|
|
32
|
+
completion(nil, self.mapError(error))
|
|
33
|
+
return
|
|
34
|
+
}
|
|
35
|
+
guard let assertion = assertion else {
|
|
36
|
+
completion(nil, CustomError.assertionFailed)
|
|
37
|
+
return
|
|
38
|
+
}
|
|
39
|
+
completion(GenerateAssertionResult(assertion: assertion), nil)
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
@objc public func generateKey(completion: @escaping (GenerateKeyResult?, Error?) -> Void) {
|
|
44
|
+
service.generateKey { keyId, error in
|
|
45
|
+
if let error = error {
|
|
46
|
+
completion(nil, self.mapError(error))
|
|
47
|
+
return
|
|
48
|
+
}
|
|
49
|
+
guard let keyId = keyId else {
|
|
50
|
+
completion(nil, CustomError.keyGenerationFailed)
|
|
51
|
+
return
|
|
52
|
+
}
|
|
53
|
+
completion(GenerateKeyResult(keyId: keyId), nil)
|
|
54
|
+
}
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
@objc public func isAvailable(completion: @escaping (IsAvailableResult?, Error?) -> Void) {
|
|
58
|
+
completion(IsAvailableResult(available: service.isSupported), nil)
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
@objc public func isSupported() -> Bool {
|
|
62
|
+
return service.isSupported
|
|
63
|
+
}
|
|
64
|
+
|
|
65
|
+
private func mapError(_ error: Error) -> Error {
|
|
66
|
+
guard let dcError = error as? DCError else {
|
|
67
|
+
return error
|
|
68
|
+
}
|
|
69
|
+
switch dcError.code {
|
|
70
|
+
case .invalidKey:
|
|
71
|
+
return CustomError.invalidKey
|
|
72
|
+
case .serverUnavailable:
|
|
73
|
+
return CustomError.serverUnavailable
|
|
74
|
+
default:
|
|
75
|
+
return error
|
|
76
|
+
}
|
|
77
|
+
}
|
|
78
|
+
}
|
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
import Foundation
|
|
2
|
+
import Capacitor
|
|
3
|
+
|
|
4
|
+
@objc(AppIntegrityPlugin)
|
|
5
|
+
public class AppIntegrityPlugin: CAPPlugin, CAPBridgedPlugin {
|
|
6
|
+
public let identifier = "AppIntegrityPlugin"
|
|
7
|
+
public let jsName = "AppIntegrity"
|
|
8
|
+
public let pluginMethods: [CAPPluginMethod] = [
|
|
9
|
+
CAPPluginMethod(name: "attestKey", returnType: CAPPluginReturnPromise),
|
|
10
|
+
CAPPluginMethod(name: "generateAssertion", returnType: CAPPluginReturnPromise),
|
|
11
|
+
CAPPluginMethod(name: "generateKey", returnType: CAPPluginReturnPromise),
|
|
12
|
+
CAPPluginMethod(name: "isAvailable", returnType: CAPPluginReturnPromise),
|
|
13
|
+
CAPPluginMethod(name: "prepareIntegrityToken", returnType: CAPPluginReturnPromise),
|
|
14
|
+
CAPPluginMethod(name: "requestIntegrityToken", returnType: CAPPluginReturnPromise)
|
|
15
|
+
]
|
|
16
|
+
|
|
17
|
+
public static let tag = "AppIntegrityPlugin"
|
|
18
|
+
|
|
19
|
+
private var implementation: AppIntegrity?
|
|
20
|
+
|
|
21
|
+
override public func load() {
|
|
22
|
+
self.implementation = AppIntegrity(plugin: self)
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
@objc func attestKey(_ call: CAPPluginCall) {
|
|
26
|
+
guard let implementation = implementation, implementation.isSupported() else {
|
|
27
|
+
rejectCallAsUnavailable(call)
|
|
28
|
+
return
|
|
29
|
+
}
|
|
30
|
+
do {
|
|
31
|
+
let options = try AttestKeyOptions(call)
|
|
32
|
+
implementation.attestKey(options, completion: { result, error in
|
|
33
|
+
if let error = error {
|
|
34
|
+
self.rejectCall(call, error)
|
|
35
|
+
} else {
|
|
36
|
+
self.resolveCall(call, result)
|
|
37
|
+
}
|
|
38
|
+
})
|
|
39
|
+
} catch {
|
|
40
|
+
self.rejectCall(call, error)
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
@objc func generateAssertion(_ call: CAPPluginCall) {
|
|
45
|
+
guard let implementation = implementation, implementation.isSupported() else {
|
|
46
|
+
rejectCallAsUnavailable(call)
|
|
47
|
+
return
|
|
48
|
+
}
|
|
49
|
+
do {
|
|
50
|
+
let options = try GenerateAssertionOptions(call)
|
|
51
|
+
implementation.generateAssertion(options, completion: { result, error in
|
|
52
|
+
if let error = error {
|
|
53
|
+
self.rejectCall(call, error)
|
|
54
|
+
} else {
|
|
55
|
+
self.resolveCall(call, result)
|
|
56
|
+
}
|
|
57
|
+
})
|
|
58
|
+
} catch {
|
|
59
|
+
self.rejectCall(call, error)
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
@objc func generateKey(_ call: CAPPluginCall) {
|
|
64
|
+
guard let implementation = implementation, implementation.isSupported() else {
|
|
65
|
+
rejectCallAsUnavailable(call)
|
|
66
|
+
return
|
|
67
|
+
}
|
|
68
|
+
implementation.generateKey(completion: { result, error in
|
|
69
|
+
if let error = error {
|
|
70
|
+
self.rejectCall(call, error)
|
|
71
|
+
} else {
|
|
72
|
+
self.resolveCall(call, result)
|
|
73
|
+
}
|
|
74
|
+
})
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
@objc func isAvailable(_ call: CAPPluginCall) {
|
|
78
|
+
implementation?.isAvailable(completion: { result, error in
|
|
79
|
+
if let error = error {
|
|
80
|
+
self.rejectCall(call, error)
|
|
81
|
+
} else {
|
|
82
|
+
self.resolveCall(call, result)
|
|
83
|
+
}
|
|
84
|
+
})
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
@objc func prepareIntegrityToken(_ call: CAPPluginCall) {
|
|
88
|
+
rejectCallAsUnimplemented(call)
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
@objc func requestIntegrityToken(_ call: CAPPluginCall) {
|
|
92
|
+
rejectCallAsUnimplemented(call)
|
|
93
|
+
}
|
|
94
|
+
|
|
95
|
+
private func rejectCall(_ call: CAPPluginCall, _ error: Error) {
|
|
96
|
+
CAPLog.print("[", AppIntegrityPlugin.tag, "] ", error)
|
|
97
|
+
let code = (error as? CustomError)?.code
|
|
98
|
+
call.reject(error.localizedDescription, code)
|
|
99
|
+
}
|
|
100
|
+
|
|
101
|
+
private func rejectCallAsUnavailable(_ call: CAPPluginCall) {
|
|
102
|
+
call.unavailable("This method is not available on this platform.")
|
|
103
|
+
}
|
|
104
|
+
|
|
105
|
+
private func rejectCallAsUnimplemented(_ call: CAPPluginCall) {
|
|
106
|
+
call.unimplemented("This method is not available on this platform.")
|
|
107
|
+
}
|
|
108
|
+
|
|
109
|
+
private func resolveCall(_ call: CAPPluginCall, _ result: Result?) {
|
|
110
|
+
if let result = result?.toJSObject() as? JSObject {
|
|
111
|
+
call.resolve(result)
|
|
112
|
+
} else {
|
|
113
|
+
call.resolve()
|
|
114
|
+
}
|
|
115
|
+
}
|
|
116
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import Foundation
|
|
2
|
+
import Capacitor
|
|
3
|
+
|
|
4
|
+
@objc public class AttestKeyOptions: NSObject {
|
|
5
|
+
let challenge: Data
|
|
6
|
+
let keyId: String
|
|
7
|
+
|
|
8
|
+
init(_ call: CAPPluginCall) throws {
|
|
9
|
+
self.challenge = try AttestKeyOptions.getChallengeFromCall(call)
|
|
10
|
+
self.keyId = try AttestKeyOptions.getKeyIdFromCall(call)
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
private static func getChallengeFromCall(_ call: CAPPluginCall) throws -> Data {
|
|
14
|
+
guard let challenge = call.getString("challenge") else {
|
|
15
|
+
throw CustomError.challengeMissing
|
|
16
|
+
}
|
|
17
|
+
guard let data = Data(base64Encoded: challenge) else {
|
|
18
|
+
throw CustomError.challengeInvalid
|
|
19
|
+
}
|
|
20
|
+
return data
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
private static func getKeyIdFromCall(_ call: CAPPluginCall) throws -> String {
|
|
24
|
+
guard let keyId = call.getString("keyId") else {
|
|
25
|
+
throw CustomError.keyIdMissing
|
|
26
|
+
}
|
|
27
|
+
return keyId
|
|
28
|
+
}
|
|
29
|
+
}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
import Foundation
|
|
2
|
+
import Capacitor
|
|
3
|
+
|
|
4
|
+
@objc public class GenerateAssertionOptions: NSObject {
|
|
5
|
+
let clientData: Data
|
|
6
|
+
let keyId: String
|
|
7
|
+
|
|
8
|
+
init(_ call: CAPPluginCall) throws {
|
|
9
|
+
self.clientData = try GenerateAssertionOptions.getClientDataFromCall(call)
|
|
10
|
+
self.keyId = try GenerateAssertionOptions.getKeyIdFromCall(call)
|
|
11
|
+
}
|
|
12
|
+
|
|
13
|
+
private static func getClientDataFromCall(_ call: CAPPluginCall) throws -> Data {
|
|
14
|
+
guard let clientData = call.getString("clientData") else {
|
|
15
|
+
throw CustomError.clientDataMissing
|
|
16
|
+
}
|
|
17
|
+
guard let data = Data(base64Encoded: clientData) else {
|
|
18
|
+
throw CustomError.clientDataInvalid
|
|
19
|
+
}
|
|
20
|
+
return data
|
|
21
|
+
}
|
|
22
|
+
|
|
23
|
+
private static func getKeyIdFromCall(_ call: CAPPluginCall) throws -> String {
|
|
24
|
+
guard let keyId = call.getString("keyId") else {
|
|
25
|
+
throw CustomError.keyIdMissing
|
|
26
|
+
}
|
|
27
|
+
return keyId
|
|
28
|
+
}
|
|
29
|
+
}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import Foundation
|
|
2
|
+
import Capacitor
|
|
3
|
+
|
|
4
|
+
@objc public class AttestKeyResult: NSObject, Result {
|
|
5
|
+
let attestationObject: Data
|
|
6
|
+
|
|
7
|
+
init(attestationObject: Data) {
|
|
8
|
+
self.attestationObject = attestationObject
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
@objc public func toJSObject() -> AnyObject {
|
|
12
|
+
var result = JSObject()
|
|
13
|
+
result["attestationObject"] = attestationObject.base64EncodedString()
|
|
14
|
+
return result as AnyObject
|
|
15
|
+
}
|
|
16
|
+
}
|