When loading graphml: Vertex with id already exists: 3

1,054 views
Skip to first unread message

ks...@kendallshaw.com

unread,
Aug 16, 2013, 12:24:48 PM8/16/13
to gremli...@googlegroups.com
Hi,

I am creating a graph using blueprints, and using GraphMLWriter to write the graph. I then want to load it into a TinkerGraph (for tinkering at this point). And I get an error message when attempting to load the graph about vertex with id 3 which has properties name="lop"  and lang="java".

If I use gremlin to write and load a graph, I get the same error. For example:

g = TinkerGraphFactory.createTinkerGraph()
v1 = g.addVertex()
v2 = g.addVertex()
v3 = g.addVertex()
v2.addEdge("edge", v1)
v3.addEdge("edge", v1)
new GraphMLWriter(g).outputGraph(new FileOutputStream("test.graphml"))

Then exit, load gremlin shell again, and:

g = TinkerGraphFactory.createTinkerGraph()
new GraphmlReader(g).inputGraph(new FileInputStream("test.graphml"))

or

g.loadGraphML('test.graphml')

It complains:

Vertex with id already exists: 3

If I load the graphml into gephi it does not complain.

At this point, I just want to persist a graph and use it to learn about blueprints and gremlin.

Am I storing and loading graphml incorrectly?

Kendall


Stephen Mallette

unread,
Aug 16, 2013, 12:29:25 PM8/16/13
to gremli...@googlegroups.com
Doing this...

g = TinkerGraphFactory.createTinkerGraph()

creates a toy graph with all those vertices/edges already in it...just do:

g = new TinkerGraph()
g.loadGraphML("test.graphml")



--
You received this message because you are subscribed to the Google Groups "Gremlin-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to gremlin-user...@googlegroups.com.
For more options, visit https://groups.google.com/groups/opt_out.

Hugh

unread,
Nov 4, 2014, 4:58:10 PM11/4/14
to gremli...@googlegroups.com
Hello,

Thanks for all your fine work on vendor agnostic graph programming.

I'm seeing the "id already exists" while using GraphMLReader on graphml written using GraphMLWriter.

I'm building up a Tinkergraph that's sufficiently large that I'm building it up in phases with persistence after each step, a read/add/write pattern. I didn't find any test cases of this pattern, here's a start on one below. My project code uses TinkerGraph.open(), here I start with classic for convenience. I'm using the sample graphml read & write code from the website doc.

I can see two edges with the same id in the graphml written by GraphMLReader.

Any insights or suggestions would be appreciated.

Thanks again,
Hugh

environment:

gremlin-core and tinkergraph-gremlin 3.0.0.M3
Java 1.8.0u25

test:

/**
 *
 */
package com.hughjdevlin;

import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import org.junit.Before;
import org.junit.Test;

import com.tinkerpop.gremlin.structure.Graph;
import com.tinkerpop.gremlin.structure.Vertex;
import com.tinkerpop.gremlin.structure.io.GraphReader;
import com.tinkerpop.gremlin.structure.io.graphml.GraphMLReader;
import com.tinkerpop.gremlin.structure.io.graphml.GraphMLWriter;
import com.tinkerpop.gremlin.tinkergraph.structure.TinkerFactory;
import com.tinkerpop.gremlin.tinkergraph.structure.TinkerGraph;

/**
 * @author hugh
 *
 */
public class TinkergraphGraphmlTest {
    Graph g;
   
    public void read(String file) throws FileNotFoundException, IOException {
        final GraphReader reader = GraphMLReader.build().create();
        try (final InputStream is = new FileInputStream(file)) {
            reader.readGraph(is, g);
        }   
    }
   
    public void write(String file) throws FileNotFoundException, IOException {
        try (final OutputStream os = new FileOutputStream(file)) {
            GraphMLWriter.build().create().writeGraph(os, g);
        }
    }

    /**
     * @throws java.lang.Exception
     */
    @Before
    public void setUp() throws Exception {
        g = TinkerFactory.createClassic();
        // Add some edges
        Integer[] ids = g.V().id().toSet().toArray(new Integer[0]);
        Vertex v0 = g.v(ids[0]);
        for(int i = 1; i < ids.length; i++) {
            v0.addEdge("newEdge", g.v(ids[i]));
        }
        write("db/TinkergraphGraphmlTest.graphml");
        g.close();
        g = TinkerGraph.open();
    }

    @Test
    public void testReadGraphml() throws FileNotFoundException, IOException {
        read("db/TinkergraphGraphmlTest.graphml");
    }

}

stack trace:

java.lang.IllegalArgumentException: Edge with id already exists: 12
    at com.tinkerpop.gremlin.structure.Graph$Exceptions.edgeWithIdAlreadyExists(Graph.java:803)
    at com.tinkerpop.gremlin.tinkergraph.structure.TinkerHelper.addEdge(TinkerHelper.java:42)
    at com.tinkerpop.gremlin.tinkergraph.structure.TinkerVertex.addEdge(TinkerVertex.java:76)
    at com.tinkerpop.gremlin.structure.util.batch.BatchGraph$BatchVertex.addEdge(BatchGraph.java:358)
    at com.tinkerpop.gremlin.structure.io.graphml.GraphMLReader.readGraph(GraphMLReader.java:189)
    at com.hughjdevlin.TinkergraphGraphmlTest.read(TinkergraphGraphmlTest.java:33)
    at com.hughjdevlin.TinkergraphGraphmlTest.testReadGraphml(TinkergraphGraphmlTest.java:62)
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
    at java.lang.reflect.Method.invoke(Method.java:483)
    at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:47)
    at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
    at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:44)
    at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
    at org.junit.internal.runners.statements.RunBefores.evaluate(RunBefores.java:26)
    at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:271)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:70)
    at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:50)
    at org.junit.runners.ParentRunner$3.run(ParentRunner.java:238)
    at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:63)
    at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:236)
    at org.junit.runners.ParentRunner.access$000(ParentRunner.java:53)
    at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:229)
    at org.junit.runners.ParentRunner.run(ParentRunner.java:309)
    at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:50)
    at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:467)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:683)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:390)
    at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:197)

graphml:

<key id="labelV" for="node" attr.name="labelV" attr.type="string"/>
<key id="name" for="node" attr.name="name" attr.type="string"/>
<key id="lang" for="node" attr.name="lang" attr.type="string"/>
<key id="age" for="node" attr.name="age" attr.type="int"/>
<key id="labelE" for="edge" attr.name="labelE" attr.type="string"/>
<key id="weight" for="edge" attr.name="weight" attr.type="float"/>
<graph id="G" edgedefault="directed">
<node id="1">
<data key="labelV">vertex</data>
<data key="name">marko</data>
<data key="age">29</data>
</node>
<node id="2">
<data key="labelV">vertex</data>
<data key="name">vadas</data>
<data key="age">27</data>
</node>
<node id="3">
<data key="labelV">vertex</data>
<data key="name">lop</data>
<data key="lang">java</data>
</node>
<node id="4">
<data key="labelV">vertex</data>
<data key="name">josh</data>
<data key="age">32</data>
</node>
<node id="5">
<data key="labelV">vertex</data>
<data key="name">ripple</data>
<data key="lang">java</data>
</node>
<node id="6">
<data key="labelV">vertex</data>
<data key="name">peter</data>
<data key="age">35</data>
</node>
<edge id="16" source="1" target="6">
<data key="labelE">newEdge</data>
</edge>
<edge id="7" source="1" target="2">
<data key="labelE">knows</data>
<data key="weight">0.5</data>
</edge>
<edge id="8" source="1" target="4">
<data key="labelE">knows</data>
<data key="weight">1.0</data>
</edge>
<edge id="9" source="1" target="3">
<data key="labelE">created</data>
<data key="weight">0.4</data>
</edge>
<edge id="10" source="4" target="5">
<data key="labelE">created</data>
<data key="weight">1.0</data>
</edge>
<edge id="11" source="4" target="3">
<data key="labelE">created</data>
<data key="weight">0.4</data>
</edge>
<edge id="12" source="6" target="3">
<data key="labelE">created</data>
<data key="weight">0.2</data>
</edge>
<edge id="12" source="1" target="2">
<data key="labelE">newEdge</data>
</edge>
<edge id="13" source="1" target="3">
<data key="labelE">newEdge</data>
</edge>
<edge id="14" source="1" target="4">
<data key="labelE">newEdge</data>
</edge>
<edge id="15" source="1" target="5">
<data key="labelE">newEdge</data>
</edge>
</graph>
</graphml>

Hugh

unread,
Nov 5, 2014, 10:33:10 AM11/5/14
to gremli...@googlegroups.com
Problem duplicated under 3.0.0.M4 as well. Thanks.

Hugh

Marko Rodriguez

unread,
Nov 5, 2014, 11:55:07 AM11/5/14
to gremli...@googlegroups.com
Hello,

You can not have two vertices, edges, or vertex-properties with the same id in the same graph.

gremlin> g = TinkerGraph.open()
==>tinkergraph[vertices:0 edges:0]
gremlin> g.addVertex(id,1)
==>v[1]
gremlin> g.addVertex(id,1)
Vertex with id already exists: 1
Display stack trace? [yN]
gremlin> g.addVertex(id,2)
==>v[2]
gremlin>

Marko.
On Nov 5, 2014, at 8:33 AM, Hugh <hughjam...@gmail.com> wrote:

Problem duplicated under 3.0.0.M4 as well. Thanks.

Hugh

--
You received this message because you are subscribed to the Google Groups "Gremlin-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to gremlin-user...@googlegroups.com.

Daniel Kuppitz

unread,
Nov 5, 2014, 12:31:58 PM11/5/14
to gremli...@googlegroups.com
It's not a GraphMLReader/Writer problem, it seems to be a problem with TinkerGraphs ID assignment. Check this out:

gremlin> g = TinkerFactory.createClassic()
==>tinkergraph[vertices:6 edges:6]
gremlin> ids = g.V().id().toList(); null
==>null
gremlin> v0 = g.v(ids[0])
==>v[1]
gremlin> ids.tail().each { id -> v0.addEdge("newEdge", g.v(id)) }; null
==>null
gremlin> g.E()
==>e[16][1-newEdge->6]
==>e[7][1-knows->2]
==>e[8][1-knows->4]
==>e[9][1-created->3]
==>e[10][4-created->5]
==>e[11][4-created->3]
==>e[12][6-created->3]
==>e[12][1-newEdge->2]

==>e[13][1-newEdge->3]
==>e[14][1-newEdge->4]
==>e[15][1-newEdge->5]
gremlin>


Cheers,
Daniel


Marko Rodriguez

unread,
Nov 5, 2014, 12:47:06 PM11/5/14
to gremli...@googlegroups.com
Hi,

Here is the insanity:

gremlin> g.e(12)          // integer
==>e[12][6-created->3]
gremlin> g.e(12l)         // long
==>e[12][1-newEdge->2]

So these are in fact TWO different edge ids. However, when you write to GraphML, I suspect it all gets converted to the same int or long-type (?? stephen) and then when you read back, two ids that are the same.

I would recommend using GremlinKryo instead of GraphML if you can to preserve the ID typing.

I can't change TinkerGraph as TinkerGraph needs to be allow ANY Java object as an ID so that it can remain the glue by which we are able to migrate graphs around. Unless people have another idea? E.g. add an ID generator to TinkerGraph -- g.setIdGenerator(Function<Element,Object> idGenerator).

Marko.

Hugh

unread,
Nov 5, 2014, 1:01:03 PM11/5/14
to gremli...@googlegroups.com
Thanks for your reply. I understand, ids need to be unique. I'm content to let t3 manage ids. The test case posted above does not do any explicit id management. It adds some edges to an existing graph, and apparently an id from the existing graph was re-used. Thanks again.

Hugh

Hugh

unread,
Nov 5, 2014, 1:05:36 PM11/5/14
to gremli...@googlegroups.com
Thank you! This is a much simpler problem duplication. I was mistaken in thinking the problem related to graphml. Thanks again,
Hugh

Daniel Kuppitz

unread,
Nov 5, 2014, 1:31:44 PM11/5/14
to gremli...@googlegroups.com
I think the easiest solution would be to use you own version of generateClassic. Just duplicate the code and append a L to each ID. Or just copy my Gist.

Cheers,
Daniel

2014-11-05 19:05 GMT+01:00 Hugh <hughjam...@gmail.com>:
Thank you! This is a much simpler problem duplication. I was mistaken in thinking the problem related to graphml. Thanks again,
Hugh

--
You received this message because you are subscribed to the Google Groups "Gremlin-users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to gremlin-user...@googlegroups.com.

Hugh

unread,
Nov 7, 2014, 2:02:16 PM11/7/14
to gremli...@googlegroups.com

I agree we seem to have a problem with TinkerGraph ID assignment. 

I've opened an issue:
Duplicate id assignment in vertex and edge adds
#336 

https://github.com/tinkerpop/tinkerpop3/issues/336
Thanks.


Reply all
Reply to author
Forward
0 new messages