API请求获取flutter dart中的对话和消息

lsmepo6l  于 2023-10-13  发布在  Flutter
关注(0)|答案(1)|浏览(141)

我在一个应用程序上使用API来获取用户信息,并在另一个选项卡中获取该特定用户的对话和消息线程,因为我知道我需要pid和tac(选项卡访问代码)作为参数,为了获取它们,它们位于另一个API(getTabAccessCode)的响应体中,我使用Postman尝试调用,它们工作正常。
下面是user_service.dart,在postman中,在其body响应中的getTabAccessCode函数中,我获得了User id,pid和tac(tab访问代码):

  1. static Future<Map<String, dynamic>> fetchUserInfo(String accessToken) async {
  2. final response = await http.get(
  3. Uri.parse(
  4. 'https://example.app/auth/example/protocol/userinfo'),
  5. headers: {
  6. 'Authorization': 'Bearer $accessToken',
  7. },
  8. );
  9. if (response.statusCode == 200) {
  10. return json.decode(response.body);
  11. } else {
  12. throw Exception(
  13. 'Error fetching user information: ${response.statusCode}');
  14. }
  15. }
  16. // This function takes a global ID and an access token as parameters
  17. static Future<Map<String, dynamic>> getTabAccessCode(
  18. String globalId, String accessToken) async {
  19. // This is the URL for the device registration
  20. final tokenUrl =
  21. 'http://example.com:9080/exp/rest/DeviceRegistration';
  22. // This is the HTTP GET request with the query parameters
  23. final response = await http.get(
  24. Uri.parse(
  25. '$tokenUrl?country=United%20Kingdom&emailID=example%40gmail.com&name=Patient%20Eleven&zoneinfo=Europe%2FParis&GlobalId=$globalId&postal_code=70001&gender=Female&accesstoken=$accessToken&appname=example'),
  26. );
  27. // This checks if the response status code is 200, which means OK
  28. if (response.statusCode == 200) {
  29. // This parses the response body into a Dart object
  30. final responseBody = jsonDecode(response.body);
  31. // Print the entire response line
  32. print('Response: $responseBody');
  33. // This gets the value of "TabAccCode"
  34. final tabAccessCode = responseBody["TabAccCode"];
  35. // If the response includes "pid" and "doctor id", retrieve them as well
  36. final pid = responseBody["pid"];
  37. final doctorid = responseBody["doctorid"];
  38. // Create a map to return all the values
  39. final resultMap = {
  40. "tabAccessCode": tabAccessCode,
  41. "pid": pid,
  42. "doctorid": doctorid,
  43. };
  44. // This returns the map containing all the values
  45. return resultMap;
  46. } else {
  47. // This throws an exception if the response status code is not 200
  48. throw Exception('Error getting Tab Access Info: ${response.statusCode}');
  49. }
  50. }

注意:getTabAccessCode API调用的响应中tab访问代码的名称为TabAccCode,而在会话和消息API调用的参数中则称为tac
有人能帮助我吗?我是一个使用API的新手,我被困在这里了。
这是conversation_page.dart,下面我试图调用函数(getTabAccessCode),它的响应中有pid和tac,但它说globalid和accesstoken是未定义的,因为它们已经定义了,但在user_service.dart中:

  1. import 'dart:convert';
  2. import 'package:efindadoc/screens/messages_page.dart';
  3. import 'package:efindadoc/screens/user_service.dart';
  4. import 'package:flutter/material.dart';
  5. import 'package:http/http.dart' as http;
  6. class ConversationPage extends StatefulWidget {
  7. @override
  8. _ConversationPageState createState() => _ConversationPageState();
  9. }
  10. class _ConversationPageState extends State<ConversationPage> {
  11. List<Map<String, dynamic>> conversations = [];
  12. String pid = '';
  13. String tac = '';
  14. @override
  15. void initState() {
  16. super.initState();
  17. initConversations();
  18. }
  19. Future<void> initConversations() async {
  20. var accessInfo = await UserService.getTabAccessCode(globalId, accessToken);
  21. var pid = accessInfo["pid"];
  22. var tac = accessInfo["tabAccessCode"];
  23. await fetchConversations(pid, tac);
  24. }
  25. Future<void> fetchConversations(String pid, String tac) async {
  26. final response = await http.get(Uri.parse(
  27. 'https://example.com/docs/getMessages?pid=$pid&user_type=doctor&function=conversation&tac=$tac&view_as=doctor',
  28. ));
  29. if (response.statusCode == 200) {
  30. final data = jsonDecode(response.body);
  31. if (data['success']) {
  32. final List<dynamic> conversationData = data['data'];
  33. conversations = conversationData
  34. .map((conversation) => Map<String, dynamic>.from(conversation))
  35. .toList();
  36. }
  37. } else {
  38. throw Exception('Failed to load conversation data');
  39. }
  40. setState(() {});
  41. }
  42. @override
  43. Widget build(BuildContext context) {
  44. return Scaffold(
  45. appBar: AppBar(
  46. title: Text('Conversation Page'),
  47. ),
  48. body: ListView.builder(
  49. itemCount: conversations.length,
  50. itemBuilder: (context, index) {
  51. final conversation = conversations[index];
  52. return ListTile(
  53. title: Text(conversation['title']),
  54. subtitle: Text(conversation['created']),
  55. onTap: () {
  56. Navigator.push(
  57. context,
  58. MaterialPageRoute(
  59. builder: (context) => MessagePage(
  60. conversationId: conversation['id'], pid: pid, tac: tac),
  61. ),
  62. );
  63. },
  64. );
  65. },
  66. ),
  67. );
  68. }
  69. }

这是messages_page.dart:

  1. import 'dart:convert';
  2. import 'package:flutter/material.dart';
  3. import 'package:http/http.dart' as http;
  4. class MessagePage extends StatefulWidget {
  5. final String conversationId;
  6. final String pid;
  7. final String tac;
  8. MessagePage({required this.conversationId, required this.pid, required this.tac});
  9. @override
  10. _MessagePageState createState() => _MessagePageState();
  11. }
  12. class _MessagePageState extends State<MessagePage> {
  13. List<Map<String, dynamic>> messages = [];
  14. @override
  15. void initState() {
  16. super.initState();
  17. fetchMessages();
  18. }
  19. Future<void> fetchMessages() async {
  20. final response = await http.get(Uri.parse(
  21. 'https://example.com/doc/getMessages?user_type=doctor&function=messages&conversation_id=${widget.conversationId}&pid=$pid&tac=$tac&view_as=doctor',
  22. ));
  23. if (response.statusCode == 200) {
  24. final data = jsonDecode(response.body);
  25. if (data['success']) {
  26. final List<dynamic> messagesData = data['data']['messages'];
  27. messages = messagesData.map((message) => Map<String, dynamic>.from(message)).toList();
  28. }
  29. } else {
  30. throw Exception('Failed to load messages data');
  31. }
  32. setState(() {});
  33. }
  34. @override
  35. Widget build(BuildContext context) {
  36. return Scaffold(
  37. appBar: AppBar(
  38. title: Text('Message Page'),
  39. ),
  40. body: ListView.builder(
  41. itemCount: messages.length,
  42. itemBuilder: (context, index) {
  43. final message = messages[index];
  44. return ListTile(
  45. title: Text(message['sender_name']),
  46. subtitle: Text(message['message']),
  47. // You can customize how you want to display the message data here.
  48. // For example, you can format the sent_at date, display sender's type, etc.
  49. );
  50. },
  51. ),
  52. );
  53. }
  54. }
ecfsfe2w

ecfsfe2w1#

我看了你的代码,似乎你必须加深一点你的理解,你的cnrc/ sync函数。
你的小部件是同步构建的,而你的函数是异步的。这意味着您的Widget首先构建并尝试访问尚未获取的数据。
你需要做的是使用FutureBuilder。它们是在构建自身之前等待API响应的小部件。
如果你的Widget还没有获取数据,你可以显示一个loadingIndicator或者其他什么。
希望能帮到你,我说清楚了。
期待您的更新:)

相关问题