Neo4j Cypher - условные записи на совпадения - PullRequest
0 голосов
/ 10 декабря 2018

У меня есть база данных с пользователями (u:User {id: 1}), статусами пользователей (us:UserStatus {status: 'pending'}) и связями между ними (u)-[hs:HAS_STATUS {from: 1541030400, to: 4102444800}]->(us).

Где пользовательские статусы могут быть "pending", "active" или "suspended"2100-01-01 - это некоторая дата в будущем, означающая, что у пользователя все еще есть этот статус.

Я пытаюсь выполнить запрос, который обновляет статус пользователя, создавая новые отношения с новым статусом и архивами.старые отношения, установив для свойства to текущую дату.

Это то, что я пробовал:

MERGE (u:User { id: 1 })
WITH u
MATCH (u)-[hs1:HAS_STATUS]->(us1:UserStatus)
WHERE us1.status <> 'active' AND hs1.to > 1544400000
SET hs1.to = 1544400000
MERGE (us2:UserStatus {status: 'active'})
MERGE (u)-[hs2:HAS_STATUS {from: 1544400000, to: 4102444800}]->(us2)

Если у пользователя уже есть статус, удовлетворяющий WHERE условие, затем оно архивируется и создается новое статусное отношение.Однако, если у пользователя еще нет статуса, предложение SET пропускается (как и предполагалось), однако пропускаются и две строки MERGE.Как я могу гарантировать, что они выполняются независимо от слияния?

Редактировать: В исходном запросе были опечатки.

Ответы [ 2 ]

0 голосов
/ 11 декабря 2018

[Это отвечает на ваш обновленный вопрос]

A MATCH (без квалификатора OPTIONAL) прервет оставшуюся часть запроса, если совпадение не удастся.

Этот запрос показывает одинспособ сопоставления с шаблоном и, при необходимости, выполнение операции записи, если совпадение выполнено успешно, без прерывания оставшейся части запроса в случае сбоя сопоставления:

MERGE (u:User { id: 1 })
FOREACH(hs IN
  [(u)-[hs1:HAS_STATUS]->(us1:UserStatus)
        WHERE us1.status <> 'active' AND hs1.to > 1544400000 | hs1] |
  SET hs.to = 1544400000)
MERGE (us2:UserStatus {status: 'active'})
MERGE (u)-[hs2:HAS_STATUS {from: 1544400000, to: 4102444800}]->(us2);

В этом запросе используется предложение FOREACH дляпереберите список (размером 0 или 1, в данном случае) соответствующих значений hs1, установив для каждого значения to значение 1544400000.Список генерируется с помощью шаблона .Даже если список пуст, остальная часть запроса все еще выполняется.

0 голосов
/ 10 декабря 2018

РЕДАКТИРОВАТЬ: предыдущий сегмент ответа удален, так как вы сказали, что «даты», которые вы используете в своем запросе, фактически заменяют секунды эпохи.

Если строки не изменены, то одно из двухпроисходит.

  1. Вашему МАТЧУ (со связанным ГДЕ) не удалось найти подходящий шаблон.Вы должны попытаться просто запустить этот MATCH и WHERE, чтобы увидеть, возвращает ли он какие-либо строки.

  2. Отношение, в котором вы пытаетесь MERGE, уже существует.Возможно, вы захотите попытаться сопоставить это отношение (с этими свойствами) между этими двумя узлами и посмотреть, существует ли оно уже.

...