AQL: динамический запрос с датами вложенного массива

Я пытался заставить этот динамический запрос работать с датами, как показано ниже в ArangoDB 3.1.

Это отлично работает, когда я не пытаюсь запросить даты, но возвращает пустой список, как только я пытаюсь запросить дату, как показано ниже ...

{ 
    query: 
        'For c IN @@collectionName 
        FILTER  (  c.@p0 == @v0  AND  c.@p1 >= @v1  AND  c.@p2 <= @v2  )  
        LIMIT  @count  RETURN c ',

    bindVars: {
        '@collectionName': 'Event',
        p0: 'isPublished',
        v0: true,
        p1: 'dates[*].startsAt',
        v1: '2018-06-01T04:00:00.000Z',
        p2: 'dates[*].startsAt',
        v2: '2018-07-01T03:59:59.999Z',
        count: 9
    } 
} 

Нужна помощь, чтобы пройти через это


person Glstunna    schedule 14.05.2018    source источник
comment
Есть ли причина, по которой вы храните свои даты в таком формате? Такие даты - это просто строки, и вы используете строковый компаратор, поскольку дата не является типом данных. Если вы конвертируете все даты в Unix Epoch time в UTC 0 (с точностью до миллисекунды), то вы имеете дело с целыми числами, и сравнение дат становится намного проще. Вам нужно будет создать функции для определения целых чисел Unix Epoch Time для заданных дат, но как только это будет сделано, это будет проще.   -  person David Thomas    schedule 14.05.2018


Ответы (1)


В вашем запросе есть ошибки, но на самом деле они не связаны с датами:

  • dates[*].startsAt не является допустимым путем к атрибуту, а является сокращенным выражением для FOR date IN dates RETURN date.startsAt, которое возвращает массив

  • Оператор сравнения >= не работает с массивами, как вы думаете. null, true, false и все числа и строки меньше любого массива, см. Тип и порядок значений. Ваш массив временных меток всегда будет больше, чем любая заданная строка временных меток. Вместо этого вы, вероятно, захотите использовать оператор сравнения массивов. как ALL >=.

  • Выражение dates[*].startsAt не может использоваться в качестве параметра привязки. В структуре документа без массива, такого как { "date": { "startsAt": "..." } }, было бы прекрасно связать ["date", "startsAt"] как p1 или p2. Обратите внимание на то, что значение параметра привязки представляет собой массив строк. "date.startsAt", с другой стороны, будет описывать путь для атрибута верхнего уровня
    { "date.startsAt": ... }, а не вложенного атрибута, начинается с даты атрибута верхнего уровня, например { "date": { "startsAt": ... } }.
    То, что вы делаете с dates[*].startsAt, описывает атрибут верхнего уровня как
    { "dates[*].startsAt": ... }, которого не существует. ["dates[*]", "startsAt"] тоже не работает. Если вы хотите использовать выражение расширения массива, вы должны написать его как c.@p1a[*].@p1b в своем запросе и использовать параметры привязки { "p1a": "dates", "p2a": "startsAt" }.

Запрос:

FOR c IN @@collectionName 
  FILTER c.@p0 == @v0
  FILTER c.@p1a[*].@p1b ALL >= @v1 
  FILTER c.@p2a[*].@p2b ALL < @v2
  LIMIT @count
  RETURN c

bindVars:

{
  "@collectionName": "Event",
  "p0": "isPublished",
  "v0": true,
  "p1a": "dates",
  "p1b": "startsAt",
  "v1": "2018-06-01T04:00:00.000Z",
  "p2a": "dates",
  "p2b": "startsAt",
  "v2": "2018-07-01T04:00:00.000Z",
  "count": 9
}
person CodeManX    schedule 14.05.2018