@falconeta/capacitor-aws-amplify 0.0.1 → 0.0.3
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.
|
@@ -1,8 +1,260 @@
|
|
|
1
1
|
import Foundation
|
|
2
|
+
import Amplify
|
|
3
|
+
import AmplifyPlugins
|
|
4
|
+
import AWSPluginsCore
|
|
5
|
+
import AWSMobileClient
|
|
2
6
|
|
|
3
7
|
@objc public class AwsAmplify: NSObject {
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
8
|
+
private let TAG = "[Capacitor AwsAmplify]"
|
|
9
|
+
static public let instance = AwsCapacitor()
|
|
10
|
+
|
|
11
|
+
private let sessionSubject = BehaviorSubject<Optional<AuthSession>>(value: nil)
|
|
12
|
+
public var isLoggedIn$: Observable<Bool> {
|
|
13
|
+
sessionSubject.map { session in
|
|
14
|
+
session != nil
|
|
15
|
+
}
|
|
7
16
|
}
|
|
17
|
+
|
|
18
|
+
struct AccessTokenPayload: Decodable {
|
|
19
|
+
var device_key:String
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
override public init() {
|
|
23
|
+
super.init()
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
public func load() {
|
|
27
|
+
initAwsService()
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
func signIn(email: String,
|
|
31
|
+
password: String,
|
|
32
|
+
onSuccess: @escaping (AuthSignInResult) -> (),
|
|
33
|
+
onError: @escaping (any Error) -> ()) {
|
|
34
|
+
Amplify.Auth.signIn(username: email, password: password) { result in
|
|
35
|
+
do {
|
|
36
|
+
let signinResult: AuthSignInResult = try result.get()
|
|
37
|
+
print ("\(self.TAG) SignIn: " + (signinResult.isSignedIn ? "Sign in succeeded" : "Sign in not complete"))
|
|
38
|
+
onSuccess(signinResult)
|
|
39
|
+
} catch {
|
|
40
|
+
print ("\(self.TAG) Sign in failed \(error)")
|
|
41
|
+
onError(error)
|
|
42
|
+
}
|
|
43
|
+
}
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
public func federatedSignIn(
|
|
47
|
+
provider: String,
|
|
48
|
+
onSuccess: @escaping (AuthSignInResult) -> (),
|
|
49
|
+
onError: @escaping (any Error) -> ()
|
|
50
|
+
) {
|
|
51
|
+
var authProvider: AuthProvider
|
|
52
|
+
|
|
53
|
+
switch provider {
|
|
54
|
+
case "Google":
|
|
55
|
+
authProvider = AuthProvider.google
|
|
56
|
+
break
|
|
57
|
+
case "Facebook":
|
|
58
|
+
authProvider = AuthProvider.facebook
|
|
59
|
+
break
|
|
60
|
+
case "SignInWithApple":
|
|
61
|
+
authProvider = AuthProvider.apple
|
|
62
|
+
break
|
|
63
|
+
default:
|
|
64
|
+
authProvider = AuthProvider.google
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
print ("\(self.TAG) federatedSignIn \(authProvider)")
|
|
68
|
+
|
|
69
|
+
DispatchQueue.main.async {
|
|
70
|
+
Amplify.Auth.signInWithWebUI(for: authProvider, presentationAnchor: UIApplication.shared.windows.first!) { result in
|
|
71
|
+
switch result {
|
|
72
|
+
case .success(let result):
|
|
73
|
+
print("\(self.TAG) federatedSignIn effettuato con successo: \(result)")
|
|
74
|
+
onSuccess(result)
|
|
75
|
+
case .failure(let error):
|
|
76
|
+
print("\(self.TAG) Impossibile effettuare il federatedSignIn: \(error)")
|
|
77
|
+
onError(error)
|
|
78
|
+
}
|
|
79
|
+
}
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
public func signOut(
|
|
85
|
+
onSuccess: @escaping (Bool) -> (),
|
|
86
|
+
onError: @escaping (any Error) -> ()
|
|
87
|
+
) {
|
|
88
|
+
Amplify.Auth.signOut() { result in
|
|
89
|
+
switch result {
|
|
90
|
+
case .success:
|
|
91
|
+
onSuccess(true)
|
|
92
|
+
case .failure(let authError):
|
|
93
|
+
print("\(self.TAG) Sign out failed with error \(authError)")
|
|
94
|
+
onError(authError)
|
|
95
|
+
}
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
public func fetchAuthSession(
|
|
100
|
+
onSuccess: @escaping (JSObject) -> (),
|
|
101
|
+
onError: @escaping (any Error) -> ()
|
|
102
|
+
) {
|
|
103
|
+
Amplify.Auth.fetchAuthSession { result in
|
|
104
|
+
do {
|
|
105
|
+
let session = try result.get()
|
|
106
|
+
var ret: JSObject = [:]
|
|
107
|
+
|
|
108
|
+
// Get user sub or identity id
|
|
109
|
+
if let identityProvider = session as? AuthCognitoIdentityProvider {
|
|
110
|
+
let usersub = try identityProvider.getUserSub().get()
|
|
111
|
+
let identityId = try identityProvider.getIdentityId().get()
|
|
112
|
+
// print("User sub - \(usersub) and identity id \(identityId)")
|
|
113
|
+
|
|
114
|
+
ret["identityId"] = identityId
|
|
115
|
+
}
|
|
116
|
+
|
|
117
|
+
// Get AWS credentials
|
|
118
|
+
// if let awsCredentialsProvider = session as? AuthAWSCredentialsProvider {
|
|
119
|
+
// let credentials = try awsCredentialsProvider.getAWSCredentials().get()
|
|
120
|
+
// print("Access key - \(credentials.accessKey) ")
|
|
121
|
+
// }
|
|
122
|
+
|
|
123
|
+
// Get cognito user pool token
|
|
124
|
+
if let cognitoTokenProvider = session as? AuthCognitoTokensProvider {
|
|
125
|
+
let tokens = try cognitoTokenProvider.getCognitoTokens().get()
|
|
126
|
+
// print("Id token - \(tokens.idToken) ")
|
|
127
|
+
|
|
128
|
+
ret["accessToken"] = tokens.accessToken
|
|
129
|
+
ret["idToken"] = tokens.idToken
|
|
130
|
+
ret["refreshToken"] = tokens.refreshToken
|
|
131
|
+
|
|
132
|
+
// Amplify.Auth.fetchDevices { result in
|
|
133
|
+
// switch result {
|
|
134
|
+
// case .success(let devices):
|
|
135
|
+
// print("\(self.TAG) devices", devices)
|
|
136
|
+
// print("\(self.TAG) device IDs", devices.map(\.id))
|
|
137
|
+
// case .failure(let error):
|
|
138
|
+
// print("\(self.TAG) error", error)
|
|
139
|
+
// }
|
|
140
|
+
// }
|
|
141
|
+
|
|
142
|
+
// Retrieve the device key from the payload of access token
|
|
143
|
+
let accessToken = tokens.accessToken as NSString
|
|
144
|
+
// print("\(self.TAG) accessToken - \(tokens.idToken) ")
|
|
145
|
+
let chunks = accessToken.components(separatedBy: ".")
|
|
146
|
+
let accessTokenPayload = self.decodeJWTPart(part: chunks[1])
|
|
147
|
+
let deviceKey = accessTokenPayload?.device_key
|
|
148
|
+
|
|
149
|
+
ret["deviceKey"] = deviceKey
|
|
150
|
+
}
|
|
151
|
+
|
|
152
|
+
self.sessionSubject.onNext(session)
|
|
153
|
+
|
|
154
|
+
print("\(self.TAG) - Fetch Auth Session successfully")
|
|
155
|
+
// print("\(self.TAG) - \(ret)")
|
|
156
|
+
onSuccess(ret)
|
|
157
|
+
} catch {
|
|
158
|
+
print("\(self.TAG) Fetch auth session failed with error - \(error)")
|
|
159
|
+
onError(error)
|
|
160
|
+
}
|
|
161
|
+
}
|
|
162
|
+
}
|
|
163
|
+
|
|
164
|
+
public func getCurrentUser() -> AuthUser {
|
|
165
|
+
return Amplify.Auth.getCurrentUser()!
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
func base64StringWithPadding(encodedString: String) -> String {
|
|
169
|
+
var stringTobeEncoded = encodedString.replacingOccurrences(of: "-", with: "+")
|
|
170
|
+
.replacingOccurrences(of: "_", with: "/")
|
|
171
|
+
let paddingCount = encodedString.count % 4
|
|
172
|
+
for _ in 0..<paddingCount {
|
|
173
|
+
stringTobeEncoded += "="
|
|
174
|
+
}
|
|
175
|
+
return stringTobeEncoded
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
func decodeJWTPart(part: String) -> AccessTokenPayload? {
|
|
179
|
+
let payloadPaddingString = base64StringWithPadding(encodedString: part)
|
|
180
|
+
guard let payloadData = Data(base64Encoded: payloadPaddingString) else {
|
|
181
|
+
fatalError("payload could not converted to data")
|
|
182
|
+
}
|
|
183
|
+
return try? JSONDecoder().decode(AccessTokenPayload.self, from: payloadData)
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
private func initAwsService() {
|
|
187
|
+
do {
|
|
188
|
+
try Amplify.add(plugin: AWSCognitoAuthPlugin())
|
|
189
|
+
try Amplify.configure()
|
|
190
|
+
print("\(self.TAG) Amplify configured with auth plugin")
|
|
191
|
+
|
|
192
|
+
Amplify.Hub.listen(to: .auth) { payload in
|
|
193
|
+
|
|
194
|
+
switch payload.eventName {
|
|
195
|
+
case HubPayload.EventName.Auth.signedIn:
|
|
196
|
+
print("\(self.TAG) User signed in")
|
|
197
|
+
// Update UI
|
|
198
|
+
break
|
|
199
|
+
|
|
200
|
+
case HubPayload.EventName.Auth.sessionExpired:
|
|
201
|
+
print("\(self.TAG) Session expired")
|
|
202
|
+
// Re-authenticate the user
|
|
203
|
+
break
|
|
204
|
+
|
|
205
|
+
case HubPayload.EventName.Auth.signedOut:
|
|
206
|
+
self.sessionSubject.onNext(nil)
|
|
207
|
+
print("\(self.TAG) User signed out")
|
|
208
|
+
// Update UI
|
|
209
|
+
break
|
|
210
|
+
|
|
211
|
+
case HubPayload.EventName.Auth.userDeleted:
|
|
212
|
+
print("\(self.TAG) User deleted")
|
|
213
|
+
// Update UI
|
|
214
|
+
break
|
|
215
|
+
|
|
216
|
+
case HubPayload.EventName.Auth.socialWebUISignInAPI:
|
|
217
|
+
print("\(self.TAG) Social login")
|
|
218
|
+
// self.fetchAuthSession { _ in } onError: { _ in }
|
|
219
|
+
|
|
220
|
+
break
|
|
221
|
+
|
|
222
|
+
default:
|
|
223
|
+
break
|
|
224
|
+
}
|
|
225
|
+
|
|
226
|
+
// print("\(self.TAG) Amplify.Hub.listen \(payload)")
|
|
227
|
+
}
|
|
228
|
+
} catch {
|
|
229
|
+
print("\(self.TAG) An error occurred setting up Amplify: \(error)")
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
|
|
233
|
+
public func getSession() -> Optional<AuthSession> {
|
|
234
|
+
do {
|
|
235
|
+
return try self.sessionSubject.value()
|
|
236
|
+
} catch {
|
|
237
|
+
return nil
|
|
238
|
+
}
|
|
239
|
+
}
|
|
240
|
+
|
|
241
|
+
// public func hasFullRegistration() -> Observable<Bool> {
|
|
242
|
+
// return Observable.create { observer in
|
|
243
|
+
// AWSMobileClient.default().getUserAttributes { (userAttributes, error) in
|
|
244
|
+
// if error != nil {
|
|
245
|
+
// print("\(self.TAG) User attributes error: \(error)")
|
|
246
|
+
// observer.onNext(false)
|
|
247
|
+
// } else if let userAttributes = userAttributes {
|
|
248
|
+
// print("\(self.TAG) User attributes: \(userAttributes)")
|
|
249
|
+
// let registrationFull = userAttributes["custom:registration_full"]
|
|
250
|
+
// if registrationFull != nil {
|
|
251
|
+
// observer.onNext(true)
|
|
252
|
+
// } else {
|
|
253
|
+
// observer.onNext(false)
|
|
254
|
+
// }
|
|
255
|
+
// }
|
|
256
|
+
// }
|
|
257
|
+
// return Disposables.create()
|
|
258
|
+
// }
|
|
259
|
+
// }
|
|
8
260
|
}
|
|
@@ -4,5 +4,7 @@
|
|
|
4
4
|
// Define the plugin using the CAP_PLUGIN Macro, and
|
|
5
5
|
// each method the plugin supports using the CAP_PLUGIN_METHOD macro.
|
|
6
6
|
CAP_PLUGIN(AwsAmplifyPlugin, "AwsAmplify",
|
|
7
|
-
CAP_PLUGIN_METHOD(
|
|
7
|
+
CAP_PLUGIN_METHOD(signIn, CAPPluginReturnPromise);
|
|
8
|
+
CAP_PLUGIN_METHOD(signOut, CAPPluginReturnPromise);
|
|
9
|
+
CAP_PLUGIN_METHOD(federatedSignIn, CAPPluginReturnPromise);
|
|
8
10
|
)
|
|
@@ -9,10 +9,74 @@ import Capacitor
|
|
|
9
9
|
public class AwsAmplifyPlugin: CAPPlugin {
|
|
10
10
|
private let implementation = AwsAmplify()
|
|
11
11
|
|
|
12
|
-
@objc func
|
|
13
|
-
let
|
|
14
|
-
call.
|
|
15
|
-
|
|
16
|
-
|
|
12
|
+
@objc func signIn(_ call: CAPPluginCall) {
|
|
13
|
+
let email = call.getString("email") ?? ""
|
|
14
|
+
let password = call.getString("password") ?? ""
|
|
15
|
+
|
|
16
|
+
self.awsCapacitor.signIn(
|
|
17
|
+
email: email,
|
|
18
|
+
password: password,
|
|
19
|
+
onSuccess: {data in
|
|
20
|
+
self.awsCapacitor.fetchAuthSession(
|
|
21
|
+
onSuccess: {session in
|
|
22
|
+
call.resolve(session)
|
|
23
|
+
},
|
|
24
|
+
onError: {error in
|
|
25
|
+
call.reject(error.localizedDescription)
|
|
26
|
+
})
|
|
27
|
+
},
|
|
28
|
+
onError: {error in
|
|
29
|
+
print(error)
|
|
30
|
+
call.reject(error.localizedDescription)
|
|
31
|
+
})
|
|
17
32
|
}
|
|
33
|
+
|
|
34
|
+
@objc func signOut(_ call: CAPPluginCall) {
|
|
35
|
+
self.awsCapacitor.signOut(
|
|
36
|
+
onSuccess: { success in
|
|
37
|
+
call.resolve([
|
|
38
|
+
"logout": success
|
|
39
|
+
])
|
|
40
|
+
}, onError: { error in
|
|
41
|
+
call.reject(error.localizedDescription)
|
|
42
|
+
})
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
@objc func federatedSignIn(_ call: CAPPluginCall) {
|
|
46
|
+
let provider = call.getString("provider") ?? ""
|
|
47
|
+
|
|
48
|
+
self.awsCapacitor.federatedSignIn(
|
|
49
|
+
provider: provider,
|
|
50
|
+
onSuccess: { data in
|
|
51
|
+
print("federatedSignIn onSuccess \(data)")
|
|
52
|
+
self.awsCapacitor.fetchAuthSession(
|
|
53
|
+
onSuccess: {session in
|
|
54
|
+
call.resolve(session)
|
|
55
|
+
},
|
|
56
|
+
onError: {error in
|
|
57
|
+
call.reject(error.localizedDescription)
|
|
58
|
+
})
|
|
59
|
+
},
|
|
60
|
+
onError: { error in
|
|
61
|
+
print(error)
|
|
62
|
+
call.reject(error.localizedDescription)
|
|
63
|
+
})
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
// var permissionCallID: String?
|
|
67
|
+
// var locationManager: CLLocationManager?
|
|
68
|
+
|
|
69
|
+
// @objc override public func requestPermissions(_ call: CAPPluginCall) {
|
|
70
|
+
// if let manager = locationManager, CLLocationManager.locationServicesEnabled() {
|
|
71
|
+
// if CLLocationManager.authorizationStatus() == .notDetermined {
|
|
72
|
+
// bridge?.saveCall(call)
|
|
73
|
+
// permissionCallID = call.callbackId
|
|
74
|
+
// manager.requestWhenInUseAuthorization()
|
|
75
|
+
// } else {
|
|
76
|
+
// checkPermissions(call)
|
|
77
|
+
// }
|
|
78
|
+
// } else {
|
|
79
|
+
// call.reject("Location services are disabled")
|
|
80
|
+
// }
|
|
81
|
+
// }
|
|
18
82
|
}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@falconeta/capacitor-aws-amplify",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.3",
|
|
4
4
|
"description": "plugin that handle amplify features",
|
|
5
5
|
"main": "dist/plugin.cjs.js",
|
|
6
6
|
"module": "dist/esm/index.js",
|
|
@@ -62,7 +62,9 @@
|
|
|
62
62
|
"typescript": "~4.1.5"
|
|
63
63
|
},
|
|
64
64
|
"peerDependencies": {
|
|
65
|
-
"@capacitor/core": "^5.0.0"
|
|
65
|
+
"@capacitor/core": "^5.0.0",
|
|
66
|
+
"@aws-amplify/auth": "^5.6.5",
|
|
67
|
+
"aws-amplify": "^5.3.11"
|
|
66
68
|
},
|
|
67
69
|
"prettier": "@ionic/prettier-config",
|
|
68
70
|
"swiftlint": "@ionic/swiftlint-config",
|