Plone为您提供filtering search results using a date range的可能性。仅使用最小日期设置正常日期范围,因此范围介于今天和过去的某个日期之间。
我需要添加设置包含开始日期和结束日期的日期范围的选项。
我正在考虑添加一个额外的选项,选中后会显示几个日期选择器,但我不知道如何设置created.query:record:list:date
变量来使用这两个值。
我试过在query
变量上传递一个列表,但后来我得到了:
Error Value: Invalid DateTime "[DateTime('2000/07/14 00:00:00 GMT-3'), DateTime('2014/07/14 00:00:00 GMT-3')]"
还有其他人之前发现了这样的要求吗?你是怎么解决的?这应该移植到核心吗?
答案 0 :(得分:2)
您可能希望使用范围参数传递索引名称的查询字典。假设您的索引已经“修改”,并且您想要一个最小值和最大值的范围,例如:
>>> from DateTime import DateTime
>>> from Products.CMFCore.utils import getToolByName
>>> catalog = getToolByName(site)
>>> startDT = DateTime(2010,12,1)
>>> endDT = DateTime(2013,12,1)
>>> query = {
... 'modified': {
... query: (startDT, endDT),
... range: 'min:max',
... }
... }
...
>>> result = catalog.unrestrictedSearchResults(query) # or .search()
此处记录了类似的内容:http://docs.plone.org/develop/plone/searching_and_indexing/query.html#querying-by-date
答案 1 :(得分:1)
我花了一些时间研究这个,我有一个有效的解决方案。
首先我们需要了解Zope和ZPT是如何工作的;当您使用created.query:record:list:date
之类的名称命名表单元素时,您告诉Zope进行一些参数转换:
有关详细信息,请查看Advanced Zope Scripting。
因此,该参数随后会自动转换为Python中的字典记录:
'created': {'query': [DateTime('2014/07/09 00:00:00 GMT-3')], 'range': 'min'}
我的错误是假设我必须在一个请求变量上传递所有列表元素。
我在表单末尾添加的代码现在看起来像这样:
<input type="radio"
id="query-date-range"
name="created.query:record:list:date:ignore_empty"
tal:attributes="value python:'';
checked python:checked=='' and 'checked' or '';"
/>
<label for="query-date-range" i18n:translate="time_range">Time range</label>
<input type="text"
id="range-start"
name="created.query:record:list:date:ignore_empty">
<input type="text"
id="range-end"
name="created.query:record:list:date:ignore_empty">
<script>
var today = new Date();
var yesterday = new Date();
yesterday.setDate(yesterday.getDate() - 1);
var start = yesterday.toLocaleDateString().slice(0, 10);
var end = today.toLocaleDateString().slice(0, 10);
$(document).ready(function() {
$("#range-start").datepicker();
$("#range-end").datepicker();
$('#range-start').hide();
$('#range-end').hide();
});
$('input:radio').change(function() {
var option = $('input:radio:checked', '#searchform').val();
if (option === '') {
$('#range-start').val(start);
$('#range-start').show();
$('#range-end').val(end);
$('#range-end').show();
$('#range').val('min:max');
}
else {
$('#range-start').val('');
$('#range-start').hide();
$('#range-end').val('');
$('#range-end').hide();
$('#range').val('min');
};
});
</script>
请特别注意以下事项:
开始日期和结束日期是与jQueryUI datepicker小部件关联的输入元素。
两个输入元素与另一个输入元素具有相同的名称(created.query:record:list:date:ignore_empty
),这里是Zope魔术发生的位置:具有相同名称的所有输入元素的值将在唯一列表记录上转换像这样:
'created': {'query': [DateTime('2014/07/15 00:00:00 GMT-3'), DateTime('2014/07/16 00:00:00 GMT-3')], 'range': 'min:max'}
我们设置了一个额外的参数转换器(ignore_empty
),它只是避免向列表中添加没有设置值的元素(我也将此转换器添加到其他输入元素中)。
当我们点击query-date-range
元素时,我们必须初始化日期选择器;当我们点击任何其他元素时,我们需要清除这些值以避免将它们添加到列表中。
我们还根据@sdupton之前提到的查询类型更改range
元素的值。
可以肯定地增强代码的JavaScript部分;我的技能非常有限。