You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Flutter项目:如何通过Microsoft Graph API上传会话传递二进制数据上传邮件附件

嘿,我来帮你解决Flutter里向Microsoft Graph上传二进制附件的问题!根据你提供的Graph API要求,咱们可以用Flutter常用的网络请求库来实现,直接传递二进制字节数组就行,下面给你详细的示例:

在Flutter中向Microsoft Graph上传二进制附件(大文件分段上传)

首先要明确核心:Graph API要求的二进制数据,在Flutter里可以通过读取文件的指定字节段,转换成Uint8List后直接作为请求体传递即可。下面分两种常用库来演示:

方法一:用官方http包实现

先确保你的pubspec.yaml里添加了http依赖:

dependencies:
  http: ^1.1.0

示例代码

import 'dart:io';
import 'package:http/http.dart' as http;

Future<void> uploadAttachmentSegment(String sessionUrl, File file, int startByte, int endByte, int totalFileSize) async {
  // 读取文件的指定字节段(注意endByte要+1,因为openRead的结束索引是开区间)
  final fileByteChunks = await file.openRead(startByte, endByte + 1).toList();
  final binaryData = Uint8List.fromList(fileByteChunks.expand((chunk) => chunk).toList());

  // 构造符合要求的请求头
  final requestHeaders = {
    'Content-Type': 'application/octet-stream',
    'Content-Length': binaryData.length.toString(),
    'Content-Range': 'bytes $startByte-$endByte/$totalFileSize',
  };

  // 发起PUT请求,直接把二进制数据作为body传入
  final response = await http.put(
    Uri.parse(sessionUrl),
    headers: requestHeaders,
    body: binaryData,
  );

  if (response.statusCode == 200 || response.statusCode == 201) {
    print('当前分段上传成功!');
  } else {
    print('上传失败,状态码:${response.statusCode},响应内容:${response.body}');
  }
}

// 调用示例:上传第一个2MB分段
void main() async {
  final targetFile = File('/your/file/path/attachment.pdf');
  final totalFileSize = await targetFile.length();
  const segmentStart = 0;
  const segmentEnd = 2097151; // 对应2MB的分段大小,符合Graph建议
  final uploadSessionUrl = 'https://outlook.office.com/api/beta/Users(\'a8e8e219-4931-95c1-b73d-62626fd79c32@72aa88bf-76f0-494f-91ab-2d7cd730db47\')/Messages(\'AAMkADI5MAAIT3drCAAA=\')/AttachmentSessions(\'AAMkADI5MAAIT3k0tAAA=\')?authtoken=eyJhbGciOiJSUzI1NiIsImtpZCI6IktmYUNIUlN6bllHMmNI';
  
  await uploadAttachmentSegment(uploadSessionUrl, targetFile, segmentStart, segmentEnd, totalFileSize);
}

方法二:用dio包实现(支持进度监听)

如果你的项目用dio(很多开发者偏好它的丰富功能),先添加依赖:

dependencies:
  dio: ^5.4.0+1

示例代码

import 'dart:io';
import 'package:dio/dio.dart';

Future<void> uploadAttachmentWithDio(String sessionUrl, File file, int startByte, int endByte, int totalFileSize) async {
  final dio = Dio();
  
  // 读取指定字节段的二进制数据
  final fileByteChunks = await file.openRead(startByte, endByte + 1).toList();
  final binaryData = Uint8List.fromList(fileByteChunks.expand((chunk) => chunk).toList());

  try {
    final response = await dio.put(
      sessionUrl,
      data: binaryData, // 直接传入二进制数据
      options: Options(
        headers: {
          'Content-Type': 'application/octet-stream',
          'Content-Length': binaryData.length.toString(),
          'Content-Range': 'bytes $startByte-$endByte/$totalFileSize',
        },
      ),
      onSendProgress: (sentBytes, totalBytesInSegment) {
        print('当前分段上传进度:${(sentBytes / totalBytesInSegment * 100).toStringAsFixed(2)}%');
      },
    );

    if (response.statusCode == 200 || response.statusCode == 201) {
      print('当前分段上传成功!');
    }
  } on DioException catch (e) {
    print('上传失败:${e.message},响应内容:${e.response?.data}');
  }
}

// 调用示例
void main() async {
  final targetFile = File('/your/file/path/attachment.pdf');
  final totalFileSize = await targetFile.length();
  const segmentStart = 0;
  const segmentEnd = 2097151;
  final uploadSessionUrl = 'https://outlook.office.com/api/beta/Users(\'a8e8e219-4931-95c1-b73d-62626fd79c32@72aa88bf-76f0-494f-91ab-2d7cd730db47\')/Messages(\'AAMkADI5MAAIT3drCAAA=\')/AttachmentSessions(\'AAMkADI5MAAIT3k0tAAA=\')?authtoken=eyJhbGciOiJSUzI1NiIsImtpZCI6IktmYUNIUlN6bllHMmNI';
  
  await uploadAttachmentWithDio(uploadSessionUrl, targetFile, segmentStart, segmentEnd, totalFileSize);
}

几个关键注意点

  • Content-Range格式:必须严格遵循bytes start-end/total的规则,start和end是当前分段的首尾字节索引(从0开始),total是文件的总字节数。
  • 分段大小:Microsoft Graph建议每个分段为2MB(2097152字节),避免因请求过大导致失败。
  • 权限与Token:确保你的authtoken有效,且拥有Mail.ReadWrite这类足够的权限。

内容的提问来源于stack exchange,提问作者Jigar

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.06 23:37:28