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

使用Microsoft Graph C# ASP.NET向OneDrive上传新文件问题

解决OneDrive全新文件上传问题

你现在能更新现有文件但没法创建新文件,核心原因是更新和创建文件的API调用逻辑虽然相似,但需要确保目标路径指向的文件不存在,并且权限和调用方式要匹配。我结合Microsoft.Graph类库的用法,给你两种场景的解决方案:

一、小文件直接上传(小于4MB)

对于小文件,直接用PutAsync方法即可——只要你指定的OneDrive路径下没有同名文件,Graph API就会自动创建新文件;如果文件已存在,就会覆盖(也就是你之前的更新逻辑)。

这里是完整的示例代码:

public async Task<ActionResult> OneDriveUploadNewFile()
{
    string token = await GetAccessToken();
    if (string.IsNullOrEmpty(token))
    {
        return Redirect("/");
    }

    // 初始化Graph客户端
    var graphClient = new GraphServiceClient(
        new DelegateAuthenticationProvider((requestMessage) =>
        {
            requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", token);
            return Task.FromResult(0);
        }));

    // 本地文件路径(替换成你要上传的文件)
    string localFilePath = @"C:\Users\YourName\Desktop\NewDocument.pdf";
    // OneDrive目标路径:确保这个路径下没有同名文件
    string oneDriveTargetPath = "/Documents/我的新文档.pdf";

    try
    {
        using (var fileStream = new FileStream(localFilePath, FileMode.Open))
        {
            // 上传并创建新文件
            var uploadedFile = await graphClient.Me.Drive.Root.ItemWithPath(oneDriveTargetPath)
                .Content
                .PutAsync<DriveItem>(fileStream);

            return Ok($"新文件创建成功!文件ID:{uploadedFile.Id}");
        }
    }
    catch (ServiceException ex)
    {
        // 捕获Graph API的具体错误,方便排查
        return BadRequest($"上传失败:{ex.Message},错误代码:{ex.Error.Code}");
    }
}

二、大文件分块上传(大于4MB)

如果文件超过4MB,必须用上传会话的方式分块上传,否则会报错。这种方式同样支持创建新文件:

public async Task<ActionResult> OneDriveUploadLargeFile()
{
    string token = await GetAccessToken();
    if (string.IsNullOrEmpty(token))
    {
        return Redirect("/");
    }

    var graphClient = new GraphServiceClient(
        new DelegateAuthenticationProvider((requestMessage) =>
        {
            requestMessage.Headers.Authorization = new AuthenticationHeaderValue("Bearer", token);
            return Task.FromResult(0);
        }));

    string localFilePath = @"C:\Users\YourName\Desktop\LargeArchive.zip";
    string oneDriveTargetPath = "/Documents/我的大压缩包.zip";
    long fileSize = new FileInfo(localFilePath).Length;

    try
    {
        // 创建上传会话
        var uploadSession = await graphClient.Me.Drive.Root.ItemWithPath(oneDriveTargetPath)
            .CreateUploadSession()
            .Request()
            .PostAsync();

        // 初始化分块上传任务
        var fileStream = new FileStream(localFilePath, FileMode.Open);
        var uploadTask = new LargeFileUploadTask<DriveItem>(uploadSession, fileStream);

        // 可选:监听上传进度
        uploadTask.UploadProgress += (sender, args) =>
        {
            Console.WriteLine($"当前上传进度:{args.Progress}%");
        };

        // 执行上传
        var uploadResult = await uploadTask.UploadAsync();

        if (uploadResult.UploadSucceeded)
        {
            return Ok($"大文件创建成功!文件ID:{uploadResult.ItemResponse.Id}");
        }
        else
        {
            return BadRequest("大文件上传失败,请检查后重试");
        }
    }
    catch (ServiceException ex)
    {
        return BadRequest($"上传失败:{ex.Message},错误代码:{ex.Error.Code}");
    }
}

关键排查点

如果还是没法创建文件,你可以从这几个方向检查:

  • 权限问题:确保你的应用已申请Files.ReadWrite(委托权限)或Files.ReadWrite.All(应用权限),并且完成了授权流程
  • 路径问题:确认目标路径的父文件夹存在(比如/Documents必须是OneDrive中已有的文件夹),如果父文件夹不存在,需要先调用API创建文件夹
  • 错误信息:捕获ServiceException后,查看ex.Error.Code和ex.Message,比如403是权限不足,404是父路径不存在,409是文件已存在(但你要创建新文件的话,这个情况应该避免)
  • OneDrive类型:如果是商业/教育版的团队站点文档库,需要把graphClient.Me.Drive换成graphClient.Sites["你的站点ID"].Drive

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.25 03:39:20