从Authy迁移至Twilio Verify后用户未验证问题求助
Authy 迁移至 Twilio Verify API 后验证失败问题排查
我们此前参考相关步骤将Authy迁移至Verify API,但迁移完成后用户仍无法完成验证。以下是使用的代码:
迁移主逻辑代码
Dim oAuthy = New clsAuthy(apiKey, False) 'Fetch details from authy to migrate to verify Dim authyDetails As clsAuthySecret = oAuthy.GetAuthyDetails(item("TwilioAuthyId")) oAuthy = Nothing 'Migrate data to verify API With oVerify .GenerateQRCode(item("UserName"), item("UserId").ToString(), authyDetails.Secret) .VerifyToken(.FactorID, authyDetails.OTP, item("UserId").ToString()) FactorId = .FactorID VerifyUrl = .QrUrl End With
Authy 信息导出方法
Public Function GetAuthyDetails(ByRef AuthyID As String) As clsAuthySecret Dim apiResponse As clsAuthySecret Dim url = String.Format("{0}/protected/json/users/{1}/secret/export", Me.baseUrl, AuthyID, Me.apikey) Try client.Headers.Set("X-Authy-API-Key", Me.apikey) Dim response = client.DownloadString(url) apiResponse = JsonConvert.DeserializeObject(Of clsAuthySecret)(response) apiResponse.RawResponse = response Catch ex As WebException apiResponse = New clsAuthySecret() apiResponse.Status = AuthyStatus.BadRequest 'bad request apiResponse.Message = ex.Message 'apiResponse.RawResponse = ex.Response.ToString() End Try If (apiResponse.Success) Then apiResponse.Status = AuthyStatus.Success End If Return apiResponse End Function
Verify API 相关方法
Public Function GenerateQRCode(ByVal Email As String, ByVal UserID As String, ByVal Secret As String ) As Task(Of Boolean) Try TwilioClient.Init(_accountSID, _authToken) Dim newFactor = NewFactorResource.Create(friendlyName:=Email, factorType:=NewFactorResource.FactorTypesEnum.Totp, pathServiceSid:=_serviceSID, pathIdentity:=UserID.ToLower(), bindingSecret:=Secret) _factorID = newFactor.Sid _qrUrl = JObject.Parse(newFactor.Binding.ToString())("uri") Catch ex As Exception _responseMessage = ex.Message Return False End Try Return True End Function Public Function VerifyToken(ByVal FactorID As String, ByVal Token As String, ByVal UserID As String ) As Task(Of Boolean) Try TwilioClient.Init(_accountSID, _authToken) Dim factor = FactorResource.Update(authPayload:=Token, pathServiceSid:=_serviceSID, pathIdentity:=UserID.ToLower(), pathSid:=FactorID) If factor.Status.ToString = "verified" Then Return True Else Return False End If Catch ex As Exception _responseMessage = ex.Message Return False End Try End Function
关键问题与遗漏步骤分析
- 异步方法未正确等待:
GenerateQRCode和VerifyToken均为异步方法(返回Task(Of Boolean)),但调用时未使用Await关键字,会导致代码执行顺序混乱——比如还未成功创建Factor就发起验证请求,或FactorID未正确赋值就传入验证方法。 - 验证Token的API调用错误:当前
VerifyToken方法使用FactorResource.Update验证Token,这是错误的。Twilio Verify API中验证TOTP Token应使用VerifyFactorResource.Create方法,FactorResource.Update仅用于更新Factor属性(如友好名称),不负责验证操作。 - Secret编码格式检查:确认从Authy导出的
authyDetails.Secret是否为Base32编码格式。Twilio Verify的bindingSecret要求必须是Base32编码字符串,若Authy返回的是其他编码(如Hex),需先转换为Base32格式。 - 错误信息不完整:Catch块仅记录
Exception.Message,建议捕获WebException时读取响应流内容,获取Twilio返回的具体错误信息,便于精准定位问题。
修正后的核心代码示例
异步调用修正
Dim oAuthy = New clsAuthy(apiKey, False) 'Fetch details from authy to migrate to verify Dim authyDetails As clsAuthySecret = oAuthy.GetAuthyDetails(item("TwilioAuthyId")) oAuthy = Nothing 'Migrate data to verify API - 使用Await等待异步方法完成 With oVerify Await .GenerateQRCode(item("UserName"), item("UserId").ToString(), authyDetails.Secret) Dim verifySuccess = Await .VerifyToken(.FactorID, authyDetails.OTP, item("UserId").ToString()) FactorId = .FactorID VerifyUrl = .QrUrl End With
验证方法修正
Public Async Function VerifyToken(ByVal FactorID As String, ByVal Token As String, ByVal UserID As String ) As Task(Of Boolean) Try TwilioClient.Init(_accountSID, _authToken) ' 使用VerifyFactorResource.Create验证Token Dim verifyResult = VerifyFactorResource.Create( authPayload:=Token, pathServiceSid:=_serviceSID, pathIdentity:=UserID.ToLower(), pathSid:=FactorID ) Return verifyResult.Status = "verified" Catch ex As Exception ' 记录完整错误信息 If TypeOf ex Is WebException Then Using reader = New StreamReader(CType(ex, WebException).Response.GetResponseStream()) _responseMessage = reader.ReadToEnd() End Using Else _responseMessage = ex.Message End If Return False End Try End Function
内容的提问来源于stack exchange,提问作者Shivam Gupta
相关产品推荐
相关产品推荐

