2012-10-11 89 views
5

RavenDB arroja InvalidOperationException cuando se llama IsOperationAllowedOnDocument utilizando el modo incrustado.RavenDB IsOperationAllowedOnDocument no admitido en modo incrustado

Puedo ver en la implementación IsOperationAllowedOnDocument una cláusula que comprueba las llamadas en modo incrustado.

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."); 

¿Existe una solución para esto que no sea el uso del modo incrustado?

Gracias por su tiempo.

Respuesta

4

me encontré la misma situación al escribir algunas pruebas unitarias. La solución que James proporcionó funcionó; sin embargo, resultó en tener una ruta de código para la prueba de la unidad y otra ruta para el código de producción, que derrotó el propósito de la prueba de la unidad. Pudimos crear una segunda tienda de documentos y conectarla a la primera tienda de documentos, lo que nos permitió acceder a los métodos de extensión de autorización con éxito. Si bien esta solución probablemente no sea buena para el código de producción (porque la creación de Almacenes de documentos es costosa) funciona muy bien para las pruebas unitarias. Aquí está un ejemplo de código:

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... 
     } 
    } 
} 

Hay par de otros elementos que debe mencionarse:

  1. El primer almacén de documentos necesita ser ejecutado con el UseEmbeddedHttpServer establecido en true para que el segundo puede acceder a él.
  2. Creé una constante para el puerto, por lo que se usaría de forma coherente y garantizaría el uso de un puerto no reservado.
3

Me encontré con esto también. Al mirar la fuente, no hay forma de hacer esa operación como está escrito. No estoy seguro si hay alguna razón intrínseca por la que ya podría fácilmente replicar la funcionalidad en mi aplicación al hacer una petición HTTP directamente para la misma información:

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(); 
Cuestiones relacionadas