2

I am using JavaScript and neo4j-driver to save a node and some relations to my graph. Everything works as expected, but I would like to read the results of my write and output it in a specific format afterwards, which I am having trouble with. For now I have only managed to return all of the variables inside my query, but I would like the output to be in this specific format:

{
  "name": p.name
  "colors: [
     {
        hex: c.hex
     }
     {
        hex: c.hex
     }
   ]
}

This is my code so far, any help is appreciated:

export const savePallete = async (palette: Palette) => {
  if (!!palette.name === false) {
    throw Error("Palette name required!");
  }

  const writeQuery = `MERGE (p:Palette {name: $name})
   ON CREATE SET p.name = $name
   FOREACH (color IN $colors |
   MERGE (c:Color {hex: color.hex})
   ON CREATE SET c.hex = color.hex
   CREATE (p)-[i:INCLUDES]->(c))
   `;
  await session.writeTransaction((tx) =>
    tx.run(writeQuery, { name: palette.name, colors: palette.colors })
  );

  const readQuery = `
    MATCH (p:Palette)
    WHERE p.name = $name
    MATCH (p)-[:INCLUDES]->(c:Color)
    RETURN *
  `;
  const readResult = await session.readTransaction((tx) =>
    tx.run(readQuery, { name: palette.name })
  );
  return readResult;
};

As an example, if I call savePallete with this object as the argument, I would want to to get back the same result:

{
    "name": "First test palette",
    "colors": [
        {
            "hex": "#123123"
        },
        {
            "hex": "#ffffff"
        },
        {
            "hex": "#000000"
        }
    ]
}
Miha Šušteršič
  • 9,742
  • 25
  • 92
  • 163
  • Hey, I tried adding this query: `MATCH (p:Palette) WHERE p.name = $name MATCH (p)-[:INCLUDES]->(c:Color) COLLECT c AS colors RETURN {name: p.name, colors: c}`. I am getting this error: `error: Neo4jError: Invalid input 'COLLECT'`. Probably some syntax error, since the collect function seems OK – Miha Šušteršič May 22 '22 at 07:17

1 Answers1

1

One way to do it is to replace your readQuery with (last 2 lines are different):

    MATCH (p:Palette)
    WHERE p.name = $name
    MATCH (p)-[:INCLUDES]->(c:Color)
    WITH COLLECT({hex: c.hex}) AS colors, p
    RETURN {name: p.name, colors: colors}

This will collect the colors` hex as a JSON and will return a JSON format.

When using sample data:

MERGE (a:Palette {name: "First test palette"})
MERGE (b:Color {hex: "#123123"})
MERGE (c:Color {hex: "#ffffff"})
MERGE (d:Color {hex: "#000000"})
MERGE (a)-[:INCLUDES]-(b)
MERGE (a)-[:INCLUDES]-(c) 
MERGE (a)-[:INCLUDES]-(d) 

it returns your expected results

nimrod serok
  • 14,151
  • 2
  • 11
  • 33
  • I ended up changing the return statement a bit just to make it prettier `RETURN p.name AS name, colors`, but the logic remains the same with the `COLLECT` statement. Thanks. – Miha Šušteršič May 22 '22 at 07:31