api - 如何在flutter中调用initState中的异步方法
问题描述
我需要从端点获取一些信息。我有这个方法:
List<Widget> cardsList = List();
List<dynamic> cardsId = List();
addToList() async {
var jsonData = await Provider.of<CardData>(context).cardsList;
print(jsonData);
for (var i = 0, len = jsonData.length; i < len; i++) {
if (jsonData[i]['account_type'] == "1") {
cardsList.add(
BankCard(
bankName: jsonData[i]['title'],
colors: [Color(0xFFD00E00), Color(0xFFF44336)],
cardNumber: jsonData[i]['number'],
cardDesc: jsonData[i]['description'],
),
);
cardsId.add(jsonData[i]['id']);
}
}
}
和一个名为 CardData 的作为提供者数据的类:
import 'package:flutter/material.dart';
import '../cards/cards.dart';
class CardData extends ChangeNotifier {
static Cards cards = Cards();
Future<dynamic> cardsList = cards.getCards();
}
和一个名为 Card 的类来发送请求并执行所有其他操作:
import 'dart:convert';
import 'package:http/http.dart' as http;
import 'package:shared_preferences/shared_preferences.dart';
class Cards {
String _accessToken;
String _refreshToken;
Future<dynamic> getCards() async {
SharedPreferences sharedPreferences = await SharedPreferences.getInstance();
_accessToken = sharedPreferences.getString("access");
_refreshToken = sharedPreferences.getString("refresh");
var jsonData;
var response = await sendRequestToGetCards(
url: "http://10.0.2.2:8000/accounts/list/", accessToken: _accessToken);
if (response.statusCode == 200) {
jsonData = json.decode(utf8.decode(response.bodyBytes));
return jsonData;
} else if (response.statusCode == 401) {
_accessToken = await getNewAccessToken(_refreshToken);
response = await sendRequestToGetCards(
url: "http://10.0.2.2:8000/accounts/list/",
accessToken: _accessToken);
if (response.statusCode == 200) {
jsonData = json.decode(utf8.decode(response.bodyBytes));
return jsonData;
}
}
}
getNewAccessToken(String refreshToken) async {
var refreshResponse = await http.post(
"http://10.0.2.2:8000/users/api/token/refresh/",
body: {'refresh': refreshToken});
if (refreshResponse.statusCode == 200) {
var jsonData = json.decode(refreshResponse.body);
return jsonData['access'];
}
}
sendRequestToGetCards({String url, String accessToken}) async {
var response = await http.get(
url,
headers: {"Authorization": "Bearer $accessToken"},
);
return response;
}
}
但是当我在 initState 中调用addToList方法在build 方法之前检索数据时,主 UI 消失了。
它出什么问题了?
解决方案
您可以在 initState 中调用异步函数,但由于它本身不是异步函数,因此在继续构建方法之前不会等待期货完成,这就是您的 UI 消失的原因,因为它正在构建没有数据所以有没有卡。我建议在您的构建方法中使用FutureBuilder在异步函数返回时进行构建。
推荐阅读
- php - 多态,获取用户喜欢的活动
- c++ - GLFW glfwCreateWindowSurface 返回 -7
- c++ - 如何从 Windows 控制台调用 .exe (C++) 以在不同目录(或任何目录)中创建文件夹?
- .htaccess - .htaccess 中存在查询字符串时重定向 URL 时遇到问题
- python - 如何使用 matplotlib 在一个条形图上添加两个数据集
- laravel - Laravel 使用单数表名作为模型,如何使用默认复数?
- amazon-web-services - AWS NAT over Direct Connect
- python - 如何从长度不均匀的列表中创建分组条形图
- python - 如何在类之外打印变量?
- c - 每当我尝试拆分字符串时都会遇到内存问题