Skip to content

This is the multi-page printable view of this section. .

Return to the regular view of this page.

Client SDKs

Overview and integration guides for official HugeGraph client SDKs (Java, Python, Go, and more).

HugeGraph provides official client SDKs for multiple programming languages, making it straightforward to connect to HugeGraph Server, manage schemas, read and write vertices and edges, execute Gremlin traversals, and run graph algorithms.

Supported Clients

  • HugeGraph Java Client

    The primary Java SDK, offering an API style similar to Gremlin. It supports schema definitions, CRUD operations, Gremlin queries, Traverser algorithms, and GraphSpace isolation.

  • HugeGraph Python Client

    The official Python SDK (pyhugegraph), maintained in the HugeGraph-AI repository. It manages schemas, reads and writes graph data, and executes Gremlin queries with first-class support for HugeGraph-LLM and HugeGraph-ML.

  • HugeGraph Go Client

    The official Go SDK, supporting version checks, schema management (PropertyKey, VertexLabel, EdgeLabel), vertex operations, and Gremlin queries.

Selection Guide

  • Java/Scala production services: Use the HugeGraph Java Client for the most comprehensive feature set, connection pooling, and advanced Traverser algorithms.
  • AI, LLM, and data science workflows: Use the HugeGraph Python Client (pyhugegraph) for Python data science, graph analytics, and native integration with HugeGraph-LLM and HugeGraph-ML.
  • Microservices and cloud-native utilities: Use the HugeGraph Go Client or integrate directly via RESTful API.
  • Interactive shell debugging: Use the Gremlin Console for command-line exploration.

1 - HugeGraph Java Client

1 Overview

HugeGraph Java Client translates Java APIs into REST requests to HugeGraph Server. It supports managing schemas and graph data, executing Gremlin queries, and calling Traverser APIs. This guide covers quick-start setup and examples alongside complete core API reference documentation.

For other languages, use the Go Client or the Python Client.

2 What You Need

  • JDK 17 for this walkthrough and for building Client 1.8.0 from Toolchain master
  • Maven 3.6.3+

3 How To Use

The basic steps to use HugeGraph-Client are as follows:

  1. Create a Maven project in IntelliJ IDEA or Eclipse.
  2. Add the HugeGraph-Client dependency to pom.xml.
  3. Create a client, call its APIs, and close it after use.

See the complete example in the following section for the detail.

4 Complete Example

4.1 Build New Maven Project

Using IDEA or Eclipse to create the project:

4.2 Add Hugegraph-Client Dependency In POM

1<dependencies>
2    <dependency>
3        <groupId>org.apache.hugegraph</groupId>
4        <artifactId>hugegraph-client</artifactId>
5        <!-- The complete examples below work with the published 1.7.0 client -->
6        <version>1.7.0</version>
7    </dependency>    
8</dependencies>

Choose the client version before building:

Use caseClient versionJava build target
Run the complete examples belowPublished 1.7.0; use the dependency aboveJava 8 in the release POM; this walkthrough uses JDK 17
Use new master APIs, such as capability detectionToolchain master (based on 1.8)Java 17

The examples use Schema, Graph, Gremlin and resource-cleanup APIs available in Client 1.7.0 and compatible with Toolchain master. The release’s Java build target does not describe the runtime requirements of every transitive dependency.

To use unreleased features from the master branch, build Client from source (see Tools source build instructions):

1java -version
2mvn -version
3mvn -Dmaven.repo.local="${candidate_dir:?Run the candidate SDK setup first}/m2" \
4  -Dsdk.validation.mode=candidate \
5  install -pl hugegraph-client -am -DskipTests -Dmaven.javadoc.skip=true -ntp

Both version checks must report JDK 17. Also pass -Dmaven.repo.local="$candidate_dir/m2" to Maven commands in projects using Client from master. Client and Server versions need not be identical; check the required APIs and compatibility before upgrading.

4.3 Example

Choose a single-record or batch example. Save the complete code as src/main/java/SingleExample.java or src/main/java/BatchExample.java in your Maven project. The copy button includes the folded lines.

4.3.1 SingleExample
  1import java.io.IOException;
  2import java.util.Iterator;
  3import java.util.List;
  4
  5import org.apache.hugegraph.driver.GraphManager;
  6import org.apache.hugegraph.driver.GremlinManager;
  7import org.apache.hugegraph.driver.HugeClient;
  8import org.apache.hugegraph.driver.SchemaManager;
  9import org.apache.hugegraph.structure.constant.T;
 10import org.apache.hugegraph.structure.graph.Edge;
 11import org.apache.hugegraph.structure.graph.Path;
 12import org.apache.hugegraph.structure.graph.Vertex;
 13import org.apache.hugegraph.structure.gremlin.Result;
 14import org.apache.hugegraph.structure.gremlin.ResultSet;
 15
 16public class SingleExample {
 17
 18    public static void main(String[] args) throws IOException {
 19        // If connect failed will throw a exception.
 20        HugeClient hugeClient = HugeClient.builder("http://localhost:8080",
 21                                                   "DEFAULT",
 22                                                   "hugegraph")
 23                                          .configUser("username", "password")
 24                                          // This is an example. In a production environment, secure credentials should be used.
 25                                          .build();
 26
 27        SchemaManager schema = hugeClient.schema();
 28
 29        schema.propertyKey("name").asText().ifNotExist().create();
 30        schema.propertyKey("age").asInt().ifNotExist().create();
 31        schema.propertyKey("city").asText().ifNotExist().create();
 32        schema.propertyKey("weight").asDouble().ifNotExist().create();
 33        schema.propertyKey("lang").asText().ifNotExist().create();
 34        schema.propertyKey("date").asDate().ifNotExist().create();
 35        schema.propertyKey("price").asInt().ifNotExist().create();
 36
 37        schema.vertexLabel("person")
 38              .properties("name", "age", "city")
 39              .primaryKeys("name")
 40              .ifNotExist()
 41              .create();
 42
 43        schema.vertexLabel("software")
 44              .properties("name", "lang", "price")
 45              .primaryKeys("name")
 46              .ifNotExist()
 47              .create();
 48
 49        schema.indexLabel("personByCity")
 50              .onV("person")
 51              .by("city")
 52              .secondary()
 53              .ifNotExist()
 54              .create();
 55
 56        schema.indexLabel("personByAgeAndCity")
 57              .onV("person")
 58              .by("age", "city")
 59              .secondary()
 60              .ifNotExist()
 61              .create();
 62
 63        schema.indexLabel("softwareByPrice")
 64              .onV("software")
 65              .by("price")
 66              .range()
 67              .ifNotExist()
 68              .create();
 69
 70        schema.edgeLabel("knows")
 71              .sourceLabel("person")
 72              .targetLabel("person")
 73              .properties("date", "weight")
 74              .ifNotExist()
 75              .create();
 76
 77        schema.edgeLabel("created")
 78              .sourceLabel("person").targetLabel("software")
 79              .properties("date", "weight")
 80              .ifNotExist()
 81              .create();
 82
 83        schema.indexLabel("createdByDate")
 84              .onE("created")
 85              .by("date")
 86              .secondary()
 87              .ifNotExist()
 88              .create();
 89
 90        schema.indexLabel("createdByWeight")
 91              .onE("created")
 92              .by("weight")
 93              .range()
 94              .ifNotExist()
 95              .create();
 96
 97        schema.indexLabel("knowsByWeight")
 98              .onE("knows")
 99              .by("weight")
100              .range()
101              .ifNotExist()
102              .create();
103
104        GraphManager graph = hugeClient.graph();
105        Vertex marko = graph.addVertex(T.LABEL, "person", "name", "marko",
106                                       "age", 29, "city", "Beijing");
107        Vertex vadas = graph.addVertex(T.LABEL, "person", "name", "vadas",
108                                       "age", 27, "city", "Hongkong");
109        Vertex lop = graph.addVertex(T.LABEL, "software", "name", "lop",
110                                     "lang", "java", "price", 328);
111        Vertex josh = graph.addVertex(T.LABEL, "person", "name", "josh",
112                                      "age", 32, "city", "Beijing");
113        Vertex ripple = graph.addVertex(T.LABEL, "software", "name", "ripple",
114                                        "lang", "java", "price", 199);
115        Vertex peter = graph.addVertex(T.LABEL, "person", "name", "peter",
116                                       "age", 35, "city", "Shanghai");
117
118        marko.addEdge("knows", vadas, "date", "2016-01-10", "weight", 0.5);
119        marko.addEdge("knows", josh, "date", "2013-02-20", "weight", 1.0);
120        marko.addEdge("created", lop, "date", "2017-12-10", "weight", 0.4);
121        josh.addEdge("created", lop, "date", "2009-11-11", "weight", 0.4);
122        josh.addEdge("created", ripple, "date", "2017-12-10", "weight", 1.0);
123        peter.addEdge("created", lop, "date", "2017-03-24", "weight", 0.2);
124
125        GremlinManager gremlin = hugeClient.gremlin();
126        System.out.println("==== Path ====");
127        ResultSet resultSet = gremlin.gremlin("g.V().outE().path()").execute();
128        Iterator<Result> results = resultSet.iterator();
129        results.forEachRemaining(result -> {
130            System.out.println(result.getObject().getClass());
131            Object object = result.getObject();
132            if (object instanceof Vertex) {
133                System.out.println(((Vertex) object).id());
134            } else if (object instanceof Edge) {
135                System.out.println(((Edge) object).id());
136            } else if (object instanceof Path) {
137                List<Object> elements = ((Path) object).objects();
138                elements.forEach(element -> {
139                    System.out.println(element.getClass());
140                    System.out.println(element);
141                });
142            } else {
143                System.out.println(object);
144            }
145        });
146
147        hugeClient.close();
148    }
149}
4.3.2 BatchExample
  1import java.util.ArrayList;
  2import java.util.List;
  3
  4import org.apache.hugegraph.driver.GraphManager;
  5import org.apache.hugegraph.driver.HugeClient;
  6import org.apache.hugegraph.driver.SchemaManager;
  7import org.apache.hugegraph.structure.graph.Edge;
  8import org.apache.hugegraph.structure.graph.Vertex;
  9
 10public class BatchExample {
 11
 12    public static void main(String[] args) {
 13        HugeClient hugeClient = HugeClient.builder("http://localhost:8080",
 14                                                   "DEFAULT",
 15                                                   "hugegraph")
 16                                          .configUser("username", "password")
 17                                          // This is an example. In a production environment, secure credentials should be used.
 18                                          .build();
 19
 20        SchemaManager schema = hugeClient.schema();
 21
 22        schema.propertyKey("name").asText().ifNotExist().create();
 23        schema.propertyKey("age").asInt().ifNotExist().create();
 24        schema.propertyKey("lang").asText().ifNotExist().create();
 25        schema.propertyKey("date").asDate().ifNotExist().create();
 26        schema.propertyKey("price").asInt().ifNotExist().create();
 27
 28        schema.vertexLabel("person")
 29              .properties("name", "age")
 30              .primaryKeys("name")
 31              .ifNotExist()
 32              .create();
 33
 34        schema.vertexLabel("person")
 35              .properties("price")
 36              .nullableKeys("price")
 37              .append();
 38
 39        schema.vertexLabel("software")
 40              .properties("name", "lang", "price")
 41              .primaryKeys("name")
 42              .ifNotExist()
 43              .create();
 44
 45        schema.indexLabel("softwareByPrice")
 46              .onV("software").by("price")
 47              .range()
 48              .ifNotExist()
 49              .create();
 50
 51        schema.edgeLabel("knows")
 52              .link("person", "person")
 53              .properties("date")
 54              .ifNotExist()
 55              .create();
 56
 57        schema.edgeLabel("created")
 58              .link("person", "software")
 59              .properties("date")
 60              .ifNotExist()
 61              .create();
 62
 63        schema.indexLabel("createdByDate")
 64              .onE("created").by("date")
 65              .secondary()
 66              .ifNotExist()
 67              .create();
 68
 69        // get schema object by name
 70        System.out.println(schema.getPropertyKey("name"));
 71        System.out.println(schema.getVertexLabel("person"));
 72        System.out.println(schema.getEdgeLabel("knows"));
 73        System.out.println(schema.getIndexLabel("createdByDate"));
 74
 75        // list all schema objects
 76        System.out.println(schema.getPropertyKeys());
 77        System.out.println(schema.getVertexLabels());
 78        System.out.println(schema.getEdgeLabels());
 79        System.out.println(schema.getIndexLabels());
 80
 81        GraphManager graph = hugeClient.graph();
 82
 83        Vertex marko = new Vertex("person").property("name", "marko")
 84                                           .property("age", 29);
 85        Vertex vadas = new Vertex("person").property("name", "vadas")
 86                                           .property("age", 27);
 87        Vertex lop = new Vertex("software").property("name", "lop")
 88                                           .property("lang", "java")
 89                                           .property("price", 328);
 90        Vertex josh = new Vertex("person").property("name", "josh")
 91                                          .property("age", 32);
 92        Vertex ripple = new Vertex("software").property("name", "ripple")
 93                                              .property("lang", "java")
 94                                              .property("price", 199);
 95        Vertex peter = new Vertex("person").property("name", "peter")
 96                                           .property("age", 35);
 97
 98        Edge markoKnowsVadas = new Edge("knows").source(marko).target(vadas)
 99                                                .property("date", "2016-01-10");
100        Edge markoKnowsJosh = new Edge("knows").source(marko).target(josh)
101                                               .property("date", "2013-02-20");
102        Edge markoCreateLop = new Edge("created").source(marko).target(lop)
103                                                 .property("date",
104                                                           "2017-12-10");
105        Edge joshCreateRipple = new Edge("created").source(josh).target(ripple)
106                                                   .property("date",
107                                                             "2017-12-10");
108        Edge joshCreateLop = new Edge("created").source(josh).target(lop)
109                                                .property("date", "2009-11-11");
110        Edge peterCreateLop = new Edge("created").source(peter).target(lop)
111                                                 .property("date",
112                                                           "2017-03-24");
113
114        List<Vertex> vertices = new ArrayList<>();
115        vertices.add(marko);
116        vertices.add(vadas);
117        vertices.add(lop);
118        vertices.add(josh);
119        vertices.add(ripple);
120        vertices.add(peter);
121
122        List<Edge> edges = new ArrayList<>();
123        edges.add(markoKnowsVadas);
124        edges.add(markoKnowsJosh);
125        edges.add(markoCreateLop);
126        edges.add(joshCreateRipple);
127        edges.add(joshCreateLop);
128        edges.add(peterCreateLop);
129
130        vertices = graph.addVertices(vertices);
131        vertices.forEach(vertex -> System.out.println(vertex));
132
133        edges = graph.addEdges(edges, false);
134        edges.forEach(edge -> System.out.println(edge));
135
136        hugeClient.close();
137    }
138}

4.4 Run The Example

  1. Start HugeGraph Server and prepare a test graph named hugegraph in graphspace DEFAULT.
  2. Set the Maven project’s JDK to 17. In the selected example, replace the Server URL, graphspace, graph and credentials in HugeClient.builder(...) and configUser(...) with your settings. Omit configUser(...) if Server does not require authentication.
  3. Run SingleExample.main() or BatchExample.main() in your IDE. Both examples create schema and graph data, print the results, and close the client. Use a test graph: existing schema or data can affect repeated runs.

The code in this document is written in java, but its style is very similar to gremlin(groovy). The user only needs to replace the variable declaration in the code with def or remove it directly, You can convert java code into groovy; in addition, each line of statement can be without a semicolon at the end, groovy considers a line to be a statement. The gremlin(groovy) written by the user in HugeGraph-Studio can refer to the java code in this document, and some examples will be given below.

This reference follows Toolchain master (Client 1.8.0). Prepare the matching dependency using the quickstart above; newly added APIs such as capability detection are unavailable in older clients.

5 HugeClient Builder & Operation Entries

HugeGraph-Client is the general entry for operating graph. Users must first create a HugeGraph-Client object and establish a connection (pseudo connection) with HugeGraph-Server before they can obtain the operation entry objects of schema, graph and gremlin.

HugeGraph-Client connects to an existing graph on the server. Its builder accepts a GraphSpace; the two-argument builder, or an empty GraphSpace value, uses DEFAULT.

1// HugeGraphServer address: "http://localhost:8080"
2// Graph Name: "hugegraph"
3HugeClient hugeClient = HugeClient.builder("http://localhost:8080", "hugegraph")
4                                //.builder("http://localhost:8080", "graphSpaceName", "hugegraph")
5                                  .configTimeout(20) // 20s timeout
6                                  // .configUser("username", "password") // set only when server auth is enabled
7                                  .build();

If the above process of creating HugeClient fails, an exception will be thrown, and the user needs to use try-catch. If successful, continue to get schema, graph and gremlin manager.

When operating through gremlin in HugeGraph-Hubble(or HugeGraph-Studio), HugeClient is not required and can be ignored.

5.1 Builder options

The builder accepts the following options. Every timeout is expressed in seconds and converted to milliseconds internally.

interfacedescriptiondefault
configUrl(String url)Server address, normally passed to builder(...) alreadyrequired
configGraph(String graph)Graph name, normally passed to builder(...) alreadyrequired
configGraphSpace(String graphSpace)GraphSpace name, a null or empty value falls back to DEFAULTDEFAULT
configUser(String username, String password)Credentials for the server, a null value is stored as an empty stringempty, no auth
configToken(String token)Token used instead of username and passwordempty
configTimeout(int seconds)Request timeout; use a positive number of seconds20
configConnectTimeout(Integer seconds)Connect timeout, left unset so that configTimeout appliesunset
configReadTimeout(Integer seconds)Read timeout, left unset so that configTimeout appliesunset
configPool(int maxConns, int maxConnsPerRoute)Connection pool sizes, passing 0 for either one restores its default4 x CPUs, 2 x CPUs
configIdleTime(int seconds)Idle connection keep-alive, must be greater than 030
configSSL(String trustStoreFile, String trustStorePassword)Truststore used for HTTPS connectionsempty
configHttpBuilder(Consumer<OkHttpClient.Builder> consumer)Callback that receives the underlying OkHttp builder for further customizationnone
graphRequired(boolean graphRequired)Whether build() rejects an empty url or graph nametrue

Current master has a unit-conversion defect in configTimeout(0): it sets 20,000 seconds instead of the default 20 seconds. Omit the call to keep the default, or use configTimeout(20) explicitly; do not use 0 to reset it.

On build(), the client reads the server API version and rejects anything outside the range [0.38, 0.81).

5.2 Operation entries

Besides schema, graph and gremlin, HugeClient exposes the following entries. The graph-scoped ones are only available when a graph name was supplied; when the client is built with an empty graph name they return null until assignGraph(graphSpace, graph) is called.

interfacereturnsscopedescription
schema()SchemaManagergraphManage PropertyKey, VertexLabel, EdgeLabel and IndexLabel
graph()GraphManagergraphAdd, query, update and delete vertices and edges, single or batch
gremlin()GremlinManagergraphRun Gremlin statements, synchronously or as an async task
cypher()CypherManagergraphRun Cypher statements, synchronously or as an async task
traverser()TraverserManagergraphRESTful traversals such as shortest path, k-out, k-neighbor and crosspoints
variables()VariablesManagergraphGet, set, list and remove graph variables
job()JobManagergraphRebuild the index of a VertexLabel, EdgeLabel or IndexLabel
task()TaskManagergraphList, get, cancel, delete and wait on async tasks
computer()ComputerManagergraphCreate, cancel, list and get computer jobs
graphs()GraphsManagergraphspaceCreate, clone, list, reload, clear and drop graphs, read and set the graph mode
graphSpace()GraphSpaceManagerserverManage GraphSpaces, see section 8
auth()AuthManagerserverManage users, groups, targets, belongs and accesses
metrics()MetricsManagerserverRead backend, system and statistics metrics
versionManager()VersionManagerserverRead the core, gremlin and API versions of the server

The client also reports what the connected server supports, so callers can branch on a capability instead of on a version string: supportsGraphSpace(), supportsCypher(), supportsGraphCreate(), supportsDefaultRole() and isServerAuthEnabled().

6 Schema

6.1 SchemaManager

SchemaManager is used to manage four kinds of schema in HugeGraph, namely PropertyKey (property type), VertexLabel (vertex type), EdgeLabel (edge type) and IndexLabel (index label). A SchemaManager object can be created for schema information definition.

The user can obtain the SchemaManager object using the following methods:

1SchemaManager schema = hugeClient.schema()

Create a schema object via gremlin in HugeGraph-Hubble:

1schema = graph.schema()

The definition process of the 4 kinds of schema is described below.

6.2 PropertyKey

6.2.1 Interface and parameter introduction

PropertyKey is used to standardize the property constraints of vertices and edges, and properties of properties are not currently supported.

The constraint information that PropertyKey allows to define includes: name, datatype, cardinality, aggregateType, writeType and userdata, which are introduced one by one below.

  • name: The name of the property, used to distinguish different PropertyKeys, PropertyKeys with the same name are not allowed.
interfaceparammust set
propertyKey(String name)namey
  • datatype: property value type, you must select an explicit setting from the following table that conforms to the specific business scenario:
interfaceJava Class
asText()String
asInt()Integer
asDate()Date
asUUID()UUID
asBoolean()Boolean
asByte()Byte
asBlob()Byte[]
asDouble()Double
asFloat()Float
asLong()Long
  • cardinality: Whether the property value is single-valued or multivalued, in the case of multivalued, it is divided into allowing-duplicate values and not-allowing-duplicate values. This item is single by default. If necessary, you can select a setting from the following table:
interfacecardinalitydescription
valueSingle()singlesingle value
valueList()listmulti-values that allow duplicate value
valueSet()setmulti-values that not allow duplicate value
  • aggregateType: How repeated writes of the same property are combined. The default is none, which keeps the last written value. The numeric options require a number datatype:
interfaceaggregateTypedescription
calcSum()sumaccumulate the written values
calcMax()maxkeep the greatest value
calcMin()minkeep the smallest value
calcOld()oldkeep the first written value and ignore updates

aggregateType(AggregateType type) sets the same thing directly, and AggregateType.NONE restores the default.

  • writeType: Whether the property belongs to the OLTP graph or to an OLAP computing result, and for OLAP whether it carries an index. The default is oltp:
writeTypedescription
OLTPordinary graph property
OLAP_COMMONOLAP property without index
OLAP_SECONDARYOLAP property with a secondary index
OLAP_RANGEOLAP property with a range index
interfacedescription
writeType(WriteType writeType)set the write type with the enum value
writeType(String name)set the write type by enum name
  • userdata: Users can add some constraints or additional information by themselves, and then check whether the incoming properties satisfy the constraints, or extract additional information when necessary:
interfacedescription
userdata(String key, Object value)The same key, the latter will cover the former
6.2.2 Create PropertyKey
1schema.propertyKey("name").asText().valueSet().ifNotExist().create()

The syntax of creating the above PropertyKey object through gremlin in HugeGraph-Hubble is exactly the same. If the user does not define the schema variable, it should be written like this:

1graph.schema().propertyKey("name").asText().valueSet().ifNotExist().create()

In the following examples, the syntax of gremlin and java is exactly the same, so we won’t repeat them.

  • ifNotExist(): Add a judgment mechanism for create, if the current PropertyKey already exists, it will not be created, otherwise the property will be created. If no ifNotExist() is added, an exception will be thrown if a property-key with the same name already exists. The same as below, and will not be repeated there.
6.2.3 Delete PropertyKey
1schema.propertyKey("name").remove()
6.2.4 Query PropertyKey
1// Get PropertyKey
2schema.getPropertyKey("name")
3
4// Get attributes of PropertyKey
5schema.getPropertyKey("name").cardinality()
6schema.getPropertyKey("name").dataType()
7schema.getPropertyKey("name").name()
8schema.getPropertyKey("name").userdata()

6.3 VertexLabel

6.3.1 Interface and parameter introduction

VertexLabel is used to define the vertex type and describe the constraint information of the vertex.

The constraint information that VertexLabel allows to define include: name, idStrategy, properties, primaryKeys, nullableKeys and ttl, which are introduced one by one below.

  • name: The name of the VertexLabel, used to distinguish different VertexLabels, VertexLabels with the same name are not allowed.
interfaceparammust set
vertexLabel(String name)namey
  • idStrategy: Each VertexLabel can choose its own ID strategy. There are currently three strategies to choose from, namely Automatic (automatically generated), Customize (user input) and PrimaryKey (primary attribute key). Among them, Automatic uses the Snowflake algorithm to generate ID, Customize requires the user to pass in the ID of string or number type, and PrimaryKey allows the user to select several properties of VertexLabel as the basis for differentiation. HugeGraph will be spliced and generated ID according to the value of the primary properties. idStrategy uses Automatic by default, but if the user does not explicitly set idStrategy and calls the primaryKeys(…) method to set the primary property, then idStrategy will automatically use PrimaryKey.
interfaceidStrategydescription
useAutomaticIdAUTOMATICgenerate id automatically by Snowflake algorithm
useCustomizeStringIdCUSTOMIZE_STRINGpassed id by user, must be string type
useCustomizeNumberIdCUSTOMIZE_NUMBERpassed id by user, must be number type
useCustomizeUuidIdCUSTOMIZE_UUIDpassed id by user, must be UUID type
usePrimaryKeyIdPRIMARY_KEYchoose some important prop as primary key to splice id
  • properties: define the properties of the vertex, the incoming parameter is the name of the PropertyKey.
interfacedescription
properties(String… properties)allow to pass multi properties
  • primaryKeys: When the user selects the ID strategy of PrimaryKey, several primary properties need to be selected from the properties of VertexLabel as the basis for differentiation;
interfacedescription
primaryKeys(String… keys)allow to choose multi prop as primaryKeys

Note that the selection of the ID strategy and the setting of primaryKeys have some mutual constraints, which cannot be called at will. The constraints are shown in the following table:

useAutomaticIduseCustomizeStringIduseCustomizeNumberIdusePrimaryKeyId
unset primaryKeysAUTOMATICCUSTOMIZE_STRINGCUSTOMIZE_NUMBERERROR
set primaryKeysERRORERRORERRORPRIMARY_KEY

The client itself only checks that the ID strategy is set once, so calling two of these methods on the same builder fails locally. The combinations above are validated by the server.

  • nullableKeys: For properties set by the properties(…) method, all of them are non-nullable by default, that is, the property must be assigned a value when creating a vertex, which may impose too strict integrity requirements on user data. In order to avoid such strong constraints, the user can set some properties to be nullable through this method, so that the properties can be unassigned when adding vertices.
interfacedescription
nullableKeys(String… properties)allow to pass multi props

Note: primaryKeys and nullableKeys cannot intersect, because a property cannot be both primary and nullable.

  • ttl: Time to live of the vertices of this label. The default is 0, which means they never expire. The client rejects a negative value. By default the countdown is relative to the moment the vertex is written; ttlStartTime instead names a date property of the label that the countdown is measured from.
interfacedescription
ttl(long ttl)set the time to live, 0 disables expiry
ttlStartTime(String property)name the date property the countdown starts from
  • enableLabelIndex: The user can specify whether to create an index for the label. If you don’t create it, you can’t globally search for the vertices and edges of the specified label. If you create it, you can search globally, like g.V().hasLabel('person'), g.E().has('label', 'person') query, but the performance will be slower when inserting data, and it will take up more storage space. This defaults to true.
interfacedescription
enableLabelIndex(boolean enable)Whether to create a label index
  • userdata: Users can add some constraints or additional information by themselves, and then check whether the incoming properties meet the constraints, or extract additional information when necessary.
interfacedescription
userdata(String key, Object value)The same key, the latter will cover the former
6.3.2 Create VertexLabel
 1// Use Automatic Id strategy
 2schema.vertexLabel("person").properties("name", "age").ifNotExist().create();
 3schema.vertexLabel("person").useAutomaticId().properties("name", "age").ifNotExist().create();
 4
 5// Use Customize_String Id strategy
 6schema.vertexLabel("person").useCustomizeStringId().properties("name", "age").ifNotExist().create();
 7// Use Customize_Number Id strategy
 8schema.vertexLabel("person").useCustomizeNumberId().properties("name", "age").ifNotExist().create();
 9// Use Customize_Uuid Id strategy
10schema.vertexLabel("person").useCustomizeUuidId().properties("name", "age").ifNotExist().create();
11
12// Use PrimaryKey Id strategy
13schema.vertexLabel("person").properties("name", "age").primaryKeys("name").ifNotExist().create();
14schema.vertexLabel("person").usePrimaryKeyId().properties("name", "age").primaryKeys("name").ifNotExist().create();
6.3.3 Update VertexLabel

VertexLabel can append constraints, but only properties and nullableKeys, and the appended properties must also be added to the nullableKeys collection.

1schema.vertexLabel("person").properties("price").nullableKeys("price").append();
6.3.4 Delete VertexLabel
1schema.vertexLabel("person").remove();
6.3.5 Query VertexLabel
 1// Get VertexLabel
 2schema.getVertexLabel("name")
 3
 4// Get attributes of VertexLabel
 5schema.getVertexLabel("person").idStrategy()
 6schema.getVertexLabel("person").primaryKeys()
 7schema.getVertexLabel("person").name()
 8schema.getVertexLabel("person").properties()
 9schema.getVertexLabel("person").nullableKeys()
10schema.getVertexLabel("person").userdata()
11schema.getVertexLabel("person").ttl()
12schema.getVertexLabel("person").ttlStartTime()

6.4 EdgeLabel

6.4.1 Interface and parameter introduction

EdgeLabel is used to define the edge type and describe the constraint information of the edge.

The constraint information that EdgeLabel allows to define include: name, sourceLabel, targetLabel, frequency, properties, sortKeys, nullableKeys and ttl, which are introduced one by one below.

  • name: The name of the EdgeLabel, used to distinguish different EdgeLabels, EdgeLabels with the same name are not allowed.
interfaceparammust set
edgeLabel(String name)namey
  • sourceLabel and targetLabel: The names of the source and the target vertex type of the edge link. Setting both is the same as declaring one link pair.

  • link: An EdgeLabel holds a set of source and target pairs, so link(...) can be called more than once to let the same edge type connect several pairs of vertex types. Once a pair has been added this way, sourceLabel(...) and targetLabel(...) are rejected, and the sourceLabel() and targetLabel() getters only work on a label that has exactly one pair. Use links() to read them all.

interfaceparammust set
link(String sourceLabel, String targetLabel)sourceLabel, targetLabely, or set the two below
sourceLabel(String label)labely, unless link() was used
targetLabel(String label)labely, unless link() was used
  • frequency: Indicating the number of times a relationship occurs between two specific vertices, which can be single (single) or multiple (frequency), the default is single.
interfacefrequencydescription
singleTime()singlea relationship can only occur once
multiTimes()multiplea relationship can occur many times
  • properties: Define the properties of the edge.
interfacedescription
properties(String… properties)allow to pass multi props
  • sortKeys: When the frequency of EdgeLabel is multiple, some properties are needed to distinguish the multiple relationships, so sortKeys (sorted keys) is introduced;
interfacedescription
sortKeys(String… keys)allow to choose multi prop as sortKeys
  • nullableKeys: Consistent with the concept of nullableKeys in vertices.

Note: sortKeys and nullableKeys also cannot intersect.

  • ttl: Consistent with the concept of ttl in vertices, with the same ttl(long ttl) and ttlStartTime(String property) methods and the same default of 0.

  • edge label type: An EdgeLabel is normal by default. It can instead be declared as the parent of a family of edge labels, as a child of such a parent, or as a general label:

interfaceedgeLabelTypedescription
asBase()PARENTdeclare the label as a parent label
withBase(String parentLabel)SUBdeclare the label as a child of ‘parentLabel’
asGeneral()GENERALdeclare the label as a general label
  • enableLabelIndex: It is consistent with the concept of enableLabelIndex in the vertex.

  • userdata: Users can add some constraints or additional information by themselves, and then check whether the incoming properties meet the constraints, or extract additional information when necessary.

interfacedescription
userdata(String key, Object value)The same key, the latter will cover the former
6.4.2 Create EdgeLabel
1schema.edgeLabel("knows").link("person", "person").properties("date").ifNotExist().create();
2schema.edgeLabel("created").multiTimes().link("person", "software").properties("date").sortKeys("date").ifNotExist().create();
6.4.3 Update EdgeLabel
1schema.edgeLabel("knows").properties("price").nullableKeys("price").append();
6.4.4 Delete EdgeLabel
1schema.edgeLabel("knows").remove();
6.4.5 Query EdgeLabel
 1// Get EdgeLabel
 2schema.getEdgeLabel("knows")
 3
 4// Get attributes of EdgeLabel
 5schema.getEdgeLabel("knows").frequency()
 6schema.getEdgeLabel("knows").sourceLabel()
 7schema.getEdgeLabel("knows").targetLabel()
 8schema.getEdgeLabel("knows").sortKeys()
 9schema.getEdgeLabel("knows").name()
10schema.getEdgeLabel("knows").properties()
11schema.getEdgeLabel("knows").nullableKeys()
12schema.getEdgeLabel("knows").userdata()
13schema.getEdgeLabel("knows").ttl()
14schema.getEdgeLabel("knows").ttlStartTime()
15schema.getEdgeLabel("knows").edgeLabelType()
16// All the source and target pairs, safe to call when there is more than one
17schema.getEdgeLabel("knows").links()

6.5 IndexLabel

6.5.1 Interface and parameter introduction

IndexLabel is used to define the index type and describe the constraint information of the index, mainly for the convenience of query.

The constraint information that IndexLabel allows to define include: name, baseType, baseValue, indexFields, indexType, which are introduced one by one below.

  • name: The name of the IndexLabel, used to distinguish different IndexLabels, IndexLabels with the same name are not allowed.
interfaceparammust set
indexLabel(String name)namey
  • baseType: Indicates whether to index VertexLabel or EdgeLabel, used in conjunction with the baseValue below.

  • baseValue: Specifies the name of the VertexLabel or EdgeLabel to be indexed.

interfaceparamdescription
onV(String baseValue)baseValuebuild index for VertexLabel: ‘baseValue’
onE(String baseValue)baseValuebuild index for EdgeLabel: ‘baseValue’
  • indexFields: on which fields to index, it can be a joint index for multiple columns.
interfaceparamdescription
by(String… fields)filesallow to build index for multi fields for secondary index
  • indexType: There are currently five types of indexes established, namely Secondary, Range, Search, Shard and Unique.
    • Secondary Index supports exact matching secondary index, allow to build joint index, joint index supports index prefix search
      • Single Property Secondary Index, support equality query, for example: the secondary index of the city property of the person vertex, you can use g.V().has("city", "Beijing") to query all the vertices with “city attribute value is Beijing”
      • Joint Secondary Index, supports prefix query and equality query, such as: joint index of city and street properties of person vertex, you can use g.V().has("city", "Beijing").has('street', 'Zhongguancun street ') to query all vertices of “city property value is Beijing and street property value is ZhongGuanCun”, or g.V().has("city", "Beijing") to query all vertices of “city property value is Beijing”.

      The query of Secondary Index is based on the query condition of “yes” or “equal”, and does not support “partial matching”.

    • Range Index supports for range queries of numeric types
      • Must be a single number or date attribute, for example: the range index of the age property of the person vertex, you can use g.V().has("age", P.gt(18)) to query the vertices with “age property value greater than 18” . In addition to P.gt(), also supports P.gte(), P.lte(), P.lt(), P.eq(), P.between() , P.inside() and P.outside() etc.
    • Search Index supports full-text search
      • It must be a single text property, such as: full-text index of the address property of the person vertex, you can use g.V().has("address", Text.contains('building') to query all vertices whose “address property contains a ‘building’”

      The query of the Search Index is based on the query condition of “is” or “contains”.

    • Shard Index supports prefix matching + numeric range query
      • The shard index of N properties supports range queries with equal prefixes. For example, the shard index of the city and age properties of the person vertex can use g.V().has("city", "Beijing").has ("age", P.between(18, 30))Query “city property is Beijing and all vertices whose age is greater than or equal to 18 and less than 30”.
      • When all N properties are text properties in a Shard Index, it is equivalent to Secondary Index.
      • When there is only one single number or date property in a Shard Index, it is equivalent to the Range Index.

      Shard Index can have any number or date property, but at most one range search condition can be provided when querying, and the prefix properties of the Shard Search conditions must be “equals”.

    • Unique Index supports properties uniqueness constraints, that is, the value of properties can be limited to not repeat, and joint indexing is allowed, but querying is not supported now
      • The unique index of single or multiple properties cannot be used for query, only the value of the property can be limited, and an error will be reported when there is a duplicate value.
interfaceindexTypedescription
secondary()Secondarysupport prefix search
range()Rangesupport range(numeric or date type) search
search()Searchsupport full text search
shard()Shardsupport prefix + range(numeric or date type) search
unique()Uniquesupport unique props value, not support search
6.5.2 Create IndexLabel

These examples assume a person vertex label with name and age, and a created edge label with date. First add the indexed properties below; id is a business property, separate from the internal vertex ID.

 1schema.propertyKey("lived").asText().ifNotExist().create();
 2schema.propertyKey("city").asText().ifNotExist().create();
 3schema.propertyKey("id").asInt().ifNotExist().create();
 4schema.vertexLabel("person").properties("lived", "city", "id")
 5      .nullableKeys("lived", "city", "id").append();
 6
 7schema.indexLabel("personByAge").onV("person").by("age").range().ifNotExist().create();
 8schema.indexLabel("createdByDate").onE("created").by("date").secondary().ifNotExist().create();
 9schema.indexLabel("personByLived").onV("person").by("lived").search().ifNotExist().create();
10schema.indexLabel("personByCityAndAge").onV("person").by("city", "age").shard().ifNotExist().create();
11schema.indexLabel("personById").onV("person").by("id").unique().ifNotExist().create();
6.5.3 Delete IndexLabel
1schema.indexLabel("personByAge").remove()
6.5.4 Query IndexLabel
1// Get IndexLabel
2schema.getIndexLabel("personByAge")
3
4// Get attributes of IndexLabel
5schema.getIndexLabel("personByAge").baseType()
6schema.getIndexLabel("personByAge").baseValue()
7schema.getIndexLabel("personByAge").indexFields()
8schema.getIndexLabel("personByAge").indexType()
9schema.getIndexLabel("personByAge").name()

7 Graph

7.1 Vertex

Vertices are the most basic elements of a graph, and there can be many vertices in a graph. Here is an example of adding vertices:

1Vertex marko = graph.addVertex(T.LABEL, "person", "name", "marko", "age", 29);
2Vertex lop = graph.addVertex(T.LABEL, "software", "name", "lop", "lang", "java", "price", 328);
  • The key to adding vertices is the vertex properties. The number of parameters of the vertex adding function must be an even number and satisfy the order of key1 -> val1, key2 -> val2 ..., and the order between key-value pairs is free .
  • The parameter must contain a special key-value pair, namely T.LABEL -> "val", which is used to define the category of the vertex, so that the program can obtain the schema definition of the VertexLabel from the cache or backend, and then do subsequent constraint checks. The label in the example is defined as person. T.LABEL is the constant "label", so the plain string works just as well.
  • If the vertex type’s ID policy is AUTOMATIC, users are not allowed to pass in id key-value pairs.
  • If the ID policy of the vertex type is CUSTOMIZE_STRING, the user needs to pass in the value of the id of the String type. The key-value pair is like: T.ID, "123456".
  • If the ID policy of the vertex type is CUSTOMIZE_NUMBER, the user needs to pass in the value of the id of the Number type. The key-value pair is like: T.ID, 123456.
  • If the ID policy of the vertex type is PRIMARY_KEY, the parameters must also contain the name and value of the properties corresponding to the primaryKeys, if not set an exception will be thrown. For example, the primaryKeys of person is name, in the example, the value of name is set to marko.
  • For properties that are not nullableKeys, a value must be assigned.
  • The remaining parameters are the settings of other properties of the vertex, but they are not required.
  • After calling the addVertex method, the vertices are inserted into the backend storage system immediately.

7.2 Edge

After added vertices, edges are also needed to form a complete graph. Here is an example of adding edges:

1Edge knows1 = marko.addEdge("knows", vadas, "city", "Beijing");
  • The function addEdge() of the (source) vertex is to add an edge(relationship) between itself and another vertex. The first parameter of the function is the label of the edge, and the second parameter is the target vertex. The position and order of these two parameters are fixed. The subsequent parameters are the order of key1 -> val1, key2 -> val2 ..., set the properties of the edge, and the key-value pair order is free.
  • The source and target vertices must conform to the definitions of source-label and target label in EdgeLabel, and cannot be added arbitrarily.
  • For properties that are not nullableKeys, a value must be assigned.

Note: When frequency is multiple, the value of the property type corresponding to sortKeys must be set.

8 GraphSpace

The client can manage multiple GraphSpaces in one physical deployment, and each GraphSpace can contain multiple graphs. When no GraphSpace is specified, it uses DEFAULT.

GraphSpaces need a server of core version 1.7.0 or later. Against an older server the client falls back to a legacy profile, and hugeClient.supportsGraphSpace() returns false.

8.1 Create GraphSpace

 1GraphSpaceManager spaceManager = hugeClient.graphSpace();
 2
 3// Define GraphSpace configuration
 4GraphSpace graphSpace = new GraphSpace();
 5graphSpace.setName("myGraphSpace");
 6graphSpace.setDescription("Business data graph space");
 7graphSpace.setMaxGraphNumber(10);  // Maximum number of graphs
 8graphSpace.setMaxRoleNumber(100);  // Maximum number of roles
 9
10// Create GraphSpace
11spaceManager.createGraphSpace(graphSpace);

8.2 GraphSpace Interface Summary

CategoryInterfaceDescription
Manager - QuerylistGraphSpace()Get all GraphSpace names
listProfile() / listProfile(String prefix)Get GraphSpace profiles
getGraphSpace(String name)Get the specified GraphSpace
getDefault()Get the default GraphSpace
Manager - Create/UpdatecreateGraphSpace(GraphSpace)Create a GraphSpace
updateGraphSpace(GraphSpace)Update configuration
setDefault(String name)Set the default GraphSpace
Manager - DeletedeleteGraphSpace(String name)Delete the specified GraphSpace
Manager - Default rolesetDefaultRole(String name, String user, String role)Grant a default role, optionally scoped to a graph with a fourth argument
checkDefaultRole(String name, String user, String role)Check a default role, optionally scoped to a graph with a fourth argument
deleteDefaultRole(String name, String user, String role)Revoke a default role, optionally scoped to a graph with a fourth argument
GraphSpace - PropertiesgetName() / getNickname() / getDescription()Get name / nickname / description
getGraphNumberUsed() / getRoleNumberUsed()Get the number of graphs / roles in use
getCpuUsed() / getMemoryUsed() / getStorageUsed()Get the resources in use
getCreateTime() / getUpdateTime()Get the creation / update time
GraphSpace - ConfigurationsetDescription(String) / setNickname(String)Set description / nickname
setMaxGraphNumber(int) / setMaxRoleNumber(int)Set the maximum number of graphs / roles
setCpuLimit(int) / setMemoryLimit(int) / setStorageLimit(int)Set the resource quotas
setConfigs(Map<String, Object>)Set extra configuration entries

2 - HugeGraph Python Client Quick Start

hugegraph-python-client is the Python SDK for Apache HugeGraph. It provides schema management, graph data manipulation, Gremlin execution, real-time traversals, and asynchronous whole-graph computing. HugeGraph-LLM and HugeGraph-ML also use this client for database operations.

The client source code is hosted in the hugegraph-ai repository under hugegraph-python-client/. The import package name is pyhugegraph.

Requirements

  • Python >= 3.12 (Python 3.12–3.14 supported).
  • HugeGraph Server 1.5.0 or later (Server 1.7+ recommends GraphSpace mode; 1.5/1.6 uses legacy routing).
  • pip or uv package manager.

Runtime dependencies include decorator, requests, urllib3, and rich.

Installation

The client provides two installation methods depending on whether you require the stable PyPI release or development features from the master branch.

Note

Version & Feature Boundary: The published PyPI release (hugegraph-python 1.7.x) provides the baseline client supporting CamelCase methods with legacy snake_case aliases. The modern features demonstrated in this guide — including native snake_case APIs, client.olap() whole-graph algorithms, client.task().wait(), client.close(), and updated traverser signatures — align with the master development branch. For testing these features, install the client from source.

PyPI (Stable 1.7.x)
1pip install hugegraph-python
2# Or using uv:
3# uv pip install hugegraph-python
Source (Master)
1git clone https://github.com/apache/hugegraph-ai.git
2cd hugegraph-ai/hugegraph-python-client
3pip install -e .
Workspace (uv)
1git clone https://github.com/apache/hugegraph-ai.git
2cd hugegraph-ai
3uv sync --extra python-client
4source .venv/bin/activate

Connect and Write Data

 1from pyhugegraph.client import PyHugeClient
 2
 3client = PyHugeClient(
 4    url="http://127.0.0.1:8080",
 5    graph="hugegraph",
 6    user="admin",
 7    pwd="admin",
 8    graphspace=None,
 9)
10
11schema = client.schema()
12schema.property_key("name").as_text().if_not_exist().create()
13schema.property_key("birthDate").as_text().if_not_exist().create()
14schema.vertex_label("Person").properties("name", "birthDate") \
15      .use_primary_key_id().primary_keys("name").if_not_exist().create()
16schema.vertex_label("Movie").properties("name") \
17      .use_primary_key_id().primary_keys("name").if_not_exist().create()
18schema.edge_label("ActedIn").source_label("Person").target_label("Movie") \
19      .if_not_exist().create()
20
21graph = client.graph()
22person = graph.add_vertex(
23    "Person", {"name": "Al Pacino", "birthDate": "1940-04-25"}
24)
25movie = graph.add_vertex("Movie", {"name": "The Godfather"})
26edge = graph.add_edge("ActedIn", person.id, movie.id, {})
27
28print(graph.get_vertex_by_id(person.id))
29print(graph.get_edge_by_id(edge.id))
30
31client.close()

Client Parameters

PyHugeClient(url, graph, user, pwd, graphspace=None, timeout=None, *, token=None)

ParameterTypeDefaultDescription
urlstrrequiredBase URL of HugeGraph Server. Prepends http:// if no scheme is provided (e.g. 127.0.0.1:8080).
graphstrrequiredTarget graph name. Second positional parameter.
userstrrequiredUsername sent via HTTP Basic Auth.
pwdstrrequiredPassword sent via HTTP Basic Auth.
graphspacestr or NoneNoneGraphSpace name. When None, resolved automatically via version probe.
timeoutfloat, tuple[float, float] or NoneNone(connect, read) timeouts in seconds, or a single float for both. Defaults to (0.5, 15.0).
tokenstr or NoneNoneExplicit Bearer token; overrides Basic Auth when provided.

Idempotent requests retry on 500, 502, and 504 responses up to three times with a 0.1 backoff factor. Task waiting automatically manages its polling budget without extra HTTP retries.

Server Version and GraphSpace

The client resolves GraphSpace routing at initialization:

  • When an explicit graphspace string is passed, GraphSpace routing is activated immediately.
  • When graphspace=None, the client checks GET {url}/versions to determine the server core version.
  • HugeGraph Server 1.7+ defaults to GraphSpace DEFAULT.
  • HugeGraph Server 1.5 / 1.6 uses legacy non-GraphSpace routing.
  • Servers prior to 1.5.0 are not supported and raise RuntimeError.
  • If the version probe fails and no GraphSpace was specified, client initialization raises an error rather than assuming an invalid route layout.

The routing mode determines request path prefixes: /graphspaces/<graphspace>/graphs/<graph>/... when GraphSpace is enabled, or /graphs/<graph>/... when disabled.

Client Accessors

PyHugeClient maintains a shared HTTP session across all accessors. Accessors cache their managers lazily:

AccessorManagerPurpose
client.schema()SchemaManagerProperty keys, vertex labels, edge labels, index labels
client.graph()GraphManagerVertex and edge CRUD, batch ingestion, paging
client.gremlin()GremlinManagerGremlin script execution
client.traverser()TraverserManagerReal-time graph traversals and paths (OLTP)
client.rank()RankManagerReal-time personalized recommendation ranking (OLTP)
client.olap()OlapManagerAsynchronous whole-graph computing algorithms (OLAP)
client.task()TaskManagerAsynchronous task status, polling, cancellation, and deletion
client.graphs()GraphsManagerGraph metadata, configuration, graph list, data clearing
client.graphspaces()GraphspaceManagerMulti-graphspace management
client.schema_templates()SchemaTemplateManagerReusable schema templates
client.auth()AuthManagerUsers, groups, targets, belongs, and access privileges
client.variable()VariableManagerGraph-level persistent key-value variables
client.metrics()MetricsManagerServer monitoring metrics
client.version()VersionManagerServer component versions
client.rest()RestClientDirect REST API calls and extended operations

Common Operations

Build the Schema

Schema builders are fluent. Call create() to apply, or use append(), eliminate(), and remove() to update existing definitions:

 1schema = client.schema()
 2
 3# Property keys: as_text / as_int / as_long / as_float / as_double / as_bool / as_date
 4# Cardinality: value_single / value_list / value_set
 5schema.property_key("age").as_int().value_single().if_not_exist().create()
 6
 7# Vertex labels: use_automatic_id / use_customize_string_id / use_primary_key_id
 8schema.vertex_label("person").properties("name", "age", "city") \
 9      .primary_keys("name").nullable_keys("city").if_not_exist().create()
10
11# Edge labels: link() specifies source and target vertex labels
12schema.edge_label("knows").link("person", "person").multi_times() \
13      .properties("date", "city").sort_keys("date").nullable_keys("city") \
14      .if_not_exist().create()
15
16# Index labels: on_v / on_e, secondary / range / search / shard / unique
17schema.index_label("personByCity").on_v("person").by("city") \
18      .secondary().if_not_exist().create()

Query the Schema

 1schema = client.schema()
 2print(schema.get_schema())            # Returns whole schema definition dictionary
 3print(schema.get_property_keys())
 4print(schema.get_vertex_labels())
 5print(schema.get_edge_labels())
 6print(schema.get_index_labels())
 7
 8# Query single definitions by name
 9print(schema.get_property_key("name"))
10print(schema.get_vertex_label("person"))
11print(schema.get_edge_label("knows"))
12print(schema.get_index_label("personByCity"))
13
14# Edge relations formatted as "Person--ActedIn-->Movie"
15print(schema.get_relations())

Read, Update, and Delete Graph Data

The graph API accepts property dictionaries:

1graph = client.graph()
2graph.append_vertex(person.id, {"birthDate": "1940-04-25"})    # Append properties
3graph.eliminate_vertex(person.id, {"birthDate": "1940-04-25"}) # Drop properties
4graph.append_edge(edge.id, {"city": "Beijing"})
5graph.eliminate_edge(edge.id, {"city": "Beijing"})
6graph.remove_edge_by_id(edge.id)
7graph.remove_vertex_by_id(person.id)

add_vertex returns a VertexData instance containing id, label, type, and properties. add_edge returns an EdgeData instance containing id, label, type, outV, outVLabel, inV, inVLabel, and properties.

Vertex IDs passed to the client may be strings, integers, or uuid.UUID objects. Booleans are rejected, and integer values must fall within the 64-bit signed range.

Batch Writes

add_vertices accepts (label, properties) tuples, and add_edges accepts (label, out_id, in_id, out_label, in_label, properties) tuples:

1graph = client.graph()
2vertices = graph.add_vertices([
3    ("person", {"name": "Alice", "age": 20}),
4    ("person", {"name": "Bob", "age": 23}),
5])
6edges = graph.add_edges([
7    ("knows", vertices[0].id, vertices[1].id, "person", "person", {"date": "2012-01-10"}),
8])

Paging and Conditional Queries

 1graph = client.graph()
 2
 3# Paging with next_page token
 4vertices, next_page = graph.get_vertex_by_page("person", limit=10)
 5vertices, next_page = graph.get_vertex_by_page("person", limit=10, page=next_page)
 6
 7# Server-side property predicates
 8older = graph.get_vertex_by_condition("person", properties={"age": "P.gt(29)"})
 9
10# Edge paging. When vertex_id is provided, direction is required
11edges, next_page = graph.get_edge_by_page(label="knows", limit=10)
12edges, next_page = graph.get_edge_by_page(vertex_id=person.id, direction="OUT", limit=10)
13
14# Batch lookup by ID list
15graph.get_vertices_by_id([v1.id, v2.id])
16graph.get_edges_by_id([e1.id, e2.id])

Execute Gremlin

1gremlin = client.gremlin()
2result = gremlin.exec("g.V().limit(5)")
3print(result)

exec() automatically binds the graph and g aliases according to the target graph name and resolved GraphSpace.

Traverse the Graph (OLTP)

client.traverser() wraps the server’s real-time traverser endpoints for neighborhood, path, and similarity queries:

 1traverser = client.traverser()
 2
 3traverser.k_out(marko_id, 2)
 4traverser.k_neighbor(marko_id, 2)
 5traverser.same_neighbors(marko_id, josh_id)
 6traverser.jaccard_similarity(marko_id, josh_id)
 7traverser.shortest_path(marko_id, ripple_id, 3)
 8traverser.all_shortest_paths(marko_id, ripple_id, 3)
 9traverser.weighted_shortest_path(marko_id, ripple_id, "weight", 3)
10traverser.single_source_shortest_path(marko_id, 2)
11traverser.multi_node_shortest_path([marko_id, josh_id], max_depth=2)
12traverser.paths(marko_id, josh_id, 2)
13traverser.crosspoints(marko_id, josh_id, 2)
14traverser.rings(marko_id, 3)
15traverser.rays(marko_id, 2)
16traverser.vertices(marko_id)
17traverser.edges(edge_id)

The POST-based variants accept complex request bodies: advanced_paths, customized_paths, template_paths, customized_crosspoints, and fusiform_similarity.

OLAP Whole-Graph Computing

For heavy full-graph algorithms (such as PageRank, Louvain, or Centrality), use client.olap(). These jobs run asynchronously on the server and are tracked through task IDs:

 1# 1. Submit an asynchronous computation task
 2receipt = client.olap().count_vertex()
 3task_id = receipt["task_id"]
 4
 5# 2. Wait for completion and retrieve results
 6task = client.task().wait(task_id, timeout=300, poll_interval=1)
 7result = client.task().result(task)
 8print(result)
 9
10# Or combine submit, wait, and decode in one step:
11result = client.olap().run("count_vertex", timeout=60)

Supported OLAP Algorithms

The server provides 17 unique whole-graph algorithm endpoints:

CategoryAlgorithm Names
Statisticscount_edge, count_vertex, subgraph_stat, triangle_count, rings
Centralitybetweenness_centrality, closeness_centrality, degree_centrality, eigenvector_centrality, stress_centrality
Community & Clusteringcluster_coefficient, k_core, louvain, lpa, weak_connected_component
Ranking & Similaritypage_rank, fusiform_similarity
Tip

Algorithms like page_rank write calculated rank properties back to the graph. For graphs requiring strict schema definitions, declare a nullable DOUBLE property named r_rank on participating vertex labels prior to execution.

Task Lifecycle Management

The TaskManager provides control over asynchronous jobs:

 1task = client.task()
 2
 3# List recent tasks
 4task.list_tasks(status="success", limit=10)
 5
 6# Poll and wait for a task to complete
 7record = task.wait(task_id, timeout=300, poll_interval=1)
 8
 9# Decode task results (parses JSON response once)
10result = task.result(record)
11
12# Cancel or delete tasks
13task.cancel_task(task_id)
14task.delete_task(task_id, force=False)
  • wait(id, timeout=300, poll_interval=1) polls status without fetching the full result payload on every tick.
  • TaskTimeoutError indicates client-side polling timed out; the background job on the server continues running.
  • To terminate a running server task, invoke cancel_task(id) explicitly.

Graph Variables, Metrics, and Metadata

 1# Graph variables
 2variable = client.variable()
 3variable.set("owner", "mary")
 4print(variable.get("owner"))
 5print(variable.all())
 6variable.remove("owner")
 7
 8# Server metrics
 9metrics = client.metrics()
10metrics.get_all_basic_metrics()
11metrics.get_system_metrics()
12metrics.get_backend_metrics()
13
14# Graph management and version
15graphs = client.graphs()
16print(graphs.list())
17print(client.version().version())

Authentication and Authorization

PyHugeClient supports both HTTP Basic Auth and Bearer Token authentication:

1# Switch session to Bearer Token authentication
2client.use_token("your-jwt-token")
3
4# Revert back to HTTP Basic Auth credentials
5client.use_token(None)

AuthManager manages users, groups, targets, belongs, and access privileges:

 1auth = client.auth()
 2
 3user = auth.create_user("test_user", "password")
 4auth.modify_user(user["id"], user_email="hugegraph@apache.org")
 5auth.get_user(user["id"])
 6auth.list_users(limit=10)
 7
 8group = auth.create_group("test_group", "read only")
 9auth.modify_group(group["id"], group_description="updated")
10auth.list_groups()
11
12target = auth.create_target("target1", "hugegraph", "127.0.0.1:8080", [])
13auth.update_target(target["id"], "target1", "hugegraph", "127.0.0.1:8080", [])
14auth.list_targets()
15
16belong = auth.create_belong(user["id"], group["id"])
17auth.update_belong(belong["id"], "description")
18auth.list_belongs()
19
20access = auth.grant_accesses(group["id"], target["id"], "READ")
21auth.modify_accesses(access["id"], "description")
22auth.list_accesses()
23
24# Clean up in reverse dependency order
25auth.revoke_accesses(access["id"])
26auth.delete_belong(belong["id"])
27auth.delete_target(target["id"])
28auth.delete_group(group["id"])
29auth.delete_user(user["id"])

Method Naming and Migration

  • Preferred style: New code should use snake_case methods (add_vertex, property_key, etc.).
  • Backward compatibility: Existing public CamelCase methods (addVertex, propertyKey, etc.) remain supported as direct aliases.
  • Client lifecycle: Use client.close() to release connection pool resources rather than closing individual managers.
  • Return contracts:
    • Legacy convenience helpers get_all_graphs(), get_version(), and get_graph_info() retain JSON strings for backwards compatibility.
    • Modern accessors client.graphs().list(), client.version().version(), and client.graphs().get(graph_name) return parsed Python dictionaries.
    • Weighted and single-source shortest path methods no longer accept max_depth (unsupported by the server endpoint); use capacity, max_degree, and skip_degree controls instead.

Direct REST API Reference

For raw endpoint interactions, batch operations, or capabilities not wrapped by high-level managers, client.rest() exposes the full REST surface:

1rest = client.rest()
2print(rest.vertex.list(label="person", offset=0, limit=20))
3print(rest.task.list(status="success", page="", limit=20))

The table below lists all 194 supported operations aligned with the server contract:

Python REST entryMethodPathQuery parameters
rest.access.create()POST/graphspaces/{graphspace}/auth/accesses—
rest.access.delete()DELETE/graphspaces/{graphspace}/auth/accesses/{id}—
rest.access.get()GET/graphspaces/{graphspace}/auth/accesses/{id}—
rest.access.list()GET/graphspaces/{graphspace}/auth/accessesgroup, target, limit
rest.access.update()PUT/graphspaces/{graphspace}/auth/accesses/{id}—
rest.adamic_adar.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/adamicadarvertex, other, direction, label, max_degree, limit
rest.algorithm.post()POST/graphspaces/{graphspace}/graphs/{graph}/jobs/algorithm/{name}—
rest.all_shortest_paths.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/allshortestpathssource, target, direction, label, max_depth, max_degree, skip_degree, with_vertex, with_edge, capacity
rest.arthas.start_arthas()PUT/arthas—
rest.belong.create()POST/graphspaces/{graphspace}/auth/belongs—
rest.belong.delete()DELETE/graphspaces/{graphspace}/auth/belongs/{id}—
rest.belong.get()GET/graphspaces/{graphspace}/auth/belongs/{id}—
rest.belong.list()GET/graphspaces/{graphspace}/auth/belongsuser, group, limit
rest.belong.update()PUT/graphspaces/{graphspace}/auth/belongs/{id}—
rest.computer.post()POST/graphspaces/{graphspace}/graphs/{graph}/jobs/computer/{name}—
rest.count.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/count—
rest.crosspoints.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/crosspointssource, target, direction, label, max_depth, max_degree, capacity, limit
rest.customized_crosspoints.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/customizedcrosspoints—
rest.customized_paths.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/customizedpaths—
rest.cypher.post()POST/graphspaces/{graphspace}/graphs/{graph}/cypher—
rest.cypher.query()GET/graphspaces/{graphspace}/graphs/{graph}/cyphercypher
rest.edge.create()POST/graphspaces/{graphspace}/graphs/{graph}/graph/edges—
rest.edge.create_batch()POST/graphspaces/{graphspace}/graphs/{graph}/graph/edges/batchcheck_vertex
rest.edge.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/graph/edges/{id}label
rest.edge.get()GET/graphspaces/{graphspace}/graphs/{graph}/graph/edges/{id}—
rest.edge.list()GET/graphspaces/{graphspace}/graphs/{graph}/graph/edgesvertex_id, direction, label, properties, keep_start_p, offset, page, limit
rest.edge.update_batch()PUT/graphspaces/{graphspace}/graphs/{graph}/graph/edges/batch—
rest.edge.update_by_id()PUT/graphspaces/{graphspace}/graphs/{graph}/graph/edges/{id}action
rest.edge_existence.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/edgeexistsource, target, label, sort_values, limit
rest.edge_label.create()POST/graphspaces/{graphspace}/graphs/{graph}/schema/edgelabels—
rest.edge_label.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/schema/edgelabels/{name}—
rest.edge_label.get()GET/graphspaces/{graphspace}/graphs/{graph}/schema/edgelabels/{name}—
rest.edge_label.list()GET/graphspaces/{graphspace}/graphs/{graph}/schema/edgelabelsnames
rest.edge_label.update()PUT/graphspaces/{graphspace}/graphs/{graph}/schema/edgelabels/{name}action
rest.edges.list()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/edgesids
rest.edges.scan()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/edges/scanstart, end, page, page_limit
rest.edges.shards()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/edges/shardssplit_size
rest.exception_trace.get()GET/exception/trace—
rest.exception_trace.trace()PUT/exception/trace—
rest.fusiform_similarity.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/fusiformsimilarity—
rest.graph_space.check_default_role()GET/graphspaces/{graphspace}/roleuser, role, graph
rest.graph_space.create()POST/graphspaces—
rest.graph_space.delete()DELETE/graphspaces/{name}—
rest.graph_space.delete_default_role()DELETE/graphspaces/{graphspace}/roleuser, role, graph
rest.graph_space.get()GET/graphspaces/{graphspace}—
rest.graph_space.list()GET/graphspaces—
rest.graph_space.list_profile()GET/graphspaces/profileprefix
rest.graph_space.manage()PUT/graphspaces/{name}—
rest.graph_space.set_default_role()POST/graphspaces/{graphspace}/role—
rest.graph_space_group.create()POST/graphspaces/{graphspace}/auth/groups—
rest.graph_space_group.delete()DELETE/graphspaces/{graphspace}/auth/groups/{id}—
rest.graph_space_group.get()GET/graphspaces/{graphspace}/auth/groups/{id}—
rest.graph_space_group.list()GET/graphspaces/{graphspace}/auth/groupslimit
rest.graph_space_group.update()PUT/graphspaces/{graphspace}/auth/groups/{id}—
rest.graphs.clear()DELETE/graphspaces/{graphspace}/graphs/{name}/clearconfirm_message
rest.graphs.clone_schema()POST/graphspaces/{graphspace}/graphs/{name}/schema-clonesource
rest.graphs.compact()PUT/graphspaces/{graphspace}/graphs/{name}/compact—
rest.graphs.create()POST/graphspaces/{graphspace}/graphs/{name}clone_graph_name
rest.graphs.create_by_text()POST/graphspaces/{graphspace}/graphs/{name}clone_graph_name
rest.graphs.create_snapshot()PUT/graphspaces/{graphspace}/graphs/{name}/snapshot_create—
rest.graphs.drop()DELETE/graphspaces/{graphspace}/graphs/{name}confirm_message
rest.graphs.get()GET/graphspaces/{graphspace}/graphs/{name}—
rest.graphs.get_conf()GET/graphspaces/{graphspace}/graphs/{name}/conf—
rest.graphs.get_default()GET/graphspaces/{graphspace}/graphs/default—
rest.graphs.graph_read_mode_get()GET/graphspaces/{graphspace}/graphs/{name}/graph_read_mode—
rest.graphs.graph_read_mode_set()PUT/graphspaces/{graphspace}/graphs/{name}/graph_read_mode—
rest.graphs.list()GET/graphspaces/{graphspace}/graphs—
rest.graphs.list_profile()GET/graphspaces/{graphspace}/graphs/profileprefix
rest.graphs.loading_mode_get()GET/graphspaces/{graphspace}/graphs/{name}/mode/owners—
rest.graphs.loading_mode_set()PUT/graphspaces/{graphspace}/graphs/{name}/mode/owners—
rest.graphs.manage()PUT/graphspaces/{graphspace}/graphs/{name}—
rest.graphs.mode_get()GET/graphspaces/{graphspace}/graphs/{name}/mode—
rest.graphs.mode_set()PUT/graphspaces/{graphspace}/graphs/{name}/mode—
rest.graphs.reload()PUT/graphspaces/{graphspace}/graphs/manage—
rest.graphs.resume_snapshot()PUT/graphspaces/{graphspace}/graphs/{name}/snapshot_resume—
rest.graphs.set_default()POST/graphspaces/{graphspace}/graphs/{name}/default—
rest.graphs.unset_default()DELETE/graphspaces/{graphspace}/graphs/{name}/default—
rest.gremlin.get()GET/gremlingremlin, language; additional query map
rest.gremlin.post()POST/gremlin—
rest.gremlin_job.post()POST/graphspaces/{graphspace}/graphs/{graph}/jobs/gremlin—
rest.group.create()POST/auth/groups—
rest.group.delete()DELETE/auth/groups/{id}—
rest.group.get()GET/auth/groups/{id}—
rest.group.list()GET/auth/groupslimit
rest.group.update()PUT/auth/groups/{id}—
rest.index_label.create()POST/graphspaces/{graphspace}/graphs/{graph}/schema/indexlabels—
rest.index_label.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/schema/indexlabels/{name}—
rest.index_label.get()GET/graphspaces/{graphspace}/graphs/{graph}/schema/indexlabels/{name}—
rest.index_label.list()GET/graphspaces/{graphspace}/graphs/{graph}/schema/indexlabelsnames
rest.index_label.update()PUT/graphspaces/{graphspace}/graphs/{graph}/schema/indexlabels/{name}action
rest.jaccard_similarity.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/jaccardsimilarityvertex, other, direction, label, max_degree
rest.jaccard_similarity.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/jaccardsimilarity—
rest.kneighbor.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/kneighborsource, direction, label, max_depth, count_only, max_degree, limit
rest.kneighbor.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/kneighbor—
rest.kout.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/koutsource, direction, label, max_depth, nearest, count_only, max_degree, capacity, limit
rest.kout.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/kout—
rest.login.login()POST/auth/login—
rest.login.logout()DELETE/auth/logout—
rest.login.verify_token()GET/auth/verify—
rest.manager.check_default_role()GET/graphspaces/{graphspace}/auth/managers/defaultrole, graph
rest.manager.check_role()GET/graphspaces/{graphspace}/auth/managers/checktype
rest.manager.create_manager()POST/graphspaces/{graphspace}/auth/managers—
rest.manager.delete()DELETE/graphspaces/{graphspace}/auth/managersuser, type
rest.manager.get_roles_in_gs()GET/graphspaces/{graphspace}/auth/managers/roleuser
rest.manager.list()GET/graphspaces/{graphspace}/auth/managerstype
rest.metrics.all()GET/metricstype
rest.metrics.backend()GET/metrics/backend—
rest.metrics.counters()GET/metrics/counters—
rest.metrics.gauges()GET/metrics/gauges—
rest.metrics.histograms()GET/metrics/histograms—
rest.metrics.meters()GET/metrics/meters—
rest.metrics.statistics()GET/metrics/statisticstype
rest.metrics.system()GET/metrics/system—
rest.metrics.timers()GET/metrics/timers—
rest.multi_node_shortest_path.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/multinodeshortestpath—
rest.neighbor_rank.neighbor_rank()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/neighborrank—
rest.paths.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/pathssource, target, direction, label, max_depth, max_degree, capacity, limit
rest.paths.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/paths—
rest.personal_rank.personal_rank()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/personalrank—
rest.profile.get_profile()GET/—
rest.profile.show_all_apis()GET/apis—
rest.project.create()POST/graphspaces/{graphspace}/auth/projects—
rest.project.delete()DELETE/graphspaces/{graphspace}/auth/projects/{id}—
rest.project.get()GET/graphspaces/{graphspace}/auth/projects/{id}—
rest.project.list()GET/graphspaces/{graphspace}/auth/projectslimit
rest.project.update()PUT/graphspaces/{graphspace}/auth/projects/{id}action
rest.property_key.create()POST/graphspaces/{graphspace}/graphs/{graph}/schema/propertykeys—
rest.property_key.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/schema/propertykeys/{name}—
rest.property_key.get()GET/graphspaces/{graphspace}/graphs/{graph}/schema/propertykeys/{name}—
rest.property_key.list()GET/graphspaces/{graphspace}/graphs/{graph}/schema/propertykeysnames
rest.property_key.update()PUT/graphspaces/{graphspace}/graphs/{graph}/schema/propertykeys/{name}action
rest.raft.add_peer()POST/graphspaces/{graphspace}/graphs/{graph}/raft/add_peergroup, endpoint
rest.raft.get_leader()GET/graphspaces/{graphspace}/graphs/{graph}/raft/get_leadergroup
rest.raft.list_peers()GET/graphspaces/{graphspace}/graphs/{graph}/raft/list_peersgroup
rest.raft.remove_peer()POST/graphspaces/{graphspace}/graphs/{graph}/raft/remove_peergroup, endpoint
rest.raft.set_leader()POST/graphspaces/{graphspace}/graphs/{graph}/raft/set_leadergroup, endpoint
rest.raft.transfer_leader()POST/graphspaces/{graphspace}/graphs/{graph}/raft/transfer_leadergroup, endpoint
rest.rays.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/rayssource, direction, label, max_depth, max_degree, capacity, limit, with_vertex, with_edge
rest.rebuild.edge_label_rebuild()PUT/graphspaces/{graphspace}/graphs/{graph}/jobs/rebuild/edgelabels/{name}—
rest.rebuild.index_label_rebuild()PUT/graphspaces/{graphspace}/graphs/{graph}/jobs/rebuild/indexlabels/{name}—
rest.rebuild.vertex_label_rebuild()PUT/graphspaces/{graphspace}/graphs/{graph}/jobs/rebuild/vertexlabels/{name}—
rest.resource_allocation.create()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/resourceallocationvertex, other, direction, label, max_degree, limit
rest.rings.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/ringssource, direction, label, max_depth, source_in_ring, max_degree, capacity, limit, with_vertex, with_edge
rest.same_neighbors.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/sameneighborsvertex, other, direction, label, max_degree, limit
rest.same_neighbors.same_neighbors()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/sameneighbors—
rest.same_neighbors_batch.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/sameneighborsbatch—
rest.schema.list()GET/graphspaces/{graphspace}/graphs/{graph}/schema—
rest.schema_template.create()POST/graphspaces/{graphspace}/schematemplates—
rest.schema_template.delete()DELETE/graphspaces/{graphspace}/schematemplates/{name}—
rest.schema_template.get()GET/graphspaces/{graphspace}/schematemplates/{name}—
rest.schema_template.list()GET/graphspaces/{graphspace}/schematemplates—
rest.schema_template.update()PUT/graphspaces/{graphspace}/schematemplates/{name}—
rest.shortest_path.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/shortestpathsource, target, direction, label, max_depth, max_degree, skip_degree, with_vertex, with_edge, capacity
rest.single_source_shortest_path.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/singlesourceshortestpathsource, direction, label, weight, max_degree, skip_degree, with_vertex, with_edge, capacity, limit
rest.target.create()POST/graphspaces/{graphspace}/auth/targets—
rest.target.delete()DELETE/graphspaces/{graphspace}/auth/targets/{id}—
rest.target.get()GET/graphspaces/{graphspace}/auth/targets/{id}—
rest.target.list()GET/graphspaces/{graphspace}/auth/targetslimit
rest.target.update()PUT/graphspaces/{graphspace}/auth/targets/{id}—
rest.task.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/tasks/{id}force
rest.task.get()GET/graphspaces/{graphspace}/graphs/{graph}/tasks/{id}with_result
rest.task.list()GET/graphspaces/{graphspace}/graphs/{graph}/tasksstatus, ids, limit, page
rest.task.update()PUT/graphspaces/{graphspace}/graphs/{graph}/tasks/{id}action
rest.template_paths.post()POST/graphspaces/{graphspace}/graphs/{graph}/traversers/templatepaths—
rest.user.create()POST/graphspaces/{graphspace}/auth/users—
rest.user.delete()DELETE/graphspaces/{graphspace}/auth/users/{id}—
rest.user.get()GET/graphspaces/{graphspace}/auth/users/{id}—
rest.user.list()GET/graphspaces/{graphspace}/auth/usersname, limit
rest.user.role()GET/graphspaces/{graphspace}/auth/users/{id}/role—
rest.user.update()PUT/graphspaces/{graphspace}/auth/users/{id}—
rest.variables.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/variables/{key}—
rest.variables.get()GET/graphspaces/{graphspace}/graphs/{graph}/variables/{key}—
rest.variables.list()GET/graphspaces/{graphspace}/graphs/{graph}/variables—
rest.variables.update()PUT/graphspaces/{graphspace}/graphs/{graph}/variables/{key}—
rest.version.list()GET/versions—
rest.vertex.create()POST/graphspaces/{graphspace}/graphs/{graph}/graph/vertices—
rest.vertex.create_batch()POST/graphspaces/{graphspace}/graphs/{graph}/graph/vertices/batch—
rest.vertex.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/graph/vertices/{id}label
rest.vertex.get()GET/graphspaces/{graphspace}/graphs/{graph}/graph/vertices/{id}—
rest.vertex.list()GET/graphspaces/{graphspace}/graphs/{graph}/graph/verticeslabel, properties, keep_start_p, offset, page, limit
rest.vertex.update_batch()PUT/graphspaces/{graphspace}/graphs/{graph}/graph/vertices/batch—
rest.vertex.update_by_id()PUT/graphspaces/{graphspace}/graphs/{graph}/graph/vertices/{id}action
rest.vertex_label.create()POST/graphspaces/{graphspace}/graphs/{graph}/schema/vertexlabels—
rest.vertex_label.delete()DELETE/graphspaces/{graphspace}/graphs/{graph}/schema/vertexlabels/{name}—
rest.vertex_label.get()GET/graphspaces/{graphspace}/graphs/{graph}/schema/vertexlabels/{name}—
rest.vertex_label.list()GET/graphspaces/{graphspace}/graphs/{graph}/schema/vertexlabelsnames
rest.vertex_label.update()PUT/graphspaces/{graphspace}/graphs/{graph}/schema/vertexlabels/{name}action
rest.vertices.list()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/verticesids
rest.vertices.scan()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/vertices/scanstart, end, page, page_limit
rest.vertices.shards()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/vertices/shardssplit_size
rest.weighted_shortest_path.get()GET/graphspaces/{graphspace}/graphs/{graph}/traversers/weightedshortestpathsource, target, direction, label, weight, max_degree, skip_degree, with_vertex, with_edge, capacity
rest.white_ip_list.list()GET/whiteiplist—
rest.white_ip_list.update_status()PUT/whiteipliststatus
rest.white_ip_list.update_white_ips()POST/whiteiplist—

Error Handling

Exceptions reside in pyhugegraph.utils.exceptions:

ExceptionRaised when
NotAuthorizedErrorServer responds with HTTP 401
NotFoundErrorServer responds with HTTP 404
ServerErrorNon-2xx server response (attaches server error payload)
ResponseParseErrorResponse body cannot be decoded to the expected structure
ServiceUnavailableErrorServer is temporarily unavailable
InvalidParameterError, CreateError, RemoveError, UpdateError, DataFormatErrorRaised on client-side validation failures

Sensitive fields (passwords, tokens, secrets) are masked automatically in logs.

1from pyhugegraph.utils.exceptions import NotFoundError
2
3try:
4    graph.get_vertex_by_id("missing-id")
5except NotFoundError:
6    print("Vertex not found")

Development and Verification

Run code quality and test suites from the root of the HugeGraph-AI repository:

  1. Format and lint checks:

    1uv run --extra dev ruff format --check .
    2uv run --extra dev ruff check .
    3uv run --extra dev ty check hugegraph-python-client/src/pyhugegraph
  2. Run unit and contract tests:

    1uv run pytest hugegraph-python-client/src/tests -m "unit or contract"
  3. Run integration tests against a HugeGraph Server:

    1HUGEGRAPH_URL=http://127.0.0.1:8080 \
    2HUGEGRAPH_GRAPH=hugegraph \
    3HUGEGRAPH_USER=admin \
    4HUGEGRAPH_PASSWORD=admin \
    5uv run pytest hugegraph-python-client/src/tests -m "integration and hugegraph"

Upstream CI validates against hugegraph/hugegraph:latest and regression tests against 1.7.0. Source code and test suites reside in hugegraph-python-client/src/pyhugegraph/ and hugegraph-python-client/src/tests/.

3 - HugeGraph Go Client Quick Start

HugeGraph Go Client is the Go SDK in the Toolchain repository. It currently provides APIs for version queries, schemas (property keys, vertex labels, and edge labels), vertices, and Gremlin. An edge data API is not implemented yet.

This module is still under development. Refer to the source code under hugegraph-client-go/api/v1 for the currently available interfaces.

Requirements

  • Go 1.19 or later
  • An accessible HugeGraph Server; examples use http://127.0.0.1:8080

Installation

Run the following command in a Go module project:

1go get github.com/apache/hugegraph-toolchain/hugegraph-client-go

Initialize the Client

NewCommonClient requires Host to be an IP address and Port to be between 1 and 65535. The client always connects over plain HTTP. Leave the username and password empty when authentication is disabled; Basic Auth is sent only when both are set.

When GraphSpace is nonempty, the Vertex and schema APIs (Schema(), Propertykey, VertexLabel, and EdgeLabel) use /graphspaces/{space}/graphs/{graph}/...; an empty value selects the legacy /graphs/{graph}/... paths. Use DEFAULT for the default space. Gremlin default aliases also use GraphSpace, treating an empty value as DEFAULT. Version() calls /versions independently of graph space.

 1package main
 2
 3import (
 4	"fmt"
 5	"log"
 6
 7	hugegraph "github.com/apache/hugegraph-toolchain/hugegraph-client-go"
 8)
 9
10func main() {
11	client, err := hugegraph.NewCommonClient(hugegraph.Config{
12		Host:       "127.0.0.1",
13		Port:       8080,
14		GraphSpace: "DEFAULT",
15		Graph:      "hugegraph",
16		Username:   "",
17		Password:   "",
18	})
19	if err != nil {
20		log.Fatal(err)
21	}
22
23	response, err := client.Version()
24	if err != nil {
25		log.Fatal(err)
26	}
27	defer response.Body.Close()
28
29	fmt.Println(response.Versions.Version)
30}

The Versions value returned by Version() includes the HugeGraph Server, Core, Gremlin, and REST API versions. The NewDefaultCommonClient() helper in the source connects to the hugegraph graph at 127.0.0.1:8080 with admin/pa authentication and a ColorLogger that prints every request and response body. Production code should normally pass an explicit configuration instead.

Configuration Options

hugegraph.Config has the following fields:

FieldTypeDescription
HoststringHugeGraph Server IP address. Host names are rejected.
PortintHugeGraph Server REST port, 1 to 65535
GraphSpacestringGraph space for the Vertex and schema APIs and default Gremlin aliases; use DEFAULT for the default space.
GraphstringGraph name configured on the server
UsernamestringServer username; empty string when authentication is disabled
PasswordstringServer password; empty string when authentication is disabled
Transporthttp.RoundTripperCustom HTTP transport; http.DefaultTransport when nil
Loggerhgtransport.LoggerRequest/response logger; no logging when nil

The hgtransport package ships four loggers: TextLogger (plain text), ColorLogger (terminal colors), CurlLogger (runnable curl commands), and JSONLogger (JSON lines). Each has the same fields: Output (an io.Writer), EnableRequestBody, and EnableResponseBody.

 1import (
 2	"os"
 3
 4	hugegraph "github.com/apache/hugegraph-toolchain/hugegraph-client-go"
 5	"github.com/apache/hugegraph-toolchain/hugegraph-client-go/hgtransport"
 6)
 7
 8client, err := hugegraph.NewCommonClient(hugegraph.Config{
 9	Host:  "127.0.0.1",
10	Port:  8080,
11	Graph: "hugegraph",
12	Logger: &hgtransport.ColorLogger{
13		Output:             os.Stdout,
14		EnableRequestBody:  true,
15		EnableResponseBody: true,
16	},
17})

Available Entry Points

CommonClient currently exposes the following entry points:

Entry pointPurpose
Version()Query the server version
Schema()Query the complete schema
PropertykeyCreate, GetAll, GetByName, UpdateUserdata, DeleteByName
VertexLabelCreate, GetAll, GetByName, UpdateUserdata, DeleteByName
EdgeLabelCreate, GetAll, DeleteByName
VertexCreate, BatchCreate, UpdateProperties (with WithAction: append or eliminate)
GremlinGet and Post. Post defaults language to gremlin-groovy, fills the graph/g aliases from GraphSpace and Graph, and returns the parsed result in Data. Get only returns the status code and prints the raw response to stdout.

Each operation takes functional options named With... on the operation itself, for example client.Gremlin.Post.WithGremlin(...) or client.Propertykey.GetByName.WithName(...).

EdgeLabel.Create accepts Properties: nil or an empty []string{} in its request data to create an edge label without properties.

Typed APIs return err for request validation, transport, response reading, or JSON decoding failures. An HTTP 4xx/5xx response can still return err == nil; for example, creating a vertex with a nonexistent label returns HTTP 400. Check that response.StatusCode is in the 2xx range before reading result data. For Gremlin.Post, also check response.Data.Status.Code for a successful Gremlin protocol status (2xx).

 1resp, err := client.Gremlin.Post(
 2	client.Gremlin.Post.WithGremlin("g.V().limit(3)"),
 3)
 4if err != nil {
 5	log.Fatal(err)
 6}
 7defer resp.Body.Close()
 8if resp.StatusCode < 200 || resp.StatusCode >= 300 {
 9	log.Fatalf("HugeGraph returned HTTP %d", resp.StatusCode)
10}
11if resp.Data.Status.Code < 200 || resp.Data.Status.Code >= 300 {
12	log.Fatalf("Gremlin returned status %d: %s", resp.Data.Status.Code, resp.Data.Status.Message)
13}
14fmt.Println(resp.Data.Result.Data)

The Vertex operations take model.Vertex[any] values from the internal/model package. Go does not allow importing an internal package from another module, so at the moment the Vertex API can only be called from code inside the client module itself; its test file is also fully commented out.

For complete usage, see the tests in each API directory, such as version_test.go, gemlin_test.go, and vertexlabel_test.go.