Flutter使用oauth2_client包无法正确跳转至指定redirectUri
问题原因
flutter_web_auth_2的CallbackActivity完成授权后,只会将应用从后台唤起回到发起授权的栈顶页面(即HomePage),并不会自动触发GoRouter的deeplink路由跳转。虽然授权成功拿到了token,但redirectUri的查询参数不会自动传递给路由,导致无法跳转到AboutPage。
解决方案
方案一:手动处理授权结果并导航(推荐)
既然已经确认oauth2Helper能成功获取token,可直接从授权回调的响应中提取realmId,然后手动调用GoRouter导航到AboutPage:
修改BooksmartOAuthHelper的authenticateOAuth2Helper方法:
void authenticateOAuth2Helper(String accountingApp, BuildContext context) async { switch (accountingApp) { case 'Quickbooks': IntuitOAuth2Client client = IntuitOAuth2Client( redirectUri: 'https://booksmart-6870c.web.app/about', customUriScheme: 'https' ); oauth2Helper = OAuth2Helper( client, grantType: OAuth2Helper.authorizationCode, clientId: intuitClientId, clientSecret: intuitClientSecret, scopes: ['com.intuit.quickbooks.accounting', 'com.intuit.quickbooks.payment'], ); // 发起授权并获取token final tokenResponse = await oauth2Helper!.fetchToken(); // 从tokenResponse的附加参数中提取realmId if (tokenResponse.additionalParameters != null) { final realmId = tokenResponse.additionalParameters!['realmId']; if (realmId != null) { quickbooksRealmId = realmId; // 手动导航到AboutPage if (context.mounted) { GoRouter.of(context).push('/about?realmId=$realmId'); } } } default: throw UnimplementedError('$accountingApp is not supported yet'); } }
方案二:调整AndroidManifest配置,让deeplink直接触发路由
将deeplink的intent-filter移回MainActivity,同时保留CallbackActivity的配置仅处理授权回调:
<manifest ...> <application ...> <activity android:name=".MainActivity" ...> <!-- 添加deeplink的intent-filter --> <intent-filter android:autoVerify="true"> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="https" android:host="booksmart-6870c.web.app" android:pathPrefix="/about" /> </intent-filter> </activity> <meta-data android:name="flutter_deeplinking_enabled" android:value="true" /> <activity android:name="com.linusu.flutter_web_auth_2.CallbackActivity" android:exported="true"> <intent-filter android:label="flutter_web_auth_2"> <action android:name="android.intent.action.VIEW" /> <category android:name="android.intent.category.DEFAULT" /> <category android:name="android.intent.category.BROWSABLE" /> <data android:scheme="https" android:host="booksmart-6870c.web.app" android:pathPrefix="/about" /> </intent-filter> </activity> </manifest>
同时在main.dart中确保GoRouter能处理deeplink:
void main() { runApp(const MyApp()); } class MyApp extends StatelessWidget { const MyApp({super.key}); @override Widget build(BuildContext context) { return MaterialApp.router( routerConfig: router, ); } }
额外注意
- 方案一更直接,不需要依赖系统deeplink的跳转逻辑,避免了Activity配置冲突的问题。
- 若使用方案二,需确保
assetlinks.json配置正确,且Android设备已验证App Link(可通过adb shell dumpsys package domain-preferred-apps命令验证)。
内容的提问来源于stack exchange,提问作者Jay Boychuk
相关产品推荐
相关产品推荐

