Azure cosmosdb 使用REST调用的Cosmosdb资源令牌授权标头

Azure cosmosdb 使用REST调用的Cosmosdb资源令牌授权标头,azure-cosmosdb,Azure Cosmosdb,Cosmosdb的概念是为用户提供权限。该权限包含一个令牌,可用于在有限的访问时间内访问指定的分区 我已经创建了一个资源令牌代理,它创建权限,检索令牌并将其返回给客户端Xamarin Forms应用程序。到目前为止还不错 如果我使用的是.NETSDK中的DocumentClient,那么该令牌(未经修改)工作得非常好 然而,我希望避免在我的应用程序中依赖于DocumentClient,而是直接向Cosmosdb调用RESTAPI 如果我将该标记放在授权标头中,则会得到该标头的格式错误。我找不到S

Cosmosdb的概念是为
用户
提供
权限
。该权限包含一个
令牌
,可用于在有限的访问时间内访问指定的分区

我已经创建了一个资源令牌代理,它创建权限,检索令牌并将其返回给客户端Xamarin Forms应用程序。到目前为止还不错

如果我使用的是
.NET
SDK中的
DocumentClient
,那么该令牌(未经修改)工作得非常好

然而,我希望避免在我的应用程序中依赖于
DocumentClient
,而是直接向Cosmosdb调用RESTAPI

如果我将该
标记
放在授权标头中,则会得到该标头的格式错误。我找不到SDK的源代码,所有示例都是通过修改主令牌构建的

有人能解释/指出/举例说明我必须如何处理从
权限获得的
资源令牌
,使其成为一个可接受的头,以便我可以进行REST调用吗


TIA

根据您的描述,我认为您已经知道如何获取资源令牌。除了资源令牌格式之外,您的所有作业都很好。你需要使用你的资源令牌,然后你的代码就可以了。我成功地测试了它

var databaseId = "db";
var collectionId = "coll";
var datetime = DateTime.UtcNow.ToString("R");
var version = "2017-02-22";
var resourceId = $"dbs/{databaseId}/colls/{collectionId}";
var auth = "type%3Dresource%26ver%3D1%26sig%3Dny%2BUlL6QIWR69OfiaSjTsw%3D%3D%3B%2Ba%2FwmK37zLn%2FoilfztnXpfyCN3n9tChunmpBdROF8BH4**********************oU0BJ4z8aDZT%2F%2FgTVJ0hgpXTK8UYMOrL5di3he9wbvQwFkFOdpXD7%2B%2Byhmb1uUOnq%2Fyp454O2fQKR8uA3KaiLCCjYZ6qr%2BQ%2BTV1Cu1u%2F6Yj34nc4UYtpRBX5K************qCGjhvpQ%3D%3D%3B";

var urlPath = $"https://***.documents.azure.com/dbs/db/colls/coll/docs/1";
Uri uri = new Uri(urlPath);
HttpRequestMessage request = new HttpRequestMessage(HttpMethod.Get, uri);
HttpClient client = new HttpClient();

client.DefaultRequestHeaders.Add("x-ms-date", datetime);
client.DefaultRequestHeaders.Add("x-ms-version", version);   
client.DefaultRequestHeaders.Add("Authorization", auth);
HttpResponseMessage response = client.SendAsync(request).Result;
var status = response.IsSuccessStatusCode;
var message = response.RequestMessage;

杰伊的解决方案是正确的。我遗漏了几个部分。此条目适用于任何面临同样情况的可怜魔鬼

  • 正如Jay指出的,permission对象中实际从Cosmosdb返回的令牌没有编码。从.NETCore2.x开始,您需要使用
    WebUtility.UrlEncode(token)
    以获得正确的格式。我花了一个小时使用
    HtmlEncode
    而不是
    UrlEncode
    。我是个白痴
  • {更新:我甚至比原来想象的还要笨。你必须使用
    HttpUtility.UrlEncode
    ,而不是
    WebUtility.UrlEncode
    。这是因为它们的编码不同。
    WebUtility
    最终会得到
    %3D
    之类的东西,而
    HttpUtility
    会对其进行编码
    %3D
    。这并不重要除了身份验证令牌。当我在DocumentClient调用上运行Fiddler时,我注意到令牌包含小写的编码值。}因此忽略上面的#1,改用
    HttpUtility

  • 我在最初的问题中提到我在使用分区,但Jay的回答没有涵盖这一点,因此我仍然失败。我指定了一个分区键,但从文档中不清楚这是
    分区键
    路径还是
    分区键
    值如果您认为权限令牌在创建时将包含权限密钥。无法知道封底下发生了什么。尝试和错误。我个人的最爱
  • 但不太明显的问题是分区键的格式。如果要将权限限制在某个分区,则需要在标头中指定该分区,如下所示:

    string json = JsonConvert.SerializeObject(new[] { "b39bcd43-8d3d-*********-4e4492fa3e7d" });
    
    client.DefaultRequestHeaders.Add(“x-ms-documentdb-partitionkey”,partitions);

  • 您需要将
    分区
    变量格式化如下:

    string json = JsonConvert.SerializeObject(new[] { "b39bcd43-8d3d-*********-4e4492fa3e7d" });
    
  • 这是因为Cosmodb需要分区键的
    数组
    ,即使它只接受列表中的分区键(据我所知)。如果您不想使用
    JsonConvert
    ,可以使用
    $”[\“{yourPartitionKey}\\]”手动构建它


    毕竟它像桃子一样有效。再次感谢你,杰!

    我将此标记为答案,因为没有人真的愿意尝试这一点,所以你,杰,为了这一点。不过,我将尝试在答案中添加更多的事实。我的答案似乎很不完美。非常感谢你的分享!不,伙计,太好了。我是真的我挣扎着说这是可能的,错误代码根本没有帮助。你向我证明了这是可以做到的,这就是打破僵局的原因。