|
71 | 71 | private(set) weak var auth: Auth? |
72 | 72 | private(set) var agentConfig: AuthRecaptchaConfig? |
73 | 73 | private(set) var tenantConfigs: [String: AuthRecaptchaConfig] = [:] |
| 74 | + // Only initialized once. Recpatcha SDK does not support multiple clients. |
74 | 75 | private(set) var recaptchaClient: RCARecaptchaClientProtocol? |
75 | 76 | private static var _shared = AuthRecaptchaVerifier() |
| 77 | + |
76 | 78 | private let kRecaptchaVersion = "RECAPTCHA_ENTERPRISE" |
77 | 79 | init() {} |
78 | 80 |
|
|
91 | 93 | _ = shared(auth: auth) |
92 | 94 | } |
93 | 95 |
|
94 | | - func siteKey() -> String? { |
95 | | - if let tenantID = auth?.tenantID { |
96 | | - if let config = tenantConfigs[tenantID] { |
97 | | - return config.siteKey |
98 | | - } |
99 | | - return nil |
100 | | - } |
101 | | - return agentConfig?.siteKey |
102 | | - } |
103 | | - |
104 | 96 | func enablementStatus(forProvider provider: AuthRecaptchaProvider) |
105 | 97 | -> AuthRecaptchaEnablementStatus { |
106 | 98 | if let tenantID = auth?.tenantID, |
|
154 | 146 | #endif // !(COCOAPODS || SWIFT_PACKAGE) |
155 | 147 | } |
156 | 148 |
|
157 | | - private static var recaptchaClient: (any RCARecaptchaClientProtocol)? |
| 149 | + func retrieveRecaptchaConfig(forceRefresh: Bool) async throws { |
| 150 | + if !forceRefresh { |
| 151 | + if let tenantID = auth?.tenantID { |
| 152 | + if tenantConfigs[tenantID] != nil { |
| 153 | + return |
| 154 | + } |
| 155 | + } else if agentConfig != nil { |
| 156 | + return |
| 157 | + } |
| 158 | + } |
| 159 | + |
| 160 | + guard let auth = auth else { |
| 161 | + throw AuthErrorUtils.error(code: .recaptchaNotEnabled, |
| 162 | + message: "No requestConfiguration for Auth instance") |
| 163 | + } |
| 164 | + let request = GetRecaptchaConfigRequest(requestConfiguration: auth.requestConfiguration) |
| 165 | + let response = try await auth.backend.call(with: request) |
| 166 | + AuthLog.logInfo(code: "I-AUT000029", message: "reCAPTCHA config retrieval succeeded.") |
| 167 | + try await parseRecaptchaConfigFromResponse(response: response) |
| 168 | + } |
| 169 | + |
| 170 | + private func siteKey() -> String? { |
| 171 | + if let tenantID = auth?.tenantID { |
| 172 | + if let config = tenantConfigs[tenantID] { |
| 173 | + return config.siteKey |
| 174 | + } |
| 175 | + return nil |
| 176 | + } |
| 177 | + return agentConfig?.siteKey |
| 178 | + } |
| 179 | + |
| 180 | + func injectRecaptchaFields(request: any AuthRPCRequest, |
| 181 | + provider: AuthRecaptchaProvider, |
| 182 | + action: AuthRecaptchaAction) async throws { |
| 183 | + try await retrieveRecaptchaConfig(forceRefresh: false) |
| 184 | + if enablementStatus(forProvider: provider) != .off { |
| 185 | + let token = try await verify(forceRefresh: false, action: action) |
| 186 | + request.injectRecaptchaFields(recaptchaResponse: token, recaptchaVersion: kRecaptchaVersion) |
| 187 | + } else { |
| 188 | + request.injectRecaptchaFields(recaptchaResponse: nil, recaptchaVersion: kRecaptchaVersion) |
| 189 | + } |
| 190 | + } |
158 | 191 |
|
159 | 192 | #if COCOAPODS || SWIFT_PACKAGE // No recaptcha on internal build system. |
160 | 193 | private func recaptchaToken(siteKey: String, |
|
206 | 239 | } |
207 | 240 | } |
208 | 241 |
|
209 | | - func retrieveRecaptchaConfig(forceRefresh: Bool) async throws { |
210 | | - if !forceRefresh { |
211 | | - if let tenantID = auth?.tenantID { |
212 | | - if tenantConfigs[tenantID] != nil { |
213 | | - return |
214 | | - } |
215 | | - } else if agentConfig != nil { |
216 | | - return |
217 | | - } |
218 | | - } |
219 | | - |
220 | | - guard let auth = auth else { |
221 | | - throw AuthErrorUtils.error(code: .recaptchaNotEnabled, |
222 | | - message: "No requestConfiguration for Auth instance") |
223 | | - } |
224 | | - let request = GetRecaptchaConfigRequest(requestConfiguration: auth.requestConfiguration) |
225 | | - let response = try await auth.backend.call(with: request) |
226 | | - AuthLog.logInfo(code: "I-AUT000029", message: "reCAPTCHA config retrieval succeeded.") |
227 | | - try await parseRecaptchaConfigFromResponse(response: response) |
228 | | - } |
229 | | - |
230 | | - func parseRecaptchaConfigFromResponse(response: GetRecaptchaConfigResponse) async throws { |
| 242 | + private func parseRecaptchaConfigFromResponse(response: GetRecaptchaConfigResponse) async throws { |
231 | 243 | var enablementStatus: [AuthRecaptchaProvider: AuthRecaptchaEnablementStatus] = [:] |
232 | 244 | var isRecaptchaEnabled = false |
233 | 245 | if let enforcementState = response.enforcementState { |
|
263 | 275 | agentConfig = config |
264 | 276 | } |
265 | 277 | } |
266 | | - |
267 | | - func injectRecaptchaFields(request: any AuthRPCRequest, |
268 | | - provider: AuthRecaptchaProvider, |
269 | | - action: AuthRecaptchaAction) async throws { |
270 | | - try await retrieveRecaptchaConfig(forceRefresh: false) |
271 | | - if enablementStatus(forProvider: provider) != .off { |
272 | | - let token = try await verify(forceRefresh: false, action: action) |
273 | | - request.injectRecaptchaFields(recaptchaResponse: token, recaptchaVersion: kRecaptchaVersion) |
274 | | - } else { |
275 | | - request.injectRecaptchaFields(recaptchaResponse: nil, recaptchaVersion: kRecaptchaVersion) |
276 | | - } |
277 | | - } |
278 | 278 | } |
279 | 279 | #endif |
0 commit comments