diff --git a/CHANGELOG.asciidoc b/CHANGELOG.asciidoc index 456dfd807bb..eb65455576f 100644 --- a/CHANGELOG.asciidoc +++ b/CHANGELOG.asciidoc @@ -81,6 +81,7 @@ image::https://raw.githubusercontent.com/apache/tinkerpop/master/docs/static/ima * Removed `minSize` setting for Gremlin Driver connection pool since connections are now short-lived HTTP connections * Added `idleConnectionTimeout` setting for Gremlin Driver and automatic closing of idle connections * Enabled TCP Keep-Alive in GremlinServer. +* Updated Python GLV examples to use HTTP and to run as part of the integration tests. == TinkerPop 3.8.0 (Grix Greven) diff --git a/gremlin-examples/gremlin-python/basic_gremlin.py b/gremlin-examples/gremlin-python/basic_gremlin.py index 256ed984416..c351270de85 100644 --- a/gremlin-examples/gremlin-python/basic_gremlin.py +++ b/gremlin-examples/gremlin-python/basic_gremlin.py @@ -23,15 +23,17 @@ from gremlin_python.process.strategies import * from gremlin_python.driver.driver_remote_connection import DriverRemoteConnection +VERTEX_LABEL = 'person' def main(): - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g') + server_url = 'ws://localhost:8182/gremlin' + rc = DriverRemoteConnection(server_url, 'g') g = traversal().with_remote(rc) # basic Gremlin: adding and retrieving data - v1 = g.add_v('person').property('name', 'marko').next() - v2 = g.add_v('person').property('name', 'stephen').next() - v3 = g.add_v('person').property('name', 'vadas').next() + v1 = g.add_v(VERTEX_LABEL).property('name', 'marko').next() + v2 = g.add_v(VERTEX_LABEL).property('name', 'stephen').next() + v3 = g.add_v(VERTEX_LABEL).property('name', 'vadas').next() # be sure to use a terminating step like next() or iterate() so that the traversal "executes" # iterate() does not return any data and is used to just generate side-effects (i.e. write data to the database) @@ -39,11 +41,11 @@ def main(): g.V(v1).add_e('knows').to(v3).property('weight', 0.75).iterate() # retrieve the data from the "marko" vertex - marko = g.V().has('person', 'name', 'marko').values('name').next() + marko = g.V().has(VERTEX_LABEL, 'name', 'marko').values('name').next() print("name: " + marko) # find the "marko" vertex and then traverse to the people he "knows" and return their data - people_marko_knows = g.V().has('person', 'name', 'marko').out('knows').values('name').to_list() + people_marko_knows = g.V().has(VERTEX_LABEL, 'name', 'marko').out('knows').values('name').to_list() for person in people_marko_knows: print("marko knows " + person) diff --git a/gremlin-examples/gremlin-python/connections.py b/gremlin-examples/gremlin-python/connections.py index f268e6c27d5..9997a181ebf 100644 --- a/gremlin-examples/gremlin-python/connections.py +++ b/gremlin-examples/gremlin-python/connections.py @@ -24,6 +24,7 @@ from gremlin_python.driver.driver_remote_connection import DriverRemoteConnection from gremlin_python.driver.serializer import GraphBinarySerializersV1 +VERTEX_LABEL = 'connection' def main(): with_remote() @@ -40,15 +41,13 @@ def with_remote(): # # which starts it in "console" mode with an empty in-memory TinkerGraph ready to go bound to a # variable named "g" as referenced in the following line. - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g') + server_url = 'ws://localhost:8182/gremlin' + rc = DriverRemoteConnection(server_url, 'g') g = traversal().with_remote(rc) - # drop existing vertices - g.V().drop().iterate() - # simple query to verify connection - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) # cleanup @@ -57,11 +56,12 @@ def with_remote(): # connecting with plain text authentication def with_auth(): - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g', username='stephen', password='password') + server_url = 'ws://localhost:8182/gremlin' + rc = DriverRemoteConnection(server_url, 'g', username='stephen', password='password') g = traversal().with_remote(rc) - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) rc.close() @@ -69,11 +69,12 @@ def with_auth(): # connecting with Kerberos SASL authentication def with_kerberos(): - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g', kerberized_service='gremlin@hostname.your.org') + server_url = 'ws://localhost:8182/gremlin' + rc = DriverRemoteConnection(server_url, 'g', kerberized_service='gremlin@hostname.your.org') g = traversal().with_remote(rc) - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) rc.close() @@ -81,8 +82,9 @@ def with_kerberos(): # connecting with customized configurations def with_configs(): + server_url = 'ws://localhost:8182/gremlin' rc = DriverRemoteConnection( - 'ws://localhost:8182/gremlin', 'g', + server_url, 'g', username="", password="", kerberized_service='', message_serializer=GraphBinarySerializersV1(), graphson_reader=None, graphson_writer=None, headers=None, session=None, @@ -90,8 +92,8 @@ def with_configs(): ) g = traversal().with_remote(rc) - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) rc.close() diff --git a/gremlin-python/docker-compose.yml b/gremlin-python/docker-compose.yml index bdc7f6332b3..a1baa4809b8 100644 --- a/gremlin-python/docker-compose.yml +++ b/gremlin-python/docker-compose.yml @@ -64,7 +64,12 @@ services: && radish -f dots -e -t -b ./radish ./gremlin-test --user-data='serializer=application/vnd.graphbinary-v4.0' --user-data='parameterize=true' && radish -f dots -e -t -b ./radish ./gremlin-test --user-data='serializer=application/vnd.graphbinary-v4.0' && radish -f dots -e -t -b ./radish ./gremlin-test --user-data='serializer=application/vnd.gremlin-v4.0+json' --user-data='parameterize=true' - && radish -f dots -e -t -b ./radish ./gremlin-test --user-data='serializer=application/vnd.gremlin-v4.0+json'; + && radish -f dots -e -t -b ./radish ./gremlin-test --user-data='serializer=application/vnd.gremlin-v4.0+json' + && echo 'Running examples...' + && python3 examples/basic_gremlin.py + && python3 examples/connections.py + && python3 examples/modern_traversals.py + && echo 'All examples completed successfully'; EXIT_CODE=$$?; chown -R `stat -c "%u:%g" .` .; exit $$EXIT_CODE" depends_on: gremlin-server-test-python: diff --git a/gremlin-python/src/main/python/examples/basic_gremlin.py b/gremlin-python/src/main/python/examples/basic_gremlin.py index 256ed984416..873fd0a731b 100644 --- a/gremlin-python/src/main/python/examples/basic_gremlin.py +++ b/gremlin-python/src/main/python/examples/basic_gremlin.py @@ -16,34 +16,39 @@ # under the License. import sys +import os sys.path.append("..") from gremlin_python.process.anonymous_traversal import traversal +from gremlin_python.process.graph_traversal import __ from gremlin_python.process.strategies import * from gremlin_python.driver.driver_remote_connection import DriverRemoteConnection +VERTEX_LABEL = os.getenv('VERTEX_LABEL', 'person') def main(): - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g') + # if there is a port placeholder in the env var then we are running with docker so set appropriate port + server_url = os.getenv('GREMLIN_SERVER_URL', 'http://localhost:8182/gremlin').format(45940) + rc = DriverRemoteConnection(server_url, 'g') g = traversal().with_remote(rc) # basic Gremlin: adding and retrieving data - v1 = g.add_v('person').property('name', 'marko').next() - v2 = g.add_v('person').property('name', 'stephen').next() - v3 = g.add_v('person').property('name', 'vadas').next() + v1 = g.add_v(VERTEX_LABEL).property('name', 'marko').next() + v2 = g.add_v(VERTEX_LABEL).property('name', 'stephen').next() + v3 = g.add_v(VERTEX_LABEL).property('name', 'vadas').next() # be sure to use a terminating step like next() or iterate() so that the traversal "executes" # iterate() does not return any data and is used to just generate side-effects (i.e. write data to the database) - g.V(v1).add_e('knows').to(v2).property('weight', 0.75).iterate() - g.V(v1).add_e('knows').to(v3).property('weight', 0.75).iterate() + g.V(v1).add_e('knows').to(__.V(v2)).property('weight', 0.75).iterate() + g.V(v1).add_e('knows').to(__.V(v3)).property('weight', 0.75).iterate() # retrieve the data from the "marko" vertex - marko = g.V().has('person', 'name', 'marko').values('name').next() + marko = g.V().has(VERTEX_LABEL, 'name', 'marko').values('name').next() print("name: " + marko) # find the "marko" vertex and then traverse to the people he "knows" and return their data - people_marko_knows = g.V().has('person', 'name', 'marko').out('knows').values('name').to_list() + people_marko_knows = g.V().has(VERTEX_LABEL, 'name', 'marko').out('knows').values('name').to_list() for person in people_marko_knows: print("marko knows " + person) diff --git a/gremlin-python/src/main/python/examples/connections.py b/gremlin-python/src/main/python/examples/connections.py index f268e6c27d5..f396a8d7972 100644 --- a/gremlin-python/src/main/python/examples/connections.py +++ b/gremlin-python/src/main/python/examples/connections.py @@ -14,21 +14,23 @@ # KIND, either express or implied. See the License for the # specific language governing permissions and limitations # under the License. - +import ssl import sys +import os sys.path.append("..") from gremlin_python.process.anonymous_traversal import traversal -from gremlin_python.process.strategies import * from gremlin_python.driver.driver_remote_connection import DriverRemoteConnection -from gremlin_python.driver.serializer import GraphBinarySerializersV1 +from gremlin_python.driver.aiohttp.transport import AiohttpHTTPTransport +from gremlin_python.driver.auth import basic +from gremlin_python.driver.serializer import GraphBinarySerializersV4 +VERTEX_LABEL = os.getenv('VERTEX_LABEL', 'connection') def main(): with_remote() with_auth() - with_kerberos() with_configs() @@ -40,15 +42,14 @@ def with_remote(): # # which starts it in "console" mode with an empty in-memory TinkerGraph ready to go bound to a # variable named "g" as referenced in the following line. - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g') + # if there is a port placeholder in the env var then we are running with docker so set appropriate port + server_url = os.getenv('GREMLIN_SERVER_URL', 'http://localhost:8182/gremlin').format(45940) + rc = DriverRemoteConnection(server_url, 'g') g = traversal().with_remote(rc) - # drop existing vertices - g.V().drop().iterate() - # simple query to verify connection - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) # cleanup @@ -57,45 +58,42 @@ def with_remote(): # connecting with plain text authentication def with_auth(): - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g', username='stephen', password='password') + # if there is a port placeholder in the env var then we are running with docker so set appropriate port + server_url = os.getenv('GREMLIN_SERVER_BASIC_AUTH_URL', 'http://localhost:8182/gremlin').format(45941) + + # disable SSL certificate verification for CI environments + if ':45941' in server_url: + ssl_opts = ssl.SSLContext(ssl.PROTOCOL_TLS_CLIENT) + ssl_opts.check_hostname = False + ssl_opts.verify_mode = ssl.CERT_NONE + rc = DriverRemoteConnection(server_url, 'g', auth=basic('stephen', 'password'), + transport_factory=lambda: AiohttpHTTPTransport(ssl_options=ssl_opts)) + else: + rc = DriverRemoteConnection(server_url, 'g', auth=basic('stephen', 'password')) + g = traversal().with_remote(rc) - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) rc.close() - -# connecting with Kerberos SASL authentication -def with_kerberos(): - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g', kerberized_service='gremlin@hostname.your.org') - g = traversal().with_remote(rc) - - v = g.add_v().iterate() - count = g.V().count().next() - print("Vertex count: " + str(count)) - - rc.close() - - # connecting with customized configurations def with_configs(): + server_url = os.getenv('GREMLIN_SERVER_URL', 'http://localhost:8182/gremlin').format(45940) rc = DriverRemoteConnection( - 'ws://localhost:8182/gremlin', 'g', - username="", password="", kerberized_service='', - message_serializer=GraphBinarySerializersV1(), graphson_reader=None, - graphson_writer=None, headers=None, session=None, - enable_user_agent_on_connect=True + server_url, 'g', + request_serializer=GraphBinarySerializersV4(), + headers=None, ) g = traversal().with_remote(rc) - v = g.add_v().iterate() - count = g.V().count().next() + v = g.add_v(VERTEX_LABEL).iterate() + count = g.V().has_label(VERTEX_LABEL).count().next() print("Vertex count: " + str(count)) rc.close() - if __name__ == "__main__": main() diff --git a/gremlin-python/src/main/python/examples/modern_traversals.py b/gremlin-python/src/main/python/examples/modern_traversals.py index ae757b10b4f..9feb66d7753 100644 --- a/gremlin-python/src/main/python/examples/modern_traversals.py +++ b/gremlin-python/src/main/python/examples/modern_traversals.py @@ -16,6 +16,7 @@ # under the License. import sys +import os sys.path.append("..") @@ -31,7 +32,16 @@ def main(): # This example requires the Modern toy graph to be preloaded upon launching the Gremlin server. # For details, see https://tinkerpop.apache.org/docs/current/reference/#gremlin-server-docker-image and use # conf/gremlin-server-modern.yaml. - rc = DriverRemoteConnection('ws://localhost:8182/gremlin', 'g') + # if there is a port placeholder in the env var then we are running with docker so set appropriate port + server_url = os.getenv('GREMLIN_SERVER_URL', 'http://localhost:8182/gremlin').format(45940) + + # CI uses port 45940 with gmodern binding, local uses 8182 with g binding + if ':45940' in server_url: + graph_binding = 'gmodern' # CI environment + else: + graph_binding = 'g' # Local environment + + rc = DriverRemoteConnection(server_url, graph_binding) g = traversal().with_remote(rc) e1 = g.V(1).both_e().to_list() # (1)