Azure Blob 放置命令在以前工作时生成错误
本文关键字:工作 错误 Blob 命令 Azure | 更新日期: 2023-09-27 18:30:00
我正在通过我创建的 C# API 将文件从 Cordova 上传到 Azure Blob 存储。最近,上传停止工作。我一直在进行更改,所以我恢复了更改,但问题仍然存在。我已经尽我所能调试了该过程,但我似乎卡住了。
过程
当我想上传文件时,将执行以下步骤:
- 有关文件的数据将上传到 Azure SQL。在插入过程中,将生成并返回 SAS 密钥。
- 该文件通过 JavaScript 上传到 C# Web API,SAS 密钥随之发送。 Web
- API 在本地存储文件,然后使用 SAS 密钥调用 WebClient.UploadFile 方法进行身份验证。
- Web API 应返回 200。
错误
该过程的第一部分运行良好。我正确地生成了一个 sas 密钥(有五分钟的窗口 - 我已将其扩展到 15 但没有成功(,并且将文件上传到 C# Web API 的 JavaScript 进展顺利(我在代码中放置了一个断点并验证了所有内容(。当我调用WebClient.UploadFile方法时会出现此问题。它曾经可以毫无问题地工作。现在我收到 403 错误。错误的状态属性显示协议错误。当我在 Fiddler 中运行它时,我得到的响应是:
服务器无法对请求进行身份验证。确保值授权标头的格式正确,包括签名。
签名字段格式不正确。
请求
下面是对我的 Azure 存储帐户的 PUT 调用的原始视图(为保护无辜者而更改了名称(:
放
https://myappname.blob.core.windows.net/myapp/792b6b3c-d8df-4100-f9be-bbd69be7f307.jpg?se=2014-11-11T19%253A32%253A33Z&sr=b&sp=w&sig=Lk5SiEEaGUwyOjxjUGkIjink26Gwe7VpXMBPw975ZrM%253D
HTTP/1.1 x-ms-blob-type: BlockBlob x-ms-date: 星期二, 11 Nov 2014
19:17:24 GMT x-ms版本: 2012-02-12 内容类型:
应用程序/八位字节流主机:myappname.blob.core.windows.net
内容长度:74784 预期:100 续
这是我生成的 SAS 密钥:
se=2014-11-11T19%3A32%3A33Z&sr=b&sp=w&sig=Lk5SiEEaGUwyOjxjUGkIjink26Gwe7VpXMBPw975ZrM%3D
《守则》
这是我的 C# 代码:
var client = new WebClient();
client.Headers.Add("x-ms-blob-type", "BlockBlob");
client.Headers.Add("x-ms-date", DateTime.UtcNow.ToString("R",
System.Globalization.CultureInfo.InvariantCulture));
client.Headers.Add("x-ms-version", "2012-02-12");
sas = Request.RequestUri.Query.Substring(Request.RequestUri.Query.IndexOf("sas=") + 4);
startIndex = Request.RequestUri.Query.IndexOf("name=") + 5;
endIndex = Request.RequestUri.Query.IndexOf("&", startIndex);
fileName = Request.RequestUri.Query.Substring(startIndex, endIndex - startIndex);
client.UploadFile(string.Format(@"{0}/{1}?{2}", endpoint, fileName, sas), "PUT", file.LocalFileName);
这是我的JavaScript代码,它通过移动服务在对SQL Azure表的插入调用上运行:
var azure = require('azure');
var qs = require('querystring');
var appSettings = require('mobileservice-config').appSettings;
function insert(item, user, request) {
// Get storage account settings from app settings.
var accountName = appSettings.STORAGE_ACCOUNT_NAME;
var accountKey = appSettings.STORAGE_ACCOUNT_ACCESS_KEY;
var host = accountName + '.blob.core.windows.net';
if ((typeof item.containerName !== "undefined") && (
item.containerName !== null)) {
// Set the BLOB store container name on the item, which must be lowercase.
item.containerName = item.containerName.toLowerCase();
// If it does not already exist, create the container
// with public read access for blobs.
var blobService = azure.createBlobService(accountName, accountKey, host);
blobService.createContainerIfNotExists(item.containerName, {
publicAccessLevel: 'blob'
}, function(error) {
if (!error) {
// Provide write access to the container for the next 5 mins.
var sharedAccessPolicy = {
AccessPolicy: {
Permissions: azure.Constants.BlobConstants.SharedAccessPermissions.WRITE,
Expiry: new Date(new Date().getTime() + 5 * 60 * 1000)
}
};
// Generate the upload URL with SAS for the new image.
var sasQueryUrl =
blobService.generateSharedAccessSignature(item.containerName,
item.resourceName, sharedAccessPolicy);
// Set the query string.
item.sasQueryString = qs.stringify(sasQueryUrl.queryString);
// Set the full path on the new new item,
// which is used for data binding on the client.
item.imagePath = sasQueryUrl.baseUrl + sasQueryUrl.path;
} else {
console.error(error);
}
request.execute();
});
} else {
request.execute();
}
}
就像我说的,在C#/Azure方面,我的知识没有任何变化。我一直在 Cordova 端玩文件上传,但由于文件成功进入 C# Web API,我看不出这将如何成为一个问题。
我的 Azure 存储日志中出现错误,但我不确定这是否真的是一个错误。我收到的错误是创建容器操作上的 409。该消息是 ClientOtherError。我不确定这是否相关的原因是因为createContainerIfNotExist方法。我不确定如果容器已经存在,这是否会产生错误(似乎不应该,但你永远不知道(。
我在您的请求 URL 中注意到的一件事是%
符号被编码为不应该发生的%25
。您的请求 URL 应以 %3D
结尾,这是 =
的 URL 编码。
看起来您缺少身份验证标头。请参阅文档:
授权 - 必需。指定身份验证方案、帐户 姓名和签名。有关详细信息,请参阅身份验证 Azure Storage Services。
有关如何设置此标头的详细信息,请参阅此处
编辑:错误,如评论中指出的那样 - "经过身份验证的请求必须包含授权标头。如果未包含此标头,则请求是匿名的,并且只能针对标记为公共访问的容器或 Blob,或者针对已为其提供共享访问签名以进行委派访问的容器、Blob、队列或表成功。