RavenDB中作为Id的Guid
各国: 支持数字或Guid Id属性,它们可以无缝工作。在这种情况下,RavenDB将自动将内部字符串ID转换为实体中显示的数字或Guid值,然后返回 我存储了以下对象:RavenDB中作为Id的Guid,ravendb,Ravendb,各国: 支持数字或Guid Id属性,它们可以无缝工作。在这种情况下,RavenDB将自动将内部字符串ID转换为实体中显示的数字或Guid值,然后返回 我存储了以下对象: class A { public Guid Id { get; set; } public Guid BId { get; set; } } class B { public Guid Id { get; set; } public string Name { get; set; } } 然
class A
{
public Guid Id { get; set; }
public Guid BId { get; set; }
}
class B
{
public Guid Id { get; set; }
public string Name { get; set; }
}
然后,我创建了以下投影:
class AB
{
public Guid Id { get; set; } // This should be the Id of A
public Guid BId { get; set; } // This should be the Id of B
public string BName { get; set; } // This should be the name of B
}
class MyIndex : AbstractIndexCreationTask<AB>
{
public MyIndex()
{
Map = docs =>
from d in docs
select new
{
d.Id,
d.BId,
BName = string.Empty
};
TransformResults = (database, results) =>
from r in results
let b = database.Load<B>("bs/" + r.BId.ToString())
select new
{
r.Id,
r.BId,
BName = b.Name
};
}
}
我创建了以下索引以创建投影:
class AB
{
public Guid Id { get; set; } // This should be the Id of A
public Guid BId { get; set; } // This should be the Id of B
public string BName { get; set; } // This should be the name of B
}
class MyIndex : AbstractIndexCreationTask<AB>
{
public MyIndex()
{
Map = docs =>
from d in docs
select new
{
d.Id,
d.BId,
BName = string.Empty
};
TransformResults = (database, results) =>
from r in results
let b = database.Load<B>("bs/" + r.BId.ToString())
select new
{
r.Id,
r.BId,
BName = b.Name
};
}
}
类MyIndex:AbstractIndexCreationTask
{
公共索引()
{
Map=docs=>
从文档中的d开始
选择新的
{
d、 身份证,
d、 投标,
BName=string.Empty
};
TransformResults=(数据库、结果)=>
从r到结果
设b=database.Load(“bs/”+r.BId.ToString())
选择新的
{
r、 身份证,
r、 投标,
BName=b.名称
};
}
}
当我使用以下查询时:
session.Query<AB, MyIndex>().FirstOrDefault(t => t.Id == guid);
session.Query().FirstOrDefault(t=>t.Id==guid);
我得到一个例外:
将值“bs/cc0a65ae-dd36-4437-8a57-fa20b91eeef7”转换为类型“System.Guid”时出错。路径“Id”
问题:
Id
是一个字符串,不再是我的Guid。但是,省略它不会返回Id。我必须做什么“bs/”+r.BId.ToString()
来加载相关文档。有没有办法不必这样做?是否有某种函数可以为我解析doc标签Id
属性
我正在使用Raven.Client 1.0.972您可以在保存时向RavenDB显式提供ID:
session.Store(doc, explicitIdValueString);
explicitIdValueString
可以是Guid字符串。此值将用于标识整个数据库中的文档,并且不会以类型标记名作为前缀。您还可以通过覆盖IDocumentStore.conventions
上的约定(如FindTypeTagName
是Func
)来定制标记名或ID生成策略,主要问题是RavenDB可以在客户端处理数字/整数,但在服务器端,RavenDB使用字符串ID
通常,不建议使用GUID/数字ID 您可以使用MultiMap/Reduce索引来实现这一点,但您需要一些技巧: 1) 您需要减少使用字符串,而不是guid。您仍然可以在AB类中以GUI的形式获取这些值,我将在下面演示 2) 您不能调用AB类的第一个属性“Id”,因为raven将尝试将其转换为“文档Id”。所以称它为“援助”,它会很好地工作 3) 在映射阶段,您必须自己操作字符串以去除文档键前缀 下面是一个示例程序,它将所有内容放在一起。这表明它确实有效,但我认为它也说明了为什么Ayende更喜欢字符串标识符,这样就不必处理这种混乱
使用系统;
使用System.Linq;
使用Raven.Client.Document;
使用Raven.Client.index;
名称空间ravenscartest
{
班级计划
{
静态void Main()
{
var documentStore=new documentStore{Url=”http://localhost:8080" };
初始化();
CreateIndexes(typeof(Program).Assembly,documentStore);
使用(var session=documentStore.OpenSession())
{
var b=new b{Id=Guid.NewGuid(),Name=“Foo”};
var a=newa{Id=Guid.NewGuid(),BId=b.Id};
会议.商店(a);
会议.商店(b);
session.SaveChanges();
}
使用(var session=documentStore.OpenSession())
{
var a=session.Query().Customize(x=>x.WaitForNonSaleResults()).First();
var b=session.Query().Customize(x=>x.WaitForNonSaleResults()).First();
WriteLine(“A:Id={0}”,A.Id);
WriteLine(“BId={0}”,a.BId);
Console.WriteLine();
WriteLine(“B:Id={0}”,B.Id);
WriteLine(“Name={0}”,b.Name);
Console.WriteLine();
var guid=a.Id;
var ab=session.Query().Customize(x=>x.WaitForNonSaleResults())
.FirstOrDefault(t=>t.AId==guid);
if(ab==null)
控制台写入线(“AB:NULL”);
其他的
{
WriteLine(“AB:AId={0}”,AB.AId);
Console.WriteLine(“BId={0}”,ab.BId);
WriteLine(“BName={0}”,ab.BName);
Console.WriteLine();
}
}
Console.WriteLine();
控制台。WriteLine(“完成”);
Console.ReadLine();
}
}
甲级
{
公共Guid Id{get;set;}
公共Guid BId{get;set;}
}
B类
{
公共Guid Id{get;set;}
公共字符串名称{get;set;}
}
AB类
{
公共Guid辅助{get;set;}
公共Guid BId{get;set;}
公共字符串BName{get;set;}
}
类MyIndex:AbstractMultiMapIndexCreationTask
{
公共索引()
{
AddMap(文档=>来自文档中的
选择新的
{
AId=a.Id.ToString().Split('/')[1],
a、 投标,
BName=(字符串)null
});
AddMap(文档=>来自文档中的b
选择新的
{
AId=(字符串)null,
BId=b.Id.ToString().Split('/')[1],
BName=b.名称
});
还原
public class User
{
public User(Guid? guid = null)
{
IdPart = (guid ?? Guid.NewGuid()).ToString("N")
}
string IdPart { get; }
string Id => $"Users/{IdPart}"
public class Project
{
public User(Guid? userId = null)
{
UserId = "Users/" + (guid ?? Guid.NewGuid()).ToString("N");
Id = $"{UserId}/project/"
}