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

PHP/Curl上传文件至SharePoint失败:返回跳转但文件未找到

SharePoint文件上传失败问题分析与修复

问题描述

使用以下PHP代码尝试将本地HTML文件上传至SharePoint:

$the_file = file_get_contents("".realpath(dirname(__FILE__))."/<file_name>.htm");//Note: the file already exists in the dir

$ch = curl_init();

curl_setopt($ch, CURLOPT_HEADER, 0);
curl_setopt($ch, CURLOPT_VERBOSE, 0);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_HTTPHEADER, array("Content-type: multipart/form-data"));
curl_setopt($ch, CURLOPT_USERPWD, "<usr>:<pass>");
curl_setopt($ch, CURLOPT_USERAGENT, "Mozilla/5.0 (X11; Linux i686; rv:6.0) Gecko/20100101 Firefox/6.0Mozilla/4.0 (compatible;)");
curl_setopt($ch, CURLOPT_URL, "https://<xxxx>.sharepoint.com/sites/<xxx>/Shared%20Documents/Forms/AllItems.aspx");

curl_setopt($ch, CURLOPT_POST, true);

$post = array('file_contents' => "the_file");

curl_setopt($ch, CURLOPT_POSTFIELDS, $post);

$response = curl_exec($ch);

if(curl_errno($ch)) {
    echo json_encode('Error: ' . curl_error($ch));
}
else {
    echo ($response);
}
curl_close($ch);

执行后返回重定向响应:

<html><head><title>Object moved</title></head><body>
<h2>Object moved to <a href="https://<xxxx>.sharepoint.com/sites/<xxxx>/_layouts/15/Authenticate.aspx?Source=%2Fsites%2F<xxx>%2FShared%20Documents%2FForms%2FAllItems%2Easpx">here</a>.</h2>
</body></html>

且SharePoint对应位置未找到上传文件。

核心错误点

  • 目标URL错误:你请求的AllItems.aspx是文档库的前端浏览页面,不是文件上传的接口,SharePoint不支持通过该页面POST上传文件。
  • 认证方式失效:现代SharePoint Online已不再支持简单的用户名密码Basic认证,直接用CURLOPT_USERPWD会触发重定向到认证页面,导致上传请求未被授权。
  • POST数据错误:代码中'file_contents' => "the_file"是字符串而非变量$the_file,实际没有传递文件内容;且手动设置Content-type: multipart/form-data会干扰curl自动生成正确的请求边界,导致上传格式无效。

修复方案

方案1:使用SharePoint REST API上传(推荐)

REST API是SharePoint官方推荐的文件操作方式,需要先获取有效的OAuth 2.0访问令牌(可通过Azure AD应用注册获取)。以下是简化示例:

$siteUrl = "https://<xxxx>.sharepoint.com/sites/<xxx>";
$folderPath = "/Shared Documents";
$fileName = "<file_name>.htm";
$fileContent = file_get_contents(realpath(dirname(__FILE__)) . "/$fileName");

$uploadUrl = "$siteUrl/_api/web/getfolderbyserverrelativeurl('$folderPath')/files/add(overwrite=true,url='$fileName')";

$ch = curl_init($uploadUrl);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, "POST");
curl_setopt($ch, CURLOPT_HTTPHEADER, [
    "Authorization: Bearer YOUR_ACCESS_TOKEN",
    "Content-Type: text/html",
    "Content-Length: " . strlen($fileContent)
]);
curl_setopt($ch, CURLOPT_POSTFIELDS, $fileContent);

$response = curl_exec($ch);
if(curl_errno($ch)) {
    echo "Error: " . curl_error($ch);
} else {
    echo "上传成功";
}
curl_close($ch);

方案2:使用WebDAV协议上传

若环境支持,可通过WebDAV的PUT请求直接上传文件,需使用支持现代认证的方式(如App密码或OAuth令牌):

$filePath = realpath(dirname(__FILE__)) . "/<file_name>.htm";
$remoteUrl = "https://<xxxx>.sharepoint.com/sites/<xxx>/Shared%20Documents/<file_name>.htm";

$ch = curl_init($remoteUrl);
curl_setopt($ch, CURLOPT_PUT, true);
curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
// 若使用App密码,可保留CURLOPT_USERPWD;否则替换为Bearer令牌
curl_setopt($ch, CURLOPT_USERPWD, "<usr>:<app_password>");
curl_setopt($ch, CURLOPT_INFILE, fopen($filePath, 'r'));
curl_setopt($ch, CURLOPT_INFILESIZE, filesize($filePath));

$response = curl_exec($ch);
if(curl_errno($ch)) {
    echo "Error: " . curl_error($ch);
} else {
    echo "上传成功";
}
curl_close($ch);

关键注意事项

  • 现代SharePoint Online必须使用OAuth 2.0认证,需在Azure AD中注册应用并配置相应权限;经典站点可临时启用App密码,但不推荐长期使用。
  • 所有文件操作应使用官方提供的API或标准协议(REST、WebDAV、Graph API),避免直接调用前端页面URL。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.07 04:35:55