情景/背景
我的申请是一项调查申请。每个Survey
都有一个Questions
数组;相反,每个Submission
(个人对调查的回答)都有一个Answers
数组。
我有一个静态索引,汇总所有答案,以便我可以根据答案显示图表(例如,每个调查的每个问题,每个选项选择了多少人)。这些数据用于渲染例如饼图。这个聚合索引(在this question中讨论)基本上为每个调查提供一个问题对象,每个选项都有总和。
问题
我想过滤这些汇总值。其中一些是微不足道的,因为它们是结果中的字段(例如,按SurveyId
或QuestionId
过滤)。但是,我还希望按提交日期(来自元数据)或LocationId
过滤,这些是Submissions
中的字段,但显然不在汇总结果中。
换句话说,我需要能够向Raven询问有关特定LocationId
或本月的问题的结果。
类
以下是单个提交的基本外观:
{
"SurveyId": 1,
"LocationId": 1,
"Answers": [
{
"QuestionId": 1,
"Values": [2,8,32],
"Comment": null
},
{
"QuestionId": 2,
"Values": [4],
"Comment": "Lorem ipsum"
},
...more answers...
]
}
目前,这是聚合结果:
public class Result
{
public int SurveyId { get; set; } // 1
public int QuestionId { get; set; } // 1
public int NumResponses { get; set; } // 576
public int NumComments { get; set; } // 265
public IList<KeyValuePair<int,int>> Values { get; set; } // [{Key:1, Value:264}, {Key:2, Value:163}, Key:4, Value:391}, ...]
}
这是聚合索引:
Map = submissions =>
from submission in submissions
from answer in submission.Answers
select new
{
submission.SurveyId,
answer.QuestionId,
NumResponses = 1,
NumComments = answer.Comment == null ? 0 : 1,
Value = answer.Value.Select(x => new KeyValuePair<int, int>(x, 1))
};
Reduce = results =>
from result in results
group result by new { result.SurveyId, result.QuestionId }
into g
select new Result
{
SurveyId = g.Key.SurveyId,
QuestionId = g.Key.QuestionId,
NumResponses = g.Sum(x => x.NumResponses),
NumComments = g.Sum(x => x.NumComments),
Value = g.SelectMany(x => x.Value)
.GroupBy(x => x.Key)
.Select(x => new KeyValuePair<int, int>(x.Key, x.Sum(y => y.Value)))
};
从概念上讲,我倾向于将这些过滤器“传递”到查询中,但从我所读到的内容来看,这是行不通的,因为索引值是异步索引(存储)而没有单独的提交日期或LocationIds
这是否意味着我需要创建所有答案的索引,然后让聚合索引查询这个新的AllAnswers索引,或者什么?我已经做了一点点搜索另一个索引查询,没有运气。或者这是字段用于什么?
感谢任何指导!
答案 0 :(得分:4)
您目前使用SurveyId
和QuestionId
汇总所有数据的索引。如果您希望按日期或位置进行分类,则这些是新索引。您只需将您想要的字段添加到地图中,将它们包含在分组键中,然后在结果中传递它们。然后,您可以轻松地通过这些键进行查询。
如果有不同的分组键,则无法将其合并为单个索引。您必须有多个索引。例如,我可能会调用您Submission_TotalsBySurveyAndQuestion
以上的索引,而另一个索引可能是Submission_TotalsBySurveyAndQuestionPerLocation
。
以这种方式思考 - 现在,您可以在查询中添加Where
或OrderBy
,与SurveyId
或QuestionId
相对 - 因为这些是分组索引中的键。如果您想按LocationId
进行过滤或排序,则必须包含该内容。
一句谨慎,你说:
我还希望按提交日期(来自元数据)进行过滤
RavenDB在元数据中(默认情况下)为您提供的唯一日期是Last-Modified
日期。对文档的任何编辑都将更新此内容。因此,如果提交日期对您很重要,那么您应该将其保存在您自己的财产中。