Я пытаюсь отфильтровать пути в моем графике на основе 2 условий:
- Если все узлы, которые я указываю, попадают в узлы пути
- Если все отношения, которые я указываю, попадают в путь отношений.
Это запрос Cypher, который я выполняю:
MATCH path=(`GROUP1`: TRAVEL_PLAN { name: 'GROUP1' })-[*]->(e1)
WITH ['USE', 'HAS', 'ALLOW'] as foundRels, ['LODGING', 'R1'] as foundNodes, path
WHERE ANY (rel in relationships(path) WHERE ALL (foundRel in foundRels WHERE type(rel) CONTAINS foundRel))
AND ANY (pathNode in nodes(path) WHERE ALL (foundNode in foundNodes WHERE pathNode.name CONTAINS foundNode))
RETURN apoc.path.elements(path) as pathElements
но проблема в том, что я получаю пустой набор результатов с 0 записями.
Как указано выше, я хочу сосредоточиться на вышеуказанном пути, используя заданные отношения и данные узлы, но я не могу просто сделать:
MATCH path=(`GROUP1`: TRAVEL_PLAN { name: 'GROUP1' })-[*]->(`LODGING`: TRAVEL_ENTITLEMENT { name: 'LODGING' })-[*]->(`R1`: RULE { name: 'R1' })-[*]->(`RS 3000` : MONEY { name: `RS 3000` })
RETURN path
потому что отношения и узлы я получаю динамически, поэтому я делаю переменную длины, расширяю и нахожу все пути вроде:
MATCH path=(`GROUP1`: TRAVEL_PLAN { name: 'GROUP1' })-[*]->(e1)
RETURN path
Я не знаю, нужно ли модифицировать запрос или что-то не так в моем подходе, потому что проблема в том, что я не могу явно сопоставить путь до того, как получу, так как не знаю, какие узлы будут существовать в MATCH
Таким образом, лучшая ставка, которую я пытаюсь сделать, это от узла, который я пытаюсь развернуть по всем путям и отфильтровать его на основе вышеупомянутых 2 условий.
Пожалуйста, предложите мне альтернативный подход, основанный на этом, или элегантный способ сделать это, чтобы я мог обрисовать путь, обрисованный в общих чертах на скриншоте.
Это пример данных для воссоздания графика на случай, если он вам понадобится.
MERGE (`BANGALORE`: LOCATION { name: 'BANGALORE' })
ON CREATE SET
`BANGALORE`.id = randomUUID(),
`BANGALORE`.type = 'LOCATION',
`BANGALORE`.created = timestamp()
ON MATCH SET
`BANGALORE`.lastUpdated = timestamp()
MERGE (`GROUP1`: TRAVEL_PLAN { name: 'GROUP1' })
ON CREATE SET
`GROUP1`.id = randomUUID(),
`GROUP1`.type = 'TRAVEL_PLAN',
`GROUP1`.created = timestamp()
ON MATCH SET
`GROUP1`.lastUpdated = timestamp()
MERGE (`LODGING`: TRAVEL_ENTITLEMENT { name: 'LODGING' })
ON CREATE SET
`LODGING`.id = randomUUID(),
`LODGING`.type = 'TRAVEL_ENTITLEMENT',
`LODGING`.created = timestamp()
ON MATCH SET
`LODGING`.lastUpdated = timestamp()
MERGE (`BOARDING`: TRAVEL_ENTITLEMENT { name: 'BOARDING' })
ON CREATE SET
`BOARDING`.id = randomUUID(),
`BOARDING`.type = 'TRAVEL_ENTITLEMENT',
`BOARDING`.created = timestamp()
ON MATCH SET
`BOARDING`.lastUpdated = timestamp()
MERGE (`R1`: RULE { name: 'R1' })
ON CREATE SET
`R1`.id = randomUUID(),
`R1`.type = 'RULE',
`R1`.created = timestamp()
ON MATCH SET
`R1`.lastUpdated = timestamp()
MERGE (`R2`: RULE { name: 'R2' })
ON CREATE SET
`R2`.id = randomUUID(),
`R2`.type = 'RULE',
`R2`.created = timestamp()
ON MATCH SET
`R2`.lastUpdated = timestamp()
MERGE (`RS 3000`: MONEY { name: 'RS 3000' })
ON CREATE SET
`RS 3000`.id = randomUUID(),
`RS 3000`.type = 'MONEY',
`RS 3000`.created = timestamp()
ON MATCH SET
`RS 3000`.lastUpdated = timestamp()
MERGE (`RS 4000`: MONEY { name: 'RS 4000' })
ON CREATE SET
`RS 4000`.id = randomUUID(),
`RS 4000`.type = 'MONEY',
`RS 4000`.created = timestamp()
ON MATCH SET
`RS 4000`.lastUpdated = timestamp()
----------------------------------------------------------------------------------------------------
CREATE INDEX ON :LOCATION(name)
CREATE INDEX ON :TRAVEL_PLAN(name)
CREATE INDEX ON :TRAVEL_ENTITLEMENT(name)
CREATE INDEX ON :RULE(name)
CREATE INDEX ON :MONEY(name)
----------------------------------------------------------------------------------------------------
MATCH (`BANGALORE`: LOCATION { name: 'BANGALORE' })
MATCH (`GROUP1`: TRAVEL_PLAN { name: 'GROUP1' })
MATCH (`LODGING`: TRAVEL_ENTITLEMENT { name: 'LODGING' })
MATCH (`BOARDING`: TRAVEL_ENTITLEMENT { name: 'BOARDING' })
MATCH (`R1`: RULE { name: 'R1' })
MATCH (`R2`: RULE { name: 'R2' })
MATCH (`RS 3000`: MONEY { name: 'RS 3000' })
MATCH (`RS 4000`: MONEY { name: 'RS 4000' })
CREATE (`GROUP1`)-[:_USE_]->(`LODGING`)
CREATE (`GROUP1`)-[:_USE_]->(`BOARDING`)
CREATE (`LODGING`)-[:_PROVIDE_IN]->(`BANGALORE`)
CREATE (`BOARDING`)-[:_PROVIDE_IN]->(`BANGALORE`)
CREATE (`LODGING`)-[:_HAS_RULE]->(`R1`)
CREATE (`BOARDING`)-[:_HAS_RULE]->(`R2`)
CREATE (`R1`)-[:_ALLOW_FOR]->(`RS 3000`)
CREATE (`R2`)-[:_ALLOW_FOR]->(`RS 4000`)
----------------------------------------------------------------------------------------------------
Я также сделал short sandbox
в Neo4j, чтобы повторить мою проблему.
Это учетные данные:
Neo4j Browser: https://10-0-1-249-33207.neo4jsandbox.com/
Direct Neo4j HTTP: http://52.86.200.133:33207/browser/
Username: neo4j
Password: help-canister-berths
JavaScript Bolt URL: bolt://ws-10-0-1-249-33206.neo4jsandbox.com:443
IP Address: 52.86.200.133
HTTP Port: 33207
Bolt Port: 33206
Expires: 2 days, 23 hours, 59 minutes