From 902709bc8750d8cd7b676ab23e9736d53e37c1f3 Mon Sep 17 00:00:00 2001 From: Michael Pollmeier Date: Mon, 30 Sep 2024 12:43:55 +0200 Subject: [PATCH] include node id in json (for StoredNode) fixes https://github.com/joernio/joern/issues/4976 --- .../io/shiftleft/semanticcpg/language/Steps.scala | 15 ++++++++++----- .../semanticcpg/language/StepsTest.scala | 3 +++ 2 files changed, 13 insertions(+), 5 deletions(-) diff --git a/semanticcpg/src/main/scala/io/shiftleft/semanticcpg/language/Steps.scala b/semanticcpg/src/main/scala/io/shiftleft/semanticcpg/language/Steps.scala index 3db74bbff3aa..e24170db71a0 100644 --- a/semanticcpg/src/main/scala/io/shiftleft/semanticcpg/language/Steps.scala +++ b/semanticcpg/src/main/scala/io/shiftleft/semanticcpg/language/Steps.scala @@ -82,14 +82,19 @@ class Steps[A](val traversal: Iterator[A]) extends AnyVal { object Steps { private lazy val nodeSerializer = new CustomSerializer[AbstractNode](implicit format => ( - { case _ => ??? }, + { case _ => ??? }, // deserializer not required for now { case node: AbstractNode => - val elementMap = (0 until node.productArity).map { i => + val elementMap = Map.newBuilder[String, Any] + (0 until node.productArity).foreach { i => val label = node.productElementName(i) val element = node.productElement(i) - label -> element - }.toMap + ("_label" -> node.label) - Extraction.decompose(elementMap) + elementMap.addOne(label -> element) + } + elementMap.addOne("_label" -> node.label) + if (node.isInstanceOf[StoredNode]) { + elementMap.addOne("_id" -> node.asInstanceOf[StoredNode].id()) + } + Extraction.decompose(elementMap.result()) } ) ) diff --git a/semanticcpg/src/test/scala/io/shiftleft/semanticcpg/language/StepsTest.scala b/semanticcpg/src/test/scala/io/shiftleft/semanticcpg/language/StepsTest.scala index deafb4044809..1d276d2341c6 100644 --- a/semanticcpg/src/test/scala/io/shiftleft/semanticcpg/language/StepsTest.scala +++ b/semanticcpg/src/test/scala/io/shiftleft/semanticcpg/language/StepsTest.scala @@ -120,6 +120,9 @@ class StepsTest extends AnyWordSpec with Matchers { val parsed = parse(json).children.head // exactly one result for the above query (parsed \ "_label") shouldBe JString("METHOD") (parsed \ "name") shouldBe JString("foo") + + // id should be defined, but we don't care what number it is + (parsed \ "_id") shouldBe a[JInt] } "operating on NewNode" in {