Dart/Flutter PostFrameCallBack 和 Uri.base.origin
Dart/Flutter PostFrameCallBack and Uri.base.origin
我正在尝试实现一个系统,用户将调用外部网站进行登录并在 url 中发回密钥。如果我在 Main.dart 中调用此应用程序屏幕作为主屏幕时调用此代码块,它会完全按预期工作:代码检查 'token' 是否在 URL 中,如果不在将重定向到外部站点以供用户登录,检索密钥并发送回 flutter 屏幕,现在它可以在执行 initState() 时找到令牌。
import 'dart:convert';
import 'package:universal_html/html.dart' as html;
import 'package:flutter/material.dart';
class LoginScreen extends StatefulWidget {
static final routeName = "/login";
const LoginScreen({Key? key}) : super(key: key);
@override
_LoginScreenState createState() => _LoginScreenState();
}
class _LoginScreenState extends State<LoginScreen> {
var tempToken;
@override
void initState() {
super.initState();
final currentUrl = Uri.base;
print(currentUrl);
if (currentUrl.queryParameters['token'] == null) {
print('looking for token');
// You are not connected so redirect to the login
WidgetsBinding.instance!.addPostFrameCallback((_) async {
html.window.location.assign(
'http://localhost:8080/auth/?source=app&after=${base64Encode(utf8.encode(currentUrl.origin))}', //where i send in the redirect back
);
});
} else {
tempToken = currentUrl.queryParameters['token'].toString();
print(tempToken);
}
}
@override
Widget build(BuildContext context) {
return const Center(child: CircularProgressIndicator());
}
问题
当我尝试从我的应用程序的欢迎屏幕重定向到此屏幕时,问题就出现了。代码的设置方式会将我发送回 currentUrl,它将是“/”而不是“/login”,将我发送到欢迎屏幕,并且令牌不再位于 url 中。知道我应该从这里去哪里吗?
我们发现在 Flutter 网络应用程序启动后立即抓取完整内容很有用 href
,代码如下:
Map<String, String>? initialQueryParameters;
void main() {
initialQueryParameters = getHref().queryParameters;
runApp(const Controller());
}
这会在您创建 MaterialApp
之前捕获任何查询参数的值,并开始路由到页面,这将更改 href
.
我们的流程是:
- index.html
- 一些 oauth 网站,重定向回
- index.html?someParam=someValue(或者可以是 index.html/#/route?...)
Flutter应用第一次运行时,someParam为null。重定向回来后,应用程序第二次运行,但现在 someParam 设置为 someValue。因为这是在启动时抓取并存储在全局 initialQueryParameters
中,所以可以在需要时检查它,即使在路由和导航可能重写 href 之后也可用。
我正在尝试实现一个系统,用户将调用外部网站进行登录并在 url 中发回密钥。如果我在 Main.dart 中调用此应用程序屏幕作为主屏幕时调用此代码块,它会完全按预期工作:代码检查 'token' 是否在 URL 中,如果不在将重定向到外部站点以供用户登录,检索密钥并发送回 flutter 屏幕,现在它可以在执行 initState() 时找到令牌。
import 'dart:convert';
import 'package:universal_html/html.dart' as html;
import 'package:flutter/material.dart';
class LoginScreen extends StatefulWidget {
static final routeName = "/login";
const LoginScreen({Key? key}) : super(key: key);
@override
_LoginScreenState createState() => _LoginScreenState();
}
class _LoginScreenState extends State<LoginScreen> {
var tempToken;
@override
void initState() {
super.initState();
final currentUrl = Uri.base;
print(currentUrl);
if (currentUrl.queryParameters['token'] == null) {
print('looking for token');
// You are not connected so redirect to the login
WidgetsBinding.instance!.addPostFrameCallback((_) async {
html.window.location.assign(
'http://localhost:8080/auth/?source=app&after=${base64Encode(utf8.encode(currentUrl.origin))}', //where i send in the redirect back
);
});
} else {
tempToken = currentUrl.queryParameters['token'].toString();
print(tempToken);
}
}
@override
Widget build(BuildContext context) {
return const Center(child: CircularProgressIndicator());
}
问题 当我尝试从我的应用程序的欢迎屏幕重定向到此屏幕时,问题就出现了。代码的设置方式会将我发送回 currentUrl,它将是“/”而不是“/login”,将我发送到欢迎屏幕,并且令牌不再位于 url 中。知道我应该从这里去哪里吗?
我们发现在 Flutter 网络应用程序启动后立即抓取完整内容很有用 href
,代码如下:
Map<String, String>? initialQueryParameters;
void main() {
initialQueryParameters = getHref().queryParameters;
runApp(const Controller());
}
这会在您创建 MaterialApp
之前捕获任何查询参数的值,并开始路由到页面,这将更改 href
.
我们的流程是:
- index.html
- 一些 oauth 网站,重定向回
- index.html?someParam=someValue(或者可以是 index.html/#/route?...)
Flutter应用第一次运行时,someParam为null。重定向回来后,应用程序第二次运行,但现在 someParam 设置为 someValue。因为这是在启动时抓取并存储在全局 initialQueryParameters
中,所以可以在需要时检查它,即使在路由和导航可能重写 href 之后也可用。