Flutter基于Gemini API开发基金顾问聊天机器人:读取XLSX文件失败求助
Flutter中使用Gemini API读取XLSX文件实现基金顾问聊天机器人
问题概述
我正在开发一款基于Flutter的基金顾问聊天机器人,希望通过Gemini API读取指定XLSX文件并基于文件内容生成回复。目前文本消息交互功能正常,但尝试实现文件读取时多次失败,且未找到Flutter相关的成熟解决方案(Python、JavaScript已有可用案例)。
现有文本交互代码
void _sendMessage() async { try { final messageText = _controller.text.trim(); if (messageText.isEmpty) return; _controller.clear(); setState(() { _messages.add(Message(text: messageText, isUser: true)); _isLoading = true; // Set loading state when sending message }); _scrollToBottom(); final model = GenerativeModel( model: 'gemini-pro', apiKey: 'API-KEY'); final content = [Content.text(messageText)]; final response = await model.generateContent(content); setState(() { _messages.add(Message(text: response.text!, isUser: false)); _isLoading = false; // Clear loading state after receiving response }); _scrollToBottom(); _controller.clear(); } catch (e) { log("Error : $e"); setState(() { _isLoading = false; // Ensure loading state is cleared on error }); } }
尝试的文件读取代码(未成功)
final geminiApi = GeminiApi('API-KEY'); const filePath = 'assets/data.xlsx'; const mimeType = 'application/vnd.google-apps.spreadsheet'; // Upload the file final fileResponse = await geminiApi.uploadFile(filePath, mimeType); final fileId = fileResponse['id']; // Wait for the file to be processed await geminiApi.waitForFileProcessing(fileId);
解决方案
核心问题分析
- 模型限制:你使用的
gemini-pro是纯文本模型,不支持文件处理,必须切换到多模态模型(如gemini-pro-vision)。 - Asset文件路径问题:Flutter打包的asset文件无法直接通过路径被外部API读取,需要先复制到本地临时目录。
- 第三方包可靠性:非官方
gemini_api包缺乏维护,建议使用官方google_generative_ai包。
具体实现步骤
1. 添加依赖
在pubspec.yaml中添加所需依赖:
dependencies: google_generative_ai: ^0.3.1 path_provider: ^2.1.2 flutter/services.dart
2. 编写Asset转本地文件工具函数
import 'dart:io'; import 'package:flutter/services.dart'; import 'package:path_provider/path_provider.dart'; Future<File> getLocalFileFromAsset(String assetPath) async { final byteData = await rootBundle.load(assetPath); final tempDir = await getTemporaryDirectory(); final file = File('${tempDir.path}/data.xlsx'); await file.writeAsBytes(byteData.buffer.asUint8List()); return file; }
3. 实现支持文件的消息发送方法
void _sendMessageWithFile() async { try { setState(() { _isLoading = true; }); // 获取本地可读取的XLSX文件 final localFile = await getLocalFileFromAsset('assets/data.xlsx'); // 初始化支持多模态的模型 final model = GenerativeModel( model: 'gemini-pro-vision', apiKey: 'YOUR_API_KEY', ); // 构建包含文件和提问文本的请求内容 final content = [ Content.multi([ TextPart('请基于这份基金数据回答我的问题:${_controller.text.trim()}'), FilePart( name: 'data.xlsx', mimeType: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet', file: localFile, ), ]) ]; // 调用API生成回复 final response = await model.generateContent(content); setState(() { _messages.add(Message(text: _controller.text.trim(), isUser: true)); _messages.add(Message(text: response.text!, isUser: false)); _isLoading = false; }); _controller.clear(); _scrollToBottom(); } catch (e) { log("Error: $e"); setState(() { _isLoading = false; }); } }
关键注意事项
- 模型选择:必须使用
gemini-pro-vision等支持多模态的模型,gemini-pro仅处理纯文本。 - MIME类型:XLSX的正确MIME类型是
application/vnd.openxmlformats-officedocument.spreadsheetml.sheet,不要使用Google Sheets的类型。 - 文件处理:Asset文件必须复制到临时目录,否则API无法读取到文件内容。
内容的提问来源于stack exchange,提问作者Mert Miraç Arık
相关产品推荐
相关产品推荐

