Flutter中使用Get请求+Bearer Token调用API展示数据及Token保存方案
解决Token保存与Laravel API调用问题
一、Token的保存(基于SharedPreferences)
- 先在
pubspec.yaml中添加依赖,执行flutter pub get:
dependencies: shared_preferences: ^2.2.2 # 可替换为最新版本
- 登录成功获取Token后,执行以下代码保存:
SharedPreferences prefs = await SharedPreferences.getInstance(); await prefs.setString('auth_token', 你的Token值);
二、修正后的product.dart代码
以下是调整后的完整代码,包含Token读取、API调用修正及UI优化:
import 'package:flutter/material.dart'; import 'package:http/http.dart' as http; import 'dart:convert'; import 'package:shared_preferences/shared_preferences.dart'; class PageSuccess extends StatefulWidget { @override State<PageSuccess> createState() => _PageSuccessState(); } class _PageSuccessState extends State<PageSuccess> { List<dynamic> data = []; Future<void> fetchProducts() async { // 读取保存的Token SharedPreferences prefs = await SharedPreferences.getInstance(); String? token = prefs.getString('auth_token'); if (token == null) { print('未找到Token,请重新登录'); return; } final response = await http.get( Uri.parse('http://10.0.2.2:8000/api/produk'), headers: { 'Content-Type': 'application/json', // Laravel API默认接收JSON格式 'Authorization': 'Bearer $token', // 携带Token验证身份 }, ); if (response.statusCode == 200) { setState(() { data = jsonDecode(response.body); // 直接解析响应体 }); print('产品数据获取成功'); } else { print('产品数据获取失败,状态码:${response.statusCode}'); print('错误详情:${response.body}'); } } @override void initState() { super.initState(); fetchProducts(); // 页面初始化时调用API } @override Widget build(BuildContext context) { return Scaffold( appBar: AppBar( centerTitle: true, title: const Text('Api Course'), ), body: Column( children: [ Expanded( child: data.isEmpty ? const Center(child: Text('加载中...')) : ListView.builder( itemCount: data.length, itemBuilder: (context, index) { return Card( child: Column( children: [ ReusableRow( title: 'kode', value: data[index]['kode'].toString(), ), ReusableRow( title: 'nama', value: data[index]['nama'].toString(), ), ReusableRow( title: 'keterangan', value: data[index]['keterangan'].toString(), ), ReusableRow( title: 'harga', value: data[index]['harga'].toString(), ), ], ), ); }, ), ) ], ), ); } } // 补充ReusableRow组件实现 class ReusableRow extends StatelessWidget { final String title; final String value; const ReusableRow({super.key, required this.title, required this.value}); @override Widget build(BuildContext context) { return Padding( padding: const EdgeInsets.symmetric(horizontal: 16, vertical: 8), child: Row( mainAxisAlignment: MainAxisAlignment.spaceBetween, children: [Text(title), Text(value)], ), ); } }
三、关键修正说明
- Token读取逻辑:不能在类成员变量中直接用
await,需在异步方法内部读取SharedPreferences。 - 请求头修正:将
Content-Type改为application/json,匹配Laravel API的默认解析格式。 - JSON解析优化:原代码中
json.encode(response.body)属于冗余操作,直接用jsonDecode(response.body)即可正确解析数据。 - 状态更新:通过
setState更新数据列表,确保UI能实时刷新。 - 空状态处理:初始化空列表,避免
ListView.builder因itemCount为null崩溃。
四、Postman验证步骤
在Postman中测试API时,添加请求头Authorization: Bearer 你的Token值,确认能正常返回产品数据后,再运行Flutter代码即可保证调用正常。
内容的提问来源于stack exchange,提问作者Raymond Pratama S
相关产品推荐
相关产品推荐

