From c916dde664220b02b9d8ef0c967c61a462128b97 Mon Sep 17 00:00:00 2001
From: cmoineau <cyril.moineau@cea.fr>
Date: Wed, 5 Jun 2024 16:12:18 +0000
Subject: [PATCH] Fix duplicate node name wen adding a GraphView to an other.
 Extra: - add Node::createUniqueName - GraphView::inView with str arg

---
 include/aidge/graph/GraphView.hpp |  7 +++++++
 include/aidge/graph/Node.hpp      | 11 +++++++++++
 src/graph/GraphView.cpp           | 13 ++++++++++++-
 src/graph/Node.cpp                | 10 ++++++++++
 4 files changed, 40 insertions(+), 1 deletion(-)

diff --git a/include/aidge/graph/GraphView.hpp b/include/aidge/graph/GraphView.hpp
index 627e78790..bbb1715cb 100644
--- a/include/aidge/graph/GraphView.hpp
+++ b/include/aidge/graph/GraphView.hpp
@@ -103,6 +103,13 @@ public:
     */
     bool inView(const NodePtr& nodePtr) const;
 
+    /**
+     * Check that a node is in the current GraphView.
+     * @param nodeName Name of the node to test the existence of.
+     * @return true if the GraphView contains a Node with the name ``nodeName``.
+     */
+    bool inView(const std::string& nodeName) const;
+
     inline NodePtr rootNode() const noexcept {
         return mRootNode;
     }
diff --git a/include/aidge/graph/Node.hpp b/include/aidge/graph/Node.hpp
index 2a0a4a3b7..a00debad1 100644
--- a/include/aidge/graph/Node.hpp
+++ b/include/aidge/graph/Node.hpp
@@ -100,6 +100,17 @@ public:
    */
   void setName(const std::string &name);
 
+  /**
+   * @brief Given the parameter name generate a new name which is unique
+   * in all the GraphView which contains this node.
+   * To generate the new name the method is called recursively and append
+   * the caracter ``_``.
+   * If no duplicate return name, this is the exit condition.
+   * @param name Base name to make unique.
+   * @return A unique name in all the GraphView which contains this one.
+  */
+  std::string createUniqueName(std::string name);
+
   /**
    * @brief Type of the node.
    * @return std::string
diff --git a/src/graph/GraphView.cpp b/src/graph/GraphView.cpp
index 77ca0b00c..89aeb1241 100644
--- a/src/graph/GraphView.cpp
+++ b/src/graph/GraphView.cpp
@@ -74,6 +74,9 @@ bool Aidge::GraphView::inView(const std::shared_ptr<Aidge::Node>& nodePtr) const
     return mNodes.find(nodePtr) != mNodes.cend();
 }
 
+bool Aidge::GraphView::inView(const std::string& nodeName) const {
+  return mNodeRegistry.find(nodeName) != mNodeRegistry.end();
+}
 
 void Aidge::GraphView::save(const std::string& path, bool verbose, bool showProducers) const {
     auto fp = std::unique_ptr<FILE, decltype(&std::fclose)>(std::fopen((path + ".mmd").c_str(), "w"), &std::fclose);
@@ -652,6 +655,14 @@ bool Aidge::GraphView::add(std::set<std::shared_ptr<Node>> otherNodes, bool incl
   std::set<NodePtr> nodesToAdd;
   std::set_difference(otherNodes.begin(), otherNodes.end(), mNodes.begin(), mNodes.end(), std::inserter(nodesToAdd, nodesToAdd.begin()));
 
+  // Check no name is common with the name in the current Graph
+  for (auto node : nodesToAdd) {
+    if (mNodeRegistry.find(node->name()) != mNodeRegistry.end()){
+      std::string newName = node->createUniqueName(node->name());
+      node->setName(newName);
+      fmt::print("Warning: node name \"{}\" is a duplicate, renaming to {}.\n", node->name(), newName);
+    }
+  }
   // List the nodes to rank, initially all the nodes in the GraphView
   std::set<NodePtr> nodesToRank(mNodes);
   nodesToRank.insert(nodesToAdd.begin(), nodesToAdd.end());
@@ -749,7 +760,7 @@ bool Aidge::GraphView::add(std::pair<NodePtr, std::set<NodePtr>> nodes, bool inc
 bool Aidge::GraphView::add(std::shared_ptr<GraphView> graph) {
     // set the rootNode to the other graphView rootNode if no rootNode yet
     mRootNode = mRootNode ? mRootNode : graph->rootNode();
-    return add(graph->getNodes(), false);
+    return add(graph->getNodes(), true);
 }
 
 void Aidge::GraphView::addChild(std::shared_ptr<Node> toOtherNode,
diff --git a/src/graph/Node.cpp b/src/graph/Node.cpp
index d8ae55322..290d61f54 100644
--- a/src/graph/Node.cpp
+++ b/src/graph/Node.cpp
@@ -61,6 +61,16 @@ void Aidge::Node::setName(const std::string& name) {
     mName = name;
 }
 
+std::string Aidge::Node::createUniqueName(std::string name){
+    for (auto graphView : views()){
+        if (graphView->inView(name)){
+            return createUniqueName(name.append("_"));
+        }else{
+            return name;
+        }
+    }
+}
+
 ///////////////////////////////////////////////////////
 //        OPERATORS
 ///////////////////////////////////////////////////////
-- 
GitLab