【发布时间】:2017-02-09 10:39:11
【问题描述】:
我在DocumentDb 中遇到了一个奇怪的问题。
我创建了一个用户和权限来操作特定的集合。然后我为该用户请求了一个具有有限有效性的资源令牌。我通过将ResourceTokenExpirySeconds 设置为 10 秒来做到这一点。为了测试它,我等待了足够长的时间以使令牌过期。但是,Azure 使用该(假定已过期)令牌接受了后续请求。
考虑到以下代码,预计此行会失败,但事实并非如此:
UserPermissionExample.TestToken(10, 15);
这里是UserPermissionExample 的实现:
public class UserPermissionExample
{
const string endPoint = "https://[ENDPOINT].documents.azure.com";
const string masterKey = "[PRIMARY-KEY]";
const string dbName = "test-db";
const string testUserId = "test-user";
const string collName = "test-coll";
public static async Task TestToken(int validity, int wait)
{
// Get a time-bound token
string token = await GetToken(validity /*seconds*/);
// Wait enough so the token gets expired
Thread.Sleep(TimeSpan.FromSeconds(wait));
// Try to add a document with the expired token. It is expected to fail:
DocumentClient client = new DocumentClient(new Uri(endPoint), token);
await client.CreateDocumentAsync(
UriFactory.CreateDocumentCollectionUri(dbName, collName),
new { name = "A test document" });
}
static async Task<string> GetToken(int tokenValiditySeconds)
{
DocumentClient client = new DocumentClient(new Uri(endPoint), masterKey);
ResourceResponse<Database> db = await UpsertDb(client);
ResourceResponse<DocumentCollection> collection = await UpsertCollection(client, db);
var userUrl = UriFactory.CreateUserUri(dbName, "testuser");
var user = await client.UpsertUserAsync(db.Resource.SelfLink, new User() { Id = testUserId });
var permission =
await client.UpsertPermissionAsync(
user.Resource.SelfLink,
new Permission()
{
Id = "PersmissionForTestUser",
PermissionMode = PermissionMode.All,
ResourceLink = collection.Resource.SelfLink,
},
new RequestOptions() { ResourceTokenExpirySeconds = tokenValiditySeconds });
permission =
await client.ReadPermissionAsync(
permission.Resource.SelfLink,
new RequestOptions() { ResourceTokenExpirySeconds = tokenValiditySeconds });
return permission.Resource.Token;
}
static async Task<ResourceResponse<DocumentCollection>> UpsertCollection(DocumentClient client, ResourceResponse<Database> db)
{
ResourceResponse<DocumentCollection> collection = null;
try
{
collection = await client.ReadDocumentCollectionAsync(UriFactory.CreateDocumentCollectionUri(dbName, collName));
}
catch (DocumentClientException ex)
{
if (ex.StatusCode == System.Net.HttpStatusCode.NotFound)
{
collection = await client.CreateDocumentCollectionAsync(db.Resource.SelfLink, new DocumentCollection() { Id = collName });
}
}
return collection;
}
static async Task<ResourceResponse<Database>> UpsertDb(DocumentClient client)
{
ResourceResponse<Database> db = null;
try
{
db = await client.ReadDatabaseAsync(UriFactory.CreateDatabaseUri(dbName));
}
catch (DocumentClientException ex)
{
if (ex.StatusCode == System.Net.HttpStatusCode.NotFound)
{
db = await client.CreateDatabaseAsync(new Database() { Id = dbName });
}
}
return db;
}
}
PS:我使用的是 Microsoft.Azure.DocumentDB version="1.11.4"。
更新:我发现 Azure 在令牌发布时间后 5 分钟开始检查令牌过期时间!然后它拒绝令牌。所以在此之前,无论token是否过期,Azure都会接受!
【问题讨论】:
-
既然您发现了这个问题,请将其作为正确答案发布,而不是对您的问题进行编辑。这样,这个问题就可以正确地结束了。
-
@DavidMakogon 这不是答案。我仍然反对宽限期。
标签: azure azure-cosmosdb