使用嵌入模式调用InvalidOperationException
时,RavenDB会抛出IsOperationAllowedOnDocument
。
我可以在IsOperationAllowedOnDocument
实现中看到一个子句检查嵌入模式下的调用。
namespace Raven.Client.Authorization
{
public static class AuthorizationClientExtensions
{
public static OperationAllowedResult[] IsOperationAllowedOnDocument(this ISyncAdvancedSessionOperation session, string userId, string operation, params string[] documentIds)
{
var serverClient = session.DatabaseCommands as ServerClient;
if (serverClient == null)
throw new InvalidOperationException("Cannot get whatever operation is allowed on document in embedded mode.");
除了不使用嵌入模式之外,还有其他解决方法吗?
感谢您的时间。
答案 0 :(得分:4)
我在编写一些单元测试时遇到了同样的情况。詹姆斯提供的解决方案有效但是,它导致了单元测试的一个代码路径和生产代码的另一个路径,这违背了单元测试的目的。我们能够创建第二个文档存储并将其连接到第一个文档存储,这使我们可以成功访问授权扩展方法。虽然这个解决方案可能不适合生产代码(因为创建文档存储很昂贵),但它可以很好地用于单元测试。这是一个代码示例:
using (var documentStore = new EmbeddableDocumentStore
{ RunInMemory = true,
UseEmbeddedHttpServer = true,
Configuration = {Port = EmbeddedModePort} })
{
documentStore.Initialize();
var url = documentStore.Configuration.ServerUrl;
using (var docStoreHttp = new DocumentStore {Url = url})
{
docStoreHttp.Initialize();
using (var session = docStoreHttp.OpenSession())
{
// now you can run code like:
// session.GetAuthorizationFor(),
// session.SetAuthorizationFor(),
// session.Advanced.IsOperationAllowedOnDocument(),
// etc...
}
}
}
还应提及其他几项:
答案 1 :(得分:3)
我也遇到过这个。看看源代码,没有办法像写的那样进行操作。不确定是否有一些内在的原因,因为我可以通过直接为相同的信息发出http请求轻松复制我的应用程序中的功能:
HttpClient http = new HttpClient();
http.BaseAddress = new Uri("http://localhost:8080");
var url = new StringBuilder("/authorization/IsAllowed/")
.Append(Uri.EscapeUriString(userid))
.Append("?operation=")
.Append(Uri.EscapeUriString(operation)
.Append("&id=").Append(Uri.EscapeUriString(entityid));
http.GetStringAsync(url.ToString()).ContinueWith((response) =>
{
var results = _session.Advanced.DocumentStore.Conventions.CreateSerializer()
.Deserialize<OperationAllowedResult[]>(
new RavenJTokenReader(RavenJToken.Parse(response.Result)));
}).Wait();